Skip to content

Speed up the SQS test suite - #1679

Merged
tomazfernandes merged 4 commits into
awspring:mainfrom
tomazfernandes:sqs-speedup
Aug 9, 2026
Merged

Speed up the SQS test suite#1679
tomazfernandes merged 4 commits into
awspring:mainfrom
tomazfernandes:sqs-speedup

Conversation

@tomazfernandes

Copy link
Copy Markdown
Contributor

Changes

Test code only. No test is removed or weakened.

Give the factories explicit shutdown timeouts. Every integration class paid the 20 second listener and 20 second acknowledgement shutdown defaults when its context closed. Set both to zero on the factories the tests already declare. SqsIntegrationTests keeps its default factory untouched, so its listeners still exercise the production defaults.

Start Localstack off the worker threads. The start ran inside a synchronized @BeforeAll and held its worker thread throughout, so the module spent its first twenty seconds with one or two tests in flight. Start it during discovery instead, and order the classes that need no container first to fill that window.

Shrink the error handler backoff windows. Linear ran 2+4+6 seconds and the jittered exponential 2+4+8 before the fourth delivery. The listeners compute their expected elapsed time from the same constants and assert with >=, so the contract is unchanged. #1675 covers the arithmetic.

Stop three unit tests waiting on real time. CompositeBackPressureHandlerTest waited five seconds to assert a one second minimum, and slept 200ms for a thread to block. A two second timeout still proves the assertion, and the thread's state is observable directly. MessageGroupingSinkTests and BatchingAcknowledgementProcessorTests sleep a random interval for ordering variety, so the range is shorter.

Result

Two runs of each on CI against current main, launched together.

JDK Before After
17 2:03 / 1:48 1:32 / 1:28
21 2:05 / 2:02 1:24 / 1:24
24 2:06 / 2:01 1:28 / 1:35

Green on all six jobs. Test counts are unchanged.

Every integration class paid the production defaults of a twenty second
listener shutdown and a twenty second acknowledgement shutdown when its context
closed. Set both to zero on the factories the tests already declare, so the
setting is visible where it applies and a test can opt out, rather than through
a global customizer that would override every class silently.

The SQS module goes from about 2:05 to about 1:22 across the three JDKs.

Acknowledgement batching is left alone. Zeroing the interval and threshold as
well was measured and bought nothing: it turns every acknowledgement into its
own call and the added load failed the interceptor and back pressure tests in
both runs it was tried in.

SqsIntegrationTests keeps its default factory untouched so its listeners still
exercise the production defaults.
The container start ran inside a synchronized @BeforeAll, so the first classes
scheduled held their worker threads for its whole duration. A plain blocking
wait does not make the pool compensate with another thread, so the module spent
its first twenty seconds with one or two tests in flight while five hundred
unit tests that need no container waited behind it.

Start it when discovery orders the classes, and order the classes that need no
container first so they fill that window. The start is asked for only when a
class in the run needs it, so a run of unit tests alone still starts nothing.

The test phase goes from 74.7 to 65.9 seconds, and the first ten seconds go
from one or two tests in flight to five to seven.
The class is the tail of the module and its longest methods are spent waiting
out real backoff: linear ran 2+4+6 seconds and the jittered exponential 2+4+8
before the fourth delivery.

The listeners derive their expected elapsed time from the same constants and
assert with '>=', so the contract that backoff delays redelivery is unchanged,
and the arithmetic itself is covered by JitterStrategiesTest and
JitterContextTest. awspring#1676 removed the assertion floors; this reduces the wait
those assertions were measuring.

The test phase goes from 57.9 to 50.5 seconds.
These have no container and no IO, so the time they spend is simulated rather
than waited on.

CompositeBackPressureHandlerTest configured a five second no-permits timeout
for a test that asserts the wait lasted at least one second, and slept a fixed
200ms to let a thread reach a blocking state. Use a two second timeout, which
still proves the assertion, and observe the thread's state instead of guessing
how long it takes to get there.

MessageGroupingSinkTests and BatchingAcknowledgementProcessorTests sleep for a
random interval to vary completion order. The variation is the point, not its
magnitude, so shorten the range.

The sleep whose length decides whether acknowledgements are still in flight
when the processor stops is left alone, since the assertion depends on it.
@github-actions github-actions Bot added the component: sqs SQS integration related issue label Aug 9, 2026
@tomazfernandes
tomazfernandes merged commit df72150 into awspring:main Aug 9, 2026
6 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

component: sqs SQS integration related issue

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant