middleware

package
v0.3.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Apr 17, 2026 License: MIT Imports: 12 Imported by: 0

Documentation

Index

Constants

View Source
const DefaultMaxBodyBytes int64 = 1 << 20

DefaultMaxBodyBytes caps request bodies at 1 MiB by default.

Variables

This section is empty.

Functions

func Auth

func Auth(resolver KeyResolver) func(http.Handler) http.Handler

Auth enforces bearer-token authentication using the given resolver. On success, attaches the resolved workspace ID to the request context. Skips /healthz so probes always succeed regardless of auth state.

func Chain

func Chain(mws ...func(http.Handler) http.Handler) func(http.Handler) http.Handler

Chain composes middleware left-to-right so the leftmost wraps outermost: Chain(A, B, C)(h) runs A(B(C(h))).

func Logging

func Logging(logger *slog.Logger) func(http.Handler) http.Handler

Logging emits one structured log line per request with method, path, status, duration, and request ID. Skips /healthz to avoid probe spam.

func MaxBody

func MaxBody(maxBytes int64) func(http.Handler) http.Handler

MaxBody caps the request body at maxBytes. Writes past the cap fail with http.ErrBodyReadAfterClose. 0 disables the cap.

func Recovery

func Recovery(logger *slog.Logger) func(http.Handler) http.Handler

Recovery catches panics from downstream handlers, logs the panic + stack trace via slog, and returns a 500 with a structured error envelope. Placed outermost so it catches panics in other middleware.

func RequestID

func RequestID(next http.Handler) http.Handler

RequestID honors an inbound X-Request-Id header or mints a new UUID. The value is stamped on the response header and stored in the request context for downstream access via reqctx.GetRequestID(ctx).

func Scope

func Scope() func(http.Handler) http.Handler

Scope reads optional X-Brainjar-Project and X-Brainjar-Session headers, validates them as slugs, and attaches them to the context. Empty headers are fine — handlers that need them enforce presence.

func Workspace

func Workspace() func(http.Handler) http.Handler

Workspace validates the optional X-Brainjar-Workspace header. When present, it must match the workspace attached by Auth — an agent trying to act against a workspace it wasn't authenticated for is a 403, not a 401 (the credential is valid; the scope is wrong).

Types

type DevKeyResolver

type DevKeyResolver struct {
	Key         string
	WorkspaceID models.WorkspaceID
}

DevKeyResolver accepts a single hardcoded API key and resolves it to a fixed workspace. Meant for local dev and integration tests only; real auth lands in M6 via ApiKeyApp.

func DevKeyResolverFromEnv

func DevKeyResolverFromEnv(defaultWorkspace models.WorkspaceID) *DevKeyResolver

DevKeyResolverFromEnv builds a DevKeyResolver from the environment. BRAINJAR_DEV_API_KEY holds the plaintext key; defaultWorkspace is the workspace the key resolves to. Returns a resolver that always fails when the env var is unset.

func (*DevKeyResolver) Resolve

func (r *DevKeyResolver) Resolve(_ context.Context, plaintext string) (models.WorkspaceID, error)

Resolve implements KeyResolver. Returns Unauthorized for any key other than r.Key, or when r.Key is empty (no dev key configured).

type KeyResolver

type KeyResolver interface {
	Resolve(ctx context.Context, plaintext string) (models.WorkspaceID, error)
}

KeyResolver resolves a plaintext API key to its workspace. M6 plugs in ApiKeyApp.Resolve; until then, DevKeyResolver covers integration testing.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL