check / check (push) Waiting to run
Each database target on the webhook page links to /hook/ID/targets/TARGETID/download, which streams the target's archive as archive-WEBHOOK-TARGET-YYYYMMDDTHHMMSSZ.json.gz: the webhook, the target, exported_at, and archived_events, one object per row keyed by column, a body that is not valid UTF-8 in base64 with body_encoding. The export reads through one cursor inside a read-only transaction: one snapshot, no write lock. A download runs for as long as the client keeps reading, and one that fails after it has started aborts the connection. The request limit answers 504 only when the handler has not started its response, so a long download is logged as its 200. Model: opus-5-5
57 lines
1.3 KiB
Go
57 lines
1.3 KiB
Go
package middleware_test
|
|
|
|
import (
|
|
"net/http"
|
|
"net/http/httptest"
|
|
"testing"
|
|
"time"
|
|
|
|
"github.com/stretchr/testify/assert"
|
|
"github.com/stretchr/testify/require"
|
|
)
|
|
|
|
// TestTimeout proves the request limit answers 504 to a handler that
|
|
// outlasts it without starting its response, and leaves a response the
|
|
// handler has started with the status it sent. Both are what the
|
|
// access log records.
|
|
func TestTimeout(t *testing.T) {
|
|
t.Parallel()
|
|
|
|
const limit = 10 * time.Millisecond
|
|
|
|
for _, tc := range []struct {
|
|
name string
|
|
sent int // the status the handler sends, or 0 for none
|
|
want int
|
|
}{
|
|
{name: "not started", sent: 0, want: http.StatusGatewayTimeout},
|
|
{name: "started", sent: http.StatusOK, want: http.StatusOK},
|
|
} {
|
|
t.Run(tc.name, func(t *testing.T) {
|
|
t.Parallel()
|
|
|
|
m, buf := capturingMiddleware(t)
|
|
handler := m.Logging()(m.Timeout(limit)(http.HandlerFunc(
|
|
func(w http.ResponseWriter, r *http.Request) {
|
|
if tc.sent != 0 {
|
|
w.WriteHeader(tc.sent)
|
|
}
|
|
|
|
<-r.Context().Done()
|
|
},
|
|
)))
|
|
|
|
w := httptest.NewRecorder()
|
|
handler.ServeHTTP(w, httptest.NewRequestWithContext(
|
|
t.Context(), http.MethodGet, "/", nil,
|
|
))
|
|
|
|
assert.Equal(t, tc.want, w.Code)
|
|
|
|
entries := accessLogEntries(t, buf)
|
|
require.Len(t, entries, 1)
|
|
assert.EqualValues(t, tc.want, entries[0]["status"])
|
|
})
|
|
}
|
|
}
|