audit

package
v1.0.0-alpha.21 Latest Latest
Warning

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

Go to latest
Published: Sep 3, 2026 License: AGPL-3.0 Imports: 17 Imported by: 0

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func BindPublicRequest

func BindPublicRequest(ctx context.Context, projectID, flowID, sessionID string)

BindPublicRequest stamps project/flow/session onto the actor slot so Path A can emit request.api without a token (hosted login/flow). No-op when projectID is empty or there is no slot. Does not set Authenticated.

func Emit

func Emit(ctx context.Context, stmts EventInserter, spec EmitSpec) error

Emit builds and inserts a Path B event. Empty ProjectID skips the insert (no actor/project scope yet).

func FromContext

func FromContext(ctx context.Context, eventType domain.EventType, category domain.EventCategory) *domain.Event

FromContext builds a domain.Event skeleton from ActorContext when present.

func Insert

func Insert(ctx context.Context, stmts EventInserter, ev *domain.Event) error

Insert persists a Path B event via stmts.InsertEvent. When ProjectID is empty the insert is skipped (optional / no actor scope yet).

func UserAttributeAuditFields

func UserAttributeAuditFields(user map[string]any, schemaJSON []byte) (keys []string, attributes map[string]any)

UserAttributeAuditFields builds attribute_keys and x-audit attribute values for user.created / user.updated payloads. Keys come from the written attributes. Values are included only when the matching top-level schema property has x-audit set (true or a non-empty string). When schemaJSON is empty or unparsable, keys are still returned and attributes is empty.

func WithActorContext

func WithActorContext(ctx context.Context, ac ActorContext) context.Context

WithActorContext stores ActorContext on ctx and updates any actor slot.

func WithActorSlot

func WithActorSlot(ctx context.Context) context.Context

WithActorSlot plants a mutable actor slot on ctx so net/http middleware can observe AuthGate enrichment that happens inside ogen on a child context.

func WithEntity

func WithEntity(ev *domain.Event, entityType, entityID string) *domain.Event

func WithPayload

func WithPayload(ev *domain.Event, payload any) (*domain.Event, error)

func WithProjectID

func WithProjectID(ev *domain.Event, projectID string) *domain.Event

WithProjectID sets ProjectID when the actor context did not supply one.

func WithRequestEventMiddleware

func WithRequestEventMiddleware(buf *RequestBuffer, next http.Handler) http.Handler

WithRequestEventMiddleware enqueues Path A request.api events after the handler when project_id is known (authenticated API, public login/flow, or POST /projects after the new id is stamped). Probes (healthz) leave project_id empty and are skipped.

Types

type ActorContext

type ActorContext struct {
	ProjectID      string
	TeamID         *string
	ActorID        *string
	ActorType      *domain.EventActorType
	ClientID       string
	TokenID        string
	DelegationType string
	DelegationID   string
	Grantor        string
	Fingerprint    string
	SessionID      *string
	FlowID         *string
	RequestID      *string
	Authenticated  bool
}

ActorContext holds server-authoritative WHO/HOW dimensions for event emission (ADR 048 §5).

func ActorFromContext

func ActorFromContext(ctx context.Context) (ActorContext, bool)

func ActorSlotFromContext

func ActorSlotFromContext(ctx context.Context) (*ActorContext, bool)

type BatchInserter

type BatchInserter func(ctx context.Context, events []*domain.Event) error

BatchInserter adapts a batch insert func to EventBatchInserter.

func (BatchInserter) InsertEvents

func (f BatchInserter) InsertEvents(ctx context.Context, events []*domain.Event) error

type EmitSpec

type EmitSpec struct {
	Type       domain.EventType
	Category   domain.EventCategory
	ProjectID  string
	EntityType string
	EntityID   string
	Payload    any
	SessionID  *string
	TokenID    string
	// Optional actor overrides when the request ActorContext is empty
	// (anonymous session mint, token issue before AuthGate, etc.).
	ActorID   *string
	ActorType *domain.EventActorType
}

EmitSpec is one Path B wide-event emission (ADR 048).

type EventBatchInserter

type EventBatchInserter interface {
	InsertEvents(ctx context.Context, events []*domain.Event) error
}

EventBatchInserter persists a Path A flush batch in one call (preferably one TX).

type EventExportSource

type EventExportSource interface {
	ListClaimedProjectIDs(ctx context.Context) ([]string, error)
	EnsureSink(ctx context.Context, sink *domain.EventSink) error
	GetEventSinkCursor(ctx context.Context, sinkID, projectID string) (*domain.EventSinkCursor, error)
	UpsertEventSinkCursor(ctx context.Context, cursor *domain.EventSinkCursor) error
	ListEventsAfterCursor(ctx context.Context, projectID string, afterCreatedAt time.Time, afterID string, limit int) ([]*domain.Event, error)
}

EventExportSource backs the shipper with claimed projects and sink cursors.

type EventInserter

type EventInserter interface {
	InsertEvent(ctx context.Context, event *domain.Event) error
}

EventInserter persists a single event (Path B TX site or Path A batch item).

type EventPurger

type EventPurger interface {
	DeleteEventsOlderThan(ctx context.Context, createdBefore time.Time) (int64, error)
}

EventPurger deletes old events across all projects (including orphaned project_id values after hard-delete).

type ExportConfig

type ExportConfig struct {
	Enabled  bool          `mapstructure:"enabled"`
	Interval time.Duration `mapstructure:"interval"`
	Sinks    []SinkConfig  `mapstructure:"sinks"`
}

ExportConfig holds deployment-scoped sinks and shipper tuning.

func DefaultExportConfig

func DefaultExportConfig() ExportConfig

type RequestBuffer

type RequestBuffer struct {
	// contains filtered or unexported fields
}

RequestBuffer is an in-process Path A queue. Flush when the buffer holds at least BatchSize events (a prefix of that many) or the oldest event exceeds MaxAge. A single background flusher owns all inserts.

func NewRequestBuffer

func NewRequestBuffer(insert EventBatchInserter, cfg RequestBufferConfig) *RequestBuffer

NewRequestBuffer starts a background flusher. Call Close on shutdown.

func (*RequestBuffer) Close

func (b *RequestBuffer) Close()

Close drains the buffer and stops the flusher.

func (*RequestBuffer) Dropped

func (b *RequestBuffer) Dropped() uint64

func (*RequestBuffer) Enqueue

func (b *RequestBuffer) Enqueue(ev *domain.Event)

Enqueue adds a request event. Drops when full (never blocks). occurred_at is enqueue time (tests / callers without a request start).

func (*RequestBuffer) EnqueueSince

func (b *RequestBuffer) EnqueueSince(ev *domain.Event, startedAt time.Time)

EnqueueSince records a request event whose forensic occurred_at is startedAt (HTTP middleware entry), not enqueue/flush time.

func (*RequestBuffer) Flushed

func (b *RequestBuffer) Flushed() uint64

func (*RequestBuffer) Len

func (b *RequestBuffer) Len() int

type RequestBufferConfig

type RequestBufferConfig struct {
	BatchSize       int
	MaxAge          time.Duration
	Capacity        int
	ShutdownTimeout time.Duration
}

RequestBufferConfig tunes Path A batching (ADR 048).

func DefaultRequestBufferConfig

func DefaultRequestBufferConfig() RequestBufferConfig

type RetentionConfig

type RetentionConfig struct {
	Retention time.Duration `mapstructure:"window"`
	Interval  time.Duration `mapstructure:"interval"`
	Enabled   bool          `mapstructure:"enabled"`
}

RetentionConfig controls time-only event purge (ADR 049).

func DefaultRetentionConfig

func DefaultRetentionConfig() RetentionConfig

type RetentionJob

type RetentionJob struct {
	// contains filtered or unexported fields
}

RetentionJob periodically deletes events older than the retention window.

func NewRetentionJob

func NewRetentionJob(purge EventPurger, cfg RetentionConfig) *RetentionJob

func (*RetentionJob) Close

func (j *RetentionJob) Close()

func (*RetentionJob) Start

func (j *RetentionJob) Start()

type SequentialBatchInserter

type SequentialBatchInserter struct {
	Inner EventInserter
}

SequentialBatchInserter inserts each event via EventInserter (tests / fallback).

func (SequentialBatchInserter) InsertEvents

func (s SequentialBatchInserter) InsertEvents(ctx context.Context, events []*domain.Event) error

type Shipper

type Shipper struct {
	// contains filtered or unexported fields
}

Shipper delivers events to deployment-configured sinks (ADR 049).

func NewShipper

func NewShipper(src EventExportSource, cfg ExportConfig) *Shipper

func (*Shipper) Close

func (s *Shipper) Close()

func (*Shipper) Start

func (s *Shipper) Start(ctx context.Context) error

type SinkConfig

type SinkConfig struct {
	Type domain.EventSinkType `mapstructure:"type"`
	URL  string               `mapstructure:"url"`
	// Enabled is opt-out: a configured sink (non-empty type) ships unless this
	// is explicitly false.
	Enabled *bool `mapstructure:"enabled"`
}

SinkConfig is a deployment-configured event sink (no project CRUD in v1).

Jump to

Keyboard shortcuts

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