PolyTests is an in-memory implementation of ITelegramBotClient designed for automated testing. Register it instead of the real TelegramBotClient and you get a fully offline, deterministic test double that delivers synthetic updates to the polling loop with long-poll semantics and records every outgoing request for assertions.
Class overview
PolyTests requires no constructor arguments — instantiate it directly and pass it to DI:
Injecting updates
EnqueueUpdate
Adds a single update to the internal queue. If the polling loop is waiting (blocking on a long-poll), the signal fires immediately and the update is delivered in the nextGetUpdates batch.
EnqueueUpdates
Enqueues multiple updates in order. Each update signals the polling loop independently, so updates are never lost even if they arrive faster than the loop processes them.Asserting outgoing requests
SentRequests returns an IReadOnlyList<object> snapshot of every request the framework sent through the client, in the order they were made:
Telegram.Bot.Requests. Use LINQ to filter:
BotUser
TheUser returned by GetMe calls. Its type is Telegram.Bot.Types.User. The default value is:
Supported requests
PolyTests answers the subset of Telegram API requests that PolyBot’s own infrastructure uses. Anything outside this list throws NotSupportedException.
Long-poll semantics
GetUpdatesRequest is handled with genuine long-poll behaviour:
- If the queue contains updates, they are dequeued immediately (up to
request.Limit, defaulting to 100) and returned as a batch. - If the queue is empty, the method waits asynchronously until either
EnqueueUpdatesignals an update or theCancellationTokenis cancelled. - When
StopAsynccancels the token,GetUpdatesRequestthrowsOperationCanceledException, ending the polling loop cleanly.
Task.Delay polling or manual timing in tests.
Using PolyTests with AddPolyBotHostedPolling
RegisterPolyTests as ITelegramBotClient before calling AddPolyBotHostedPolling. The hosted service picks up the test client from DI:
Using PolyTests with AddPolyBotWebhook
For webhook integration tests, resolve the hosted service to triggerStartAsync, which calls SetWebhook, then stop it to trigger DeleteWebhook: