Skip to content

Commit 6e09641

Browse files
committed
Replace time.Sleep in tests with deterministic synchronization
Use require.Eventually, time.AfterFunc, and channel synchronization instead of fixed time.Sleep calls to make tests faster and less flaky. - telemetry: poll mockHTTP.GetRequestCount() with require.Eventually - fake/proxy: use channel write and require.Eventually for sync points - runtime/fallback: use time.AfterFunc for context cancel, require.Eventually for cooldown expiry - tui/styles: poll atomic callback counter with require.Eventually Assisted-By: cagent
1 parent 1577440 commit 6e09641

5 files changed

Lines changed: 41 additions & 58 deletions

File tree

pkg/fake/proxy_test.go

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -234,8 +234,8 @@ func TestStreamCopy_ContextCancellation(t *testing.T) {
234234
done <- StreamCopy(c, resp)
235235
}()
236236

237-
// Give StreamCopy time to start and block on the read
238-
time.Sleep(50 * time.Millisecond)
237+
// Write some data to ensure StreamCopy is actively reading before we cancel
238+
slowBody.data <- []byte("initial")
239239

240240
// Cancel the context - this should cause StreamCopy to return immediately
241241
cancel()
@@ -328,8 +328,10 @@ func TestSimulatedStreamCopy_ContextCancellation(t *testing.T) {
328328
done <- SimulatedStreamCopy(c, resp, 10*time.Millisecond)
329329
}()
330330

331-
// Wait for data to be written
332-
time.Sleep(50 * time.Millisecond)
331+
// Wait until at least the first chunk has been written to the recorder
332+
require.Eventually(t, func() bool {
333+
return rec.Body.Len() > 0
334+
}, time.Second, 5*time.Millisecond, "expected first chunk to be written")
333335

334336
// Cancel the context and close the body (simulating client disconnect)
335337
cancel()

pkg/runtime/fallback_test.go

Lines changed: 4 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -243,10 +243,7 @@ func TestSleepWithContext(t *testing.T) {
243243
ctx, cancel := context.WithCancel(t.Context())
244244

245245
// Cancel context after a short delay
246-
go func() {
247-
time.Sleep(10 * time.Millisecond)
248-
cancel()
249-
}()
246+
time.AfterFunc(10*time.Millisecond, cancel)
250247

251248
start := time.Now()
252249
completed := sleepWithContext(ctx, 1*time.Second)
@@ -699,11 +696,9 @@ func TestFallbackCooldownState(t *testing.T) {
699696
assert.Equal(t, 0, state.fallbackIndex)
700697

701698
// Wait for cooldown to expire
702-
time.Sleep(150 * time.Millisecond)
703-
704-
// Should no longer be in cooldown
705-
state = rt.getCooldownState(agentName)
706-
assert.Nil(t, state, "cooldown should have expired")
699+
require.Eventually(t, func() bool {
700+
return rt.getCooldownState(agentName) == nil
701+
}, time.Second, 10*time.Millisecond, "cooldown should have expired")
707702

708703
// Set cooldown again and then clear it
709704
rt.setCooldownState(agentName, 1, 1*time.Hour)

pkg/runtime/runtime_test.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -577,7 +577,8 @@ func TestStartBackgroundRAGInit_StopsForwardingAfterContextCancel(t *testing.T)
577577
// Cancel the context and ensure no further events are forwarded.
578578
cancel()
579579

580-
// Give the forwarder time to observe cancellation.
580+
// Brief yield to allow the forwarder goroutine to observe cancellation.
581+
// This is a timing-based negative test: we verify no event is forwarded.
581582
time.Sleep(10 * time.Millisecond)
582583

583584
// Emit another event; it should NOT be forwarded.

pkg/telemetry/telemetry_test.go

Lines changed: 21 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -128,12 +128,11 @@ func TestSessionTracking(t *testing.T) {
128128
// Multiple ends should be safe
129129
client.RecordSessionEnd(ctx)
130130

131-
// Wait for events to be processed
132-
time.Sleep(20 * time.Millisecond)
131+
require.Eventually(t, func() bool {
132+
return mockHTTP.GetRequestCount() > 0
133+
}, time.Second, 5*time.Millisecond, "Expected HTTP requests to be made for session tracking events")
133134

134135
requestCount := mockHTTP.GetRequestCount()
135-
assert.Positive(t, requestCount, "Expected HTTP requests to be made for session tracking events")
136-
137136
t.Logf("Session tracking HTTP requests captured: %d", requestCount)
138137

139138
requests := mockHTTP.GetRequests()
@@ -165,12 +164,11 @@ func TestCommandTracking(t *testing.T) {
165164
require.NoError(t, err)
166165
assert.True(t, executed)
167166

168-
// Wait for events to be processed
169-
time.Sleep(20 * time.Millisecond)
167+
require.Eventually(t, func() bool {
168+
return mockHTTP.GetRequestCount() > 0
169+
}, time.Second, 5*time.Millisecond, "Expected HTTP requests to be made for command tracking")
170170

171171
requestCount := mockHTTP.GetRequestCount()
172-
assert.Positive(t, requestCount, "Expected HTTP requests to be made for command tracking")
173-
174172
t.Logf("Command tracking HTTP requests captured: %d", requestCount)
175173

176174
requests := mockHTTP.GetRequests()
@@ -200,12 +198,11 @@ func TestCommandTrackingWithError(t *testing.T) {
200198

201199
assert.Equal(t, testErr, err)
202200

203-
// Wait for events to be processed
204-
time.Sleep(20 * time.Millisecond)
201+
require.Eventually(t, func() bool {
202+
return mockHTTP.GetRequestCount() > 0
203+
}, time.Second, 5*time.Millisecond, "Expected HTTP requests to be made for command error tracking")
205204

206205
requestCount := mockHTTP.GetRequestCount()
207-
assert.Positive(t, requestCount, "Expected HTTP requests to be made for command error tracking")
208-
209206
t.Logf("Command error tracking HTTP requests captured: %d", requestCount)
210207
}
211208

@@ -493,11 +490,11 @@ func TestAllEventTypes(t *testing.T) {
493490
// End session
494491
client.RecordSessionEnd(ctx)
495492

496-
// Wait for events to be processed
497-
time.Sleep(20 * time.Millisecond)
493+
require.Eventually(t, func() bool {
494+
return mockHTTP.GetRequestCount() > 0
495+
}, time.Second, 5*time.Millisecond, "Expected HTTP requests to be made for telemetry events")
498496

499497
requestCount := mockHTTP.GetRequestCount()
500-
assert.Positive(t, requestCount, "Expected HTTP requests to be made for telemetry events")
501498

502499
t.Logf("Total HTTP requests captured: %d", requestCount)
503500

@@ -609,14 +606,12 @@ func TestHTTPRequestVerification(t *testing.T) {
609606

610607
client.Track(ctx, event)
611608

612-
// Give time for background processing
613-
time.Sleep(20 * time.Millisecond)
609+
require.Eventually(t, func() bool {
610+
return mockHTTP.GetRequestCount() > 0
611+
}, time.Second, 5*time.Millisecond, "Expected HTTP request to be made")
614612

615-
// Debug output
616613
t.Logf("HTTP requests captured: %d", mockHTTP.GetRequestCount())
617614

618-
assert.Positive(t, mockHTTP.GetRequestCount(), "Expected HTTP request to be made")
619-
620615
requests := mockHTTP.GetRequests()
621616
req := requests[0]
622617

@@ -699,11 +694,9 @@ func TestNon2xxHTTPResponseHandling(t *testing.T) {
699694

700695
client.Track(t.Context(), &CommandEvent{Action: "error-test", Success: true})
701696

702-
// Give time for background processing
703-
time.Sleep(20 * time.Millisecond)
704-
705-
requestCount := mockHTTP.GetRequestCount()
706-
assert.Positive(t, requestCount, "Expected HTTP request to be made despite error response")
697+
require.Eventually(t, func() bool {
698+
return mockHTTP.GetRequestCount() > 0
699+
}, time.Second, 5*time.Millisecond, "Expected HTTP request to be made despite error response")
707700

708701
mockHTTP.SetResponse(&http.Response{
709702
StatusCode: http.StatusNotFound,
@@ -714,8 +707,7 @@ func TestNon2xxHTTPResponseHandling(t *testing.T) {
714707

715708
client.Track(t.Context(), &CommandEvent{Action: "not-found-test", Success: true})
716709

717-
time.Sleep(20 * time.Millisecond)
718-
719-
finalRequestCount := mockHTTP.GetRequestCount()
720-
assert.GreaterOrEqual(t, finalRequestCount, 2, "Expected at least 2 HTTP requests (500 + 404)")
710+
require.Eventually(t, func() bool {
711+
return mockHTTP.GetRequestCount() >= 2
712+
}, time.Second, 5*time.Millisecond, "Expected at least 2 HTTP requests (500 + 404)")
721713
}

pkg/tui/styles/theme_watcher_test.go

Lines changed: 8 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -47,9 +47,6 @@ colors:
4747
err := watcher.Watch("test-theme")
4848
require.NoError(t, err)
4949

50-
// Give the watcher time to start
51-
time.Sleep(100 * time.Millisecond)
52-
5350
// Modify the theme file
5451
updatedContent := `version: 1
5552
name: Updated Theme
@@ -58,11 +55,10 @@ colors:
5855
`
5956
require.NoError(t, os.WriteFile(themePath, []byte(updatedContent), 0o644))
6057

61-
// Wait for the debounce timer and callback
62-
time.Sleep(1 * time.Second)
63-
64-
// Verify callback was called with the correct themeRef
65-
assert.GreaterOrEqual(t, callbackCount.Load(), int32(1), "callback should have been called at least once")
58+
// Wait for the watcher to detect the change and fire the callback
59+
require.Eventually(t, func() bool {
60+
return callbackCount.Load() >= 1
61+
}, 5*time.Second, 50*time.Millisecond, "callback should have been called at least once")
6662
ref, ok := lastThemeRef.Load().(string)
6763
assert.True(t, ok)
6864
assert.Equal(t, "test-theme", ref, "callback should receive the correct theme ref")
@@ -205,14 +201,11 @@ func TestThemeWatcher_SignalsOnAnyFileChange(t *testing.T) {
205201
err := watcher.Watch("signal-test")
206202
require.NoError(t, err)
207203

208-
time.Sleep(100 * time.Millisecond)
209-
210204
// Write any content (even invalid YAML) - watcher just signals, doesn't validate
211205
require.NoError(t, os.WriteFile(themePath, []byte("this is: [not: valid yaml"), 0o644))
212206

213-
// Wait for debounce
214-
time.Sleep(1 * time.Second)
215-
216-
// Callback SHOULD be called because watcher only signals - validation is TUI's job
217-
assert.GreaterOrEqual(t, callbackCount.Load(), int32(1), "callback should be called for any file change")
207+
// Wait for the watcher to detect the change and fire the callback
208+
require.Eventually(t, func() bool {
209+
return callbackCount.Load() >= 1
210+
}, 5*time.Second, 50*time.Millisecond, "callback should be called for any file change")
218211
}

0 commit comments

Comments
 (0)