:bug: run the ws-session sync handlers on the test dispatcher to fix a CI flake (#5058)
GeneralSyncManagerTest's two ws-session tests build handlers through
GeneralSyncManager.createSyncHandler, which hardcoded
namedScope(ioDispatcher, "GeneralSyncHandler"). The handler and its
SyncPollingManager therefore ran on real Dispatchers.IO threads while the
test drove virtual time.
The verified path — registerSession -> onSessionOpened -> fastReconnect ->
SyncPollingManager.reset() -> forceResolve() -> emitEvent — suspends on
reset()'s stateMutex. The polling loop grabs that same mutex on its first
waitForNextExecution (nextExecutionTime starts at 0), on an IO thread the
test scheduler knows nothing about. When the two collide, advanceUntilIdle()
returns with fastReconnect still parked on the mutex and the verify fails
with "emitEvent was not called". That is what run 35852991873 hit on main;
the same commit had passed on its PR branch minutes earlier.
createSyncHandler now takes its scope from a syncHandlerScopeFactory
constructor parameter, defaulting to the current behaviour. It is a factory
rather than a scope because SyncHandler.cancelScope() must only tear down
its own handler. The two ws tests pass a factory backed by the test
dispatcher, so the whole chain stays on virtual time.
Those two tests also switch from advanceUntilIdle() to a bounded
advanceTimeBy(100), the same approach GeneralSyncHandlerTest already uses:
once the handler is on the test dispatcher, SyncPollingManager's
`while (isActive) { delay(...) }` loop is on virtual time too, and
advanceUntilIdle() would spin forever. The rest of the class is untouched
and keeps the production IO scope. Y
Yiqun Zhang committed
f32c19b5f0e604efecbef3a78108a984f88976fe
Parent: e93c181
Committed by GitHub <noreply@github.com>
on 9/23/2026, 1:17:07 PM