Deploy main eacf1e7 to prod
check / check (push) Waiting to run

Replaces #559, which conflicted.

Model: opus-5-5
This commit is contained in:
2026-10-25 01:55:36 +00:00
parent 1647b43aa6
commit 537374e4cc
311 changed files with 35614 additions and 14120 deletions
+80 -39
View File
@@ -1,10 +1,14 @@
package handlers
import (
"context"
"html/template"
"log/slog"
"net/http"
"net/http/httptest"
"time"
"gorm.io/gorm"
"sneak.berlin/go/webhooker/internal/database"
)
@@ -15,10 +19,16 @@ func (s *Handlers) SetLogForTest(log *slog.Logger) {
s.log = log
}
// MaxRenderedBodyBytesForTest exposes the event log's body cap
// to the handlers_test package.
// MaxRenderedBodyBytesForTest exposes the body cap of the lists
// of events to the handlers_test package.
const MaxRenderedBodyBytesForTest = maxRenderedBodyBytes
// NewBodyViewForTest exposes newBodyView for use in the
// handlers_test package.
func NewBodyViewForTest(body []byte, size int64) BodyView {
return newBodyView("/hook/w/events/e", body, size)
}
// MaxRenderedResponseBytesForTest exposes the event log's
// delivery response cap to the handlers_test package.
const MaxRenderedResponseBytesForTest = maxRenderedResponseBytes
@@ -27,16 +37,19 @@ const MaxRenderedResponseBytesForTest = maxRenderedResponseBytes
// per-delivery attempt ceiling to the handlers_test package.
const MaxRenderedAttemptsForTest = maxRenderedAttempts
// MaxTargetRetriesForTest exposes the target max_retries ceiling to
// MaxTargetAttemptsForTest exposes the target max_attempts ceiling to
// the handlers_test package, so the tests assert against the constant
// the handlers enforce rather than a number copied beside it.
const MaxTargetRetriesForTest = maxTargetRetries
const MaxTargetAttemptsForTest = maxTargetAttempts
// PageOrFirstForTest exposes pageOrFirst for use in the handlers_test
// package.
func PageOrFirstForTest(s string) int {
return pageOrFirst(s)
}
// EventDBLeftMsgForTest and SidecarLeftMsgForTest expose the two
// messages the webhook delete handler logs when a file of the event
// database is left on disk, so a test checking that one is absent
// checks for the handler's own wording.
const (
EventDBLeftMsgForTest = eventDBLeftMsg
SidecarLeftMsgForTest = sidecarLeftMsg
)
// DummyVerificationsForTest reports how many equivalent-cost
// verifications were charged for usernames that do not exist. It
@@ -60,15 +73,45 @@ func TrimPartialRuneForTest(b []byte) []byte {
func (s *Handlers) LoadEventLogViewsForTest(
w http.ResponseWriter,
webhook database.Webhook,
page int,
) []EventLogView {
views, _, _ := s.loadEventsWithDeliveries(
w, webhook, nil, page,
w, newRequestForTest(), webhook, nil, nil,
)
return views
}
// WebhookStatsForTest returns the figures the statistics pane on a
// webhook's page shows, from the webhook's entrypoints and targets
// loaded as that page loads them.
func (s *Handlers) WebhookStatsForTest(webhookID string) *WebhookStats {
var entrypoints []database.Entrypoint
s.db.DB().Where("webhook_id = ?", webhookID).Find(&entrypoints)
var targets []database.Target
s.db.DB().Where("webhook_id = ?", webhookID).Find(&targets)
return s.loadWebhookStats(webhookID, entrypoints, targets)
}
// FinishedByTargetForTest exposes finishedByTarget for use in the
// handlers_test package.
func FinishedByTargetForTest(
webhookDB *gorm.DB, since time.Time,
) ([]TargetFinished, error) {
return finishedByTarget(webhookDB, since)
}
// newRequestForTest is the request the helpers here pass on for
// callers that have none: it is used only to render the error page.
func newRequestForTest() *http.Request {
return httptest.NewRequestWithContext(
context.Background(), http.MethodGet, "/", nil,
)
}
// AddTemplateForTest registers a template under a page name so that
// the handlers_test package can drive the render path with a
// template of its own.
@@ -90,37 +133,35 @@ func (s *Handlers) RenderTemplateForTest(
s.renderTemplate(w, r, pageTemplate, data)
}
// BuildSlackTargetConfigForTest exposes
// buildSlackTargetConfig for use in the handlers_test package.
func (s *Handlers) BuildSlackTargetConfigForTest(
w http.ResponseWriter,
r *http.Request,
// SetSlackTargetSettingsForTest exposes setSlackTargetSettings for use
// in the handlers_test package.
func (s *Handlers) SetSlackTargetSettingsForTest(
ctx context.Context,
target *database.Target,
targetURL string,
) (string, error) {
return s.buildSlackTargetConfig(w, r, targetURL)
) string {
return s.setSlackTargetSettings(ctx, target, targetURL)
}
// BuildHTTPTargetConfigForTest exposes buildHTTPTargetConfig
// for use in the handlers_test package, taking the form fields
// an HTTP target's configuration is built from.
func (s *Handlers) BuildHTTPTargetConfigForTest(
w http.ResponseWriter,
r *http.Request,
targetURL, headers, timeout string,
) (string, error) {
return s.buildHTTPTargetConfig(w, r, targetFormInput{
URL: targetURL,
Headers: headers,
Timeout: timeout,
})
// SetDatabaseTargetSettingsForTest exposes setDatabaseTargetSettings
// for use in the handlers_test package.
func SetDatabaseTargetSettingsForTest(
target *database.Target,
expiry, rotation string,
) string {
return setDatabaseTargetSettings(target, expiry, rotation)
}
// BuildDatabaseTargetConfigForTest exposes
// buildDatabaseTargetConfig for use in the handlers_test
// package.
func (s *Handlers) BuildDatabaseTargetConfigForTest(
w http.ResponseWriter,
expiry string,
) (string, error) {
return s.buildDatabaseTargetConfig(w, expiry)
// FormatArchiveExpiryForTest exposes formatArchiveExpiry.
func FormatArchiveExpiryForTest(expiry time.Duration) string {
return formatArchiveExpiry(expiry)
}
// ArchiveFileViewForTest exposes archiveFileView, which describes a
// database target's archive files as the target list shows them at
// now.
func (s *Handlers) ArchiveFileViewForTest(
webhook *database.Webhook, target *database.Target, now time.Time,
) *ArchiveFileView {
return s.archiveFileView(webhook, target, now)
}