Documentation
¶
Index ¶
- Variables
- func DefaultTenantIDPattern() *regexp.Regexp
- func FanOutRetentionCleanup(ctx context.Context, log logger.Logger, tenants []string, ...) error
- func GetTenant(ctx context.Context) (string, bool)
- func SetTenant(ctx context.Context, tenantID string) context.Context
- func TenantID(ctx context.Context) (string, error)
- func ValidateTenantID(id string) error
- type CompositeResolver
- type HeaderResolver
- type PathResolver
- type RetentionDelete
- type SubdomainResolver
- type TenantResolver
- type ValidatingResolver
Constants ¶
This section is empty.
Variables ¶
var ErrInvalidTenantID = errors.New("multitenant: tenant id does not match the default grammar")
ErrInvalidTenantID reports a tenant identifier that does not match DefaultTenantIDPattern.
var ErrNoTenant = errors.New("multitenant: no tenant in context")
ErrNoTenant reports a context that carries no tenant. It is the error form of GetTenant's ok result, so every lane answers "no tenant" the same way.
var ErrTenantResolutionFailed = errors.New("tenant resolution failed")
ErrTenantResolutionFailed is returned when a resolver cannot determine the tenant identifier.
Functions ¶
func DefaultTenantIDPattern ¶ added in v0.61.0
DefaultTenantIDPattern returns the framework's tenant identifier grammar.
func FanOutRetentionCleanup ¶ added in v0.42.0
func FanOutRetentionCleanup( ctx context.Context, log logger.Logger, tenants []string, getDB func(context.Context) (dbtypes.Interface, error), retention time.Duration, name string, del RetentionDelete, ) error
FanOutRetentionCleanup runs a retention delete once per tenant, resolving each tenant's database via getDB with that tenant injected into the context (SetTenant). Per-tenant errors AND panics are collected with errors.Join so one unhealthy tenant cannot block the others. Single-tenant callers pass tenants=[""] (SetTenant("") is a no-op). name labels the job in log and error messages (e.g. "outbox", "inbox").
This is shared by the outbox and inbox cleanup jobs, whose Execute bodies are otherwise identical — only the store delete and the label differ.
func TenantID ¶ added in v0.61.0
TenantID is GetTenant in error form: the tenant identifier, or ErrNoTenant.
func ValidateTenantID ¶ added in v0.61.0
ValidateTenantID checks an identifier against DefaultTenantIDPattern.
SECURITY: the identifier is caller-written (an HTTP header, a message stamp), so the error carries its byte length only — never the value itself.
Types ¶
type CompositeResolver ¶
type CompositeResolver struct {
Resolvers []TenantResolver
TenantRegex *regexp.Regexp // Optional validation pattern
}
CompositeResolver tries multiple resolvers until one succeeds.
func (*CompositeResolver) ResolveTenant ¶
ResolveTenant implements TenantResolver.
type HeaderResolver ¶
type HeaderResolver struct {
HeaderName string
}
HeaderResolver extracts the tenant identifier from a configured request header.
func (*HeaderResolver) ResolveTenant ¶
ResolveTenant implements TenantResolver.
type PathResolver ¶ added in v0.34.0
PathResolver extracts the tenant identifier from a path segment.
Segment is 1-indexed (segment 1 is the first non-empty path part after the leading slash). When Prefix is non-empty, the resolver only attempts extraction for requests whose path equals Prefix exactly or starts with "Prefix/" — non-matching paths return ErrTenantResolutionFailed so the composite chain (if any) can fall through to other resolvers.
func (*PathResolver) ResolveTenant ¶ added in v0.34.0
ResolveTenant implements TenantResolver.
type RetentionDelete ¶ added in v0.42.0
type RetentionDelete func(ctx context.Context, db dbtypes.Interface, cutoff time.Time) (int64, error)
RetentionDelete removes rows older than cutoff from the resolved tenant database. It is the per-vendor delete a retention-cleanup job runs (e.g. the outbox's DeletePublished or the inbox's DeleteProcessed) and matches those store methods' signatures directly.
type SubdomainResolver ¶
SubdomainResolver extracts the tenant identifier from the request host.
func (*SubdomainResolver) ResolveTenant ¶
ResolveTenant implements TenantResolver.
type TenantResolver ¶
type TenantResolver interface {
ResolveTenant(ctx context.Context, req *http.Request) (string, error)
}
TenantResolver resolves the tenant identifier from an incoming request.
type ValidatingResolver ¶
type ValidatingResolver struct {
Resolver TenantResolver
TenantRegex *regexp.Regexp
}
ValidatingResolver wraps any resolver with tenant ID validation.
func (*ValidatingResolver) ResolveTenant ¶
ResolveTenant implements TenantResolver with validation.