Repository navigation
fix: replace batcher dependency to avoid shutdown deadlock in logmq - #1160
Merged
Merged
Conversation
alexbouchardd
approved these changes
Oct 23, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
The log consumer's
Shutdowncan hang until the process is killed. Inmikestefanello/batcherv0.1.0,Shutdown's final flush restarts the ticker as it returns, andShutdownthen takes the processing lock and keeps it. A tick in that window sends the ticker goroutine to wait on that lock, soShutdown's unbuffered send to that goroutine is never received. Pending messages are already flushed by then, so nothing is lost; only shutdown stalls.It is rare with the default 10 s batch delay. logmq tests use much shorter delays and hit it under CPU load:
TestCharacterization_TwoDestinationsInterleaved,TestDisabledSignals_FailedEmitFailure_Nacksand others fail now and then withbp.Shutdown did not return within 30s. Running the logmq tests in parallel with CPU burners, 13 of 80 runs hung before this change and none of 40 after.internal/batcherreplaces the dependency with a genericBatcher[T]. It flushes atMaxItems, orMaxWaitafter a batch's first item, and runs at mostMaxInFlightflushes at once. Flushes run outside its lock, soClosehas no handoff to wait on: it flushes what is pending and waits for running flushes. The dependency is removed fromgo.mod.Addthat fills a batch waits for the previous write to finish, then starts its own. Before, everyAddwaited while a batch was written; now the next batch can fill during a write.Other improvements:
TestDelivery_ExhaustedRetries_LoserAcksWhileWinnerInFlight: wait for bothattempt.failedsends before asserting; the winner's send runs concurrently and could land after the check.🤖 Generated with Claude Code