decision

package
v1.0.0 Latest Latest
Warning

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

Go to latest
Published: Mar 28, 2026 License: Apache-2.0 Imports: 21 Imported by: 0

Documentation

Index

Constants

This section is empty.

Variables

View Source
var (
	ErrNilOrchestratorDependency = errors.New("orchestrator dependency is nil")
	ErrEmptyIdentifier           = errors.New("identifier must not be empty")
	ErrEnvelopeNotFound          = errors.New("envelope not found")
	ErrEnvelopeNotAwaitingReview = errors.New("envelope is not awaiting review")
	ErrEnvelopeAlreadyClosed     = errors.New("envelope is already closed")
	ErrInvalidReviewDecision     = errors.New("decision must be APPROVED or REJECTED")

	// ErrScopedRequestConflict is returned when a duplicate (request_source,
	// request_id) pair is submitted with a different payload hash than the
	// original. This indicates request identity reuse with a mutated body and
	// is always a caller error.
	ErrScopedRequestConflict = errors.New("scoped request conflict: same (request_source, request_id) submitted with a different payload")
)

Functions

This section is empty.

Types

type Clock

type Clock func() time.Time

Clock allows time.Now to be injected for deterministic testing.

type EscalationResolution

type EscalationResolution struct {
	EnvelopeID   string
	Decision     envelope.ReviewDecision
	ReviewerID   string
	ReviewerKind string
	Notes        string
}

EscalationResolution is the input to ResolveEscalation.

type EvaluationRecorder

type EvaluationRecorder interface {
	RecordEvaluationDuration(outcome string, duration time.Duration)
	IncrementEvaluationOutcome(outcome string, reasonCode string)
	IncrementEvaluationFailure(stage string)
}

EvaluationRecorder tracks business outcomes from evaluations. Implementations should be safe for concurrent use.

Duration Semantics: RecordEvaluationDuration measures end-to-end committed evaluation latency as seen by the caller, including domain logic execution and transaction commit overhead. This will be close to but slightly higher than TransactionRecorder.RecordTransactionDuration for the same operation.

Failure Stage Semantics: IncrementEvaluationFailure distinguishes system failures from business rejections. Current stages:

  • "persistence": Repository operation, audit append, or policy infrastructure failure Future stages might include: "validation", "policy_engine", "external_service"

type EvaluationResult

type EvaluationResult struct {
	Outcome     eval.Outcome
	ReasonCode  eval.ReasonCode
	EnvelopeID  string
	State       envelope.EnvelopeState
	Explanation string

	// Policy transparency fields — always populated, never affect evaluation decisions.
	//
	// PolicyMode reflects the active policy evaluator's mode (e.g. "noop").
	// PolicyReference echoes the resolved profile's policy_ref when set.
	// PolicySkipped is true when the profile declares a policy_ref but the active
	// evaluator is noop — meaning the policy step ran but had no real effect.
	PolicyMode      string
	PolicyReference string
	PolicySkipped   bool
}

EvaluationResult is the typed result returned by the orchestrator.

type FailureCategory

type FailureCategory string

FailureCategory represents a typed classification of evaluation failures for observability. These categories enable precise monitoring and alerting without relying on fragile string matching.

const (
	FailureCategoryEnvelopePersistence FailureCategory = "envelope_persistence"
	FailureCategoryAuditAppend         FailureCategory = "audit_append"
	FailureCategoryInvalidTransition   FailureCategory = "invalid_transition"
	FailureCategoryPolicyEvaluation    FailureCategory = "policy_evaluation"
	FailureCategoryAuthorityResolution FailureCategory = "authority_resolution"
	FailureCategoryResolveReview       FailureCategory = "resolve_review"
	FailureCategoryIdempotencyConflict FailureCategory = "idempotency_conflict"
	FailureCategoryUnknown             FailureCategory = "unknown"
)

type NoOpEvaluationRecorder

type NoOpEvaluationRecorder struct{}

NoOpEvaluationRecorder is a no-op implementation used as the default.

func (NoOpEvaluationRecorder) IncrementEvaluationFailure

func (NoOpEvaluationRecorder) IncrementEvaluationFailure(string)

func (NoOpEvaluationRecorder) IncrementEvaluationOutcome

func (NoOpEvaluationRecorder) IncrementEvaluationOutcome(string, string)

func (NoOpEvaluationRecorder) RecordEvaluationDuration

func (NoOpEvaluationRecorder) RecordEvaluationDuration(string, time.Duration)

type Orchestrator

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

Orchestrator coordinates the MIDAS evaluation flow.

func NewOrchestrator

func NewOrchestrator(
	store RepositoryStore,
	policies policy.PolicyEvaluator,
	metrics EvaluationRecorder,
) (*Orchestrator, error)

NewOrchestrator constructs an Orchestrator with a real clock.

func NewOrchestratorWithClock

func NewOrchestratorWithClock(
	store RepositoryStore,
	policies policy.PolicyEvaluator,
	metrics EvaluationRecorder,
	clock Clock,
) (*Orchestrator, error)

NewOrchestratorWithClock constructs an Orchestrator with an injected clock.

func (*Orchestrator) Evaluate

Evaluate executes the full MIDAS authority evaluation flow inside a database transaction. All repository and audit operations commit together or roll back together.

func (*Orchestrator) GetEnvelopeByID

func (o *Orchestrator) GetEnvelopeByID(ctx context.Context, id string) (*envelope.Envelope, error)

func (*Orchestrator) GetEnvelopeByRequestID

func (o *Orchestrator) GetEnvelopeByRequestID(ctx context.Context, requestID string) (*envelope.Envelope, error)

func (*Orchestrator) GetEnvelopeByRequestScope

func (o *Orchestrator) GetEnvelopeByRequestScope(ctx context.Context, requestSource, requestID string) (*envelope.Envelope, error)

GetEnvelopeByRequestScope retrieves an envelope by (request_source, request_id) composite key. This is the preferred lookup for scoped idempotency checks.

func (*Orchestrator) ListEnvelopes

func (o *Orchestrator) ListEnvelopes(ctx context.Context) ([]*envelope.Envelope, error)

func (*Orchestrator) ListEnvelopesByState

func (o *Orchestrator) ListEnvelopesByState(ctx context.Context, state envelope.EnvelopeState) ([]*envelope.Envelope, error)

ListEnvelopesByState returns all envelopes in the given lifecycle state. An empty state returns all envelopes.

func (*Orchestrator) ResolveEscalation

func (o *Orchestrator) ResolveEscalation(ctx context.Context, res EscalationResolution) (*envelope.Envelope, error)

ResolveEscalation records a reviewer's decision on an escalated envelope and closes it. The envelope must be in AWAITING_REVIEW state.

Event sequence:

AuditEventEscalationReviewed — semantic record of the review decision
AuditEventEnvelopeClosed     — uniform close event (same as non-escalated path)

The two-event sequence means:

  • "all closed envelopes" queries on AuditEventEnvelopeClosed work uniformly,
  • "all reviewed escalations" queries on AuditEventEscalationReviewed work independently.

func (*Orchestrator) Simulate

Simulate runs the full authority evaluation flow without persisting any state. It performs the same resolution and threshold checks as Evaluate but does not create an envelope, write audit events, or queue outbox messages.

Use this for hypothetical "what-if" evaluation in the Explorer sandbox. The returned EvaluationResult has an empty EnvelopeID; all other fields are populated identically to a live evaluation.

type RepositoryStore

type RepositoryStore interface {
	Repositories() (*store.Repositories, error)
	WithTx(ctx context.Context, operation string, fn func(*store.Repositories) error) error
}

RepositoryStore abstracts transactional repository access.

Jump to

Keyboard shortcuts

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