Skip to main content

Module store

Module store 

Source
Expand description

Tamper-evident trace storage: a background SQLite writer fed by a bounded channel.

The hot request path never blocks on disk: it try_sends a Trace down a bounded channel and returns immediately (dropping the trace if the writer has fallen far enough behind to fill the buffer — bounded memory over a guaranteed write). A single background task owns the SQLite connection, assigns each trace’s prev_hash from the current chain head, computes its hash, and appends it (SPEC §9: the hash chain is only meaningful if every writer agrees on chain order, which a single writer task guarantees for free).

Enums§

StoreError
Errors from the trace store.

Constants§

TRACE_CHANNEL_CAP
Trace buffer depth. Deep enough to absorb normal write bursts; bounded so a wedged writer (disk stall) can’t OOM the process — excess traces are dropped with a warning, not queued forever.

Functions§

append_deferred
Append a deferred verdict for trace_id (a downstream outcome or async gate result). This writes ONLY to the deferred_verdicts table; the sealed trace and its hash are untouched, so the audit chain remains verifiable (SPEC §8.3.4 — the outcome-feedback loop).
load_all_traces
Load every trace from the database in insertion (chain) order — used by tests and operators to verify the hash chain with firstpass_core::verify_chain.
load_deferred
Load the deferred verdicts recorded for trace_id, oldest first. Malformed stored rows are skipped (logged), never fatal — a corrupt late outcome must not break reading the trace.
load_trace_view
Load a single trace by id with its deferred verdicts merged into deferred — the view for display/inspection. This is deliberately separate from load_all_traces: merging deferred verdicts changes the record, so a merged trace must NOT be fed to verify_chain (chain verification always runs on the sealed bodies from load_all_traces).
open
Open (creating if needed) the SQLite trace database, migrate its schema, and spawn the background writer task.
trace_exists
Whether a trace with trace_id exists — used to reject feedback for unknown traces.

Type Aliases§

TraceSender
Sending half of the trace channel; cheap to clone, safe to share across request handlers. Sending is fire-and-forget via try_send — the hot path never awaits the writer, and a bounded buffer means a stalled writer sheds load (drops traces) instead of growing memory without limit.