Supersedes 0047. Closes gap C43 (audit part).
Context
0047 (Proposed) routed audit through events without a tamper-evidence rule or a retention rule. The owner’s audit answers AU1 to AU8 and SC8 (mem L644–653, L552, 2026-10-20) fix them.Decision
- What is audited (AU1). Every action, every data change (a redacted diff through
@Auditable), security events, and sensitive reads. - Envelope (AU2). A rich envelope on each record.
- Tamper evidence (AU3). Storage is append-only. Each tenant has a hash chain. A KMS-signed checkpoint is written daily. S3 Object Lock holds the records.
stackra audit:verifychecks the chain. - Same transaction (AU4). Evidence goes to the outbox in the same transaction as the change. Operator, break-glass and impersonation paths fail closed.
- Reads.
@AccessLoggedwrites application-level access logs. pgaudit records direct database sessions in production. There is no CDC (change-data-capture) tool. - Retention (AU5 and SC8). Thirteen months hot, in partitioned Postgres. Cold storage is S3 Parquet. Money events are kept seven years.
- Tenant access (AU6). A tenant can view and export its own audit log. A SIEM stream is a Pro entitlement tier.
Consequences
- An audit gap is detectable, because a broken chain fails verification.
- Audit is written with the change, so a change without its audit record cannot commit.
Enforcement
planned —stackra audit:verify in CI against a sample tenant; the outbox test covers the same-transaction rule.
Open questions
- Volume budget and batching window for read audits, and whether a failed read audit blocks the read (register D-11). The owner decides.
Supersedes and sources
Supersedes: 0047. Sources: owner audit answers AU1–AU8 (stackra-decisions-2026-10-19.md L644–653, 2026-10-20); SC8 (L552). Closes gap C43 (audit part).