// Package httpapi provides the HTTP-facing layer for the multi-tenant // backend: auth middleware, tenant context propagation, and route // wiring for the auth and note endpoints. package httpapi import ( "context" "errors" ) // Tenant carries the per-request tenant identity extracted from a // validated JWT. It is the only thing handlers need to know about // "who is this request for". type Tenant struct { UserID string Email string } type ctxKey struct{} // ErrNoTenant indicates that handler code expected a tenant on the // request context but found none. This is always a programming error // (the route was reached without going through AuthMiddleware). var ErrNoTenant = errors.New("httpapi: no tenant in context") // WithTenant returns a derived context carrying t. func WithTenant(ctx context.Context, t Tenant) context.Context { return context.WithValue(ctx, ctxKey{}, t) } // TenantFrom retrieves the tenant from ctx. Panics are avoided by // returning ErrNoTenant when the value is missing. func TenantFrom(ctx context.Context) (Tenant, error) { v, ok := ctx.Value(ctxKey{}).(Tenant) if !ok { return Tenant{}, ErrNoTenant } return v, nil }