Skip to content

Commit 051080b

Browse files
committed
Timeout mw: rework how test waits for timeout. Using sleep as delay is problematic when CI worker is slower than usual.
1 parent 28797c7 commit 051080b

File tree

1 file changed

+22
-20
lines changed

1 file changed

+22
-20
lines changed

middleware/timeout_test.go

Lines changed: 22 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -328,12 +328,13 @@ func TestTimeoutCanHandleContextDeadlineOnNextHandler(t *testing.T) {
328328
func TestTimeoutWithFullEchoStack(t *testing.T) {
329329
// test timeout with full http server stack running, do see what http.Server.ErrorLog contains
330330
var testCases = []struct {
331-
name string
332-
whenPath string
333-
expectStatusCode int
334-
expectResponse string
335-
expectLogContains []string
336-
expectLogNotContains []string
331+
name string
332+
whenPath string
333+
whenForceHandlerTimeout bool
334+
expectStatusCode int
335+
expectResponse string
336+
expectLogContains []string
337+
expectLogNotContains []string
337338
}{
338339
{
339340
name: "404 - write response in global error handler",
@@ -352,10 +353,11 @@ func TestTimeoutWithFullEchoStack(t *testing.T) {
352353
expectLogContains: []string{`"status":418,"error":"",`},
353354
},
354355
{
355-
name: "503 - handler timeouts, write response in timeout middleware",
356-
whenPath: "/?delay=50ms",
357-
expectResponse: "<html><head><title>Timeout</title></head><body><h1>Timeout</h1></body></html>",
358-
expectStatusCode: http.StatusServiceUnavailable,
356+
name: "503 - handler timeouts, write response in timeout middleware",
357+
whenForceHandlerTimeout: true,
358+
whenPath: "/",
359+
expectResponse: "<html><head><title>Timeout</title></head><body><h1>Timeout</h1></body></html>",
360+
expectStatusCode: http.StatusServiceUnavailable,
359361
expectLogNotContains: []string{
360362
"echo:http: superfluous response.WriteHeader call from",
361363
"{", // means that logger was not called.
@@ -371,21 +373,18 @@ func TestTimeoutWithFullEchoStack(t *testing.T) {
371373
e.Logger.SetOutput(buf)
372374

373375
// NOTE: timeout middleware is first as it changes Response.Writer and causes data race for logger middleware if it is not first
374-
// FIXME: I have no idea how to fix this without adding mutexes.
375376
e.Use(TimeoutWithConfig(TimeoutConfig{
376377
Timeout: 15 * time.Millisecond,
377378
}))
378379
e.Use(Logger())
379380
e.Use(Recover())
380381

382+
wg := sync.WaitGroup{}
383+
if tc.whenForceHandlerTimeout {
384+
wg.Add(1) // make `wg.Wait()` block until we release it with `wg.Done()`
385+
}
381386
e.GET("/", func(c echo.Context) error {
382-
var delay time.Duration
383-
if err := echo.QueryParamsBinder(c).Duration("delay", &delay).BindError(); err != nil {
384-
return err
385-
}
386-
if delay > 0 {
387-
time.Sleep(delay)
388-
}
387+
wg.Wait()
389388
return c.JSON(http.StatusTeapot, map[string]string{"message": "OK"})
390389
})
391390

@@ -401,6 +400,9 @@ func TestTimeoutWithFullEchoStack(t *testing.T) {
401400
assert.NoError(t, err)
402401
return
403402
}
403+
if tc.whenForceHandlerTimeout {
404+
wg.Done()
405+
}
404406

405407
assert.Equal(t, tc.expectStatusCode, res.StatusCode)
406408
if body, err := ioutil.ReadAll(res.Body); err == nil {
@@ -411,10 +413,10 @@ func TestTimeoutWithFullEchoStack(t *testing.T) {
411413

412414
logged := buf.String()
413415
for _, subStr := range tc.expectLogContains {
414-
assert.True(t, strings.Contains(logged, subStr))
416+
assert.True(t, strings.Contains(logged, subStr), "expected logs to contain: %v", subStr)
415417
}
416418
for _, subStr := range tc.expectLogNotContains {
417-
assert.False(t, strings.Contains(logged, subStr))
419+
assert.False(t, strings.Contains(logged, subStr), "expected logs not to contain: %v", subStr)
418420
}
419421
})
420422
}

0 commit comments

Comments
 (0)