ops-warden/wiki/AuditTrail.md
tegwick ec625873fb
All checks were successful
CI Smoke / host-smoke (push) Successful in 0s
CI Smoke / container-smoke (push) Successful in 1s
Review layer model v0.4; correct an unsound audit claim it exposes
Assessment in history/2026-08-29-layer-model-v04-review.md. No objection to the
ruling; both ops-warden amendments were adopted (5.2 conduit, 5.3 declared gap).
Three findings, one against us.

The one against us is real. 9.6 requires emission atomic with the state change
for load-bearing evidence. ops-warden ca.py carries `pass  # audit must not block
signing` and AuditTrail.md advertises that the trail never blocks the primary
action, so a failed append loses the event while the cert still issues -- a
suppressed event leaving the chain intact, which is exactly what 9.6 describes.

Whether to make it atomic is gate-house doctrine, not ops-wardens call: it would
give the estates operational access lane a new dependency on its own evidence
store. But one half of the fix is ours regardless -- the trail must not be read
as complete. AuditTrail.md now says absence of a record is not evidence of
absence, which it did not.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01YWBMovyFoy9RRrfL7zKvPJ

Assistant: claude-code
Assistant-Model: opus
Assistant-Process: 4014535@bnt-lap001
Assistant-Session: d0036016-73e8-4da1-8e47-563e3ab39a3c
2026-08-29 02:46:50 +02:00

3 KiB

Audit Trail — Unified ops-warden Activity

Date: 2026-07-01
Workplan: WARDEN-WP-0022

ops-warden records metadata only for every action it performs. No token, key, cert body, or other secret value ever lands in the audit log.


What is recorded

Kind Source actions Typical fields
sign warden sign, warden issue, cert_command actor, backend, TTL, policy_decision_id
access warden access --fetch / --exec need id, owner repo, subject, decision id, outcome
worker warden worker tick, approve, full-auto execute triage counts, draft id, outcome
hub State Hub progress notes (--hub) summary, author, event type

Storage

  • Primary: {state_dir}/audit.jsonl — append-only JSONL (default ~/.local/state/warden/audit.jsonl)
  • Legacy (merged for back-compat): signatures.log, access-audit.log

Rotation: when audit.jsonl exceeds 5 MiB it is renamed to audit.jsonl.1 and a fresh file starts.

Secret-material guard

record_event() rejects fields that look like secret values (known token prefixes, high-entropy runs). Signing and proxy paths swallow audit failures so gatekeeping never blocks the primary action — but tests prove values cannot be written.

Absence of a record is not evidence of absence. Because emission never blocks the primary action (src/warden/ca.py), a failed append loses the event while the action still happens. This trail proves that the records it holds were not altered or truncated; it does not prove that every action produced one. Do not reason from a missing entry. This is the estate-wide bound in security-layer-model_v0.4 §9.6 — completeness is the source's obligation, and whether ops-warden must make signing emission atomic is an open question with gate-house (history/2026-08-29-layer-model-v04-review.md, Finding 3).


Query

# Human table — last 7 days
warden activity

# Filter and JSON for agents
warden activity --days 3 --kind sign --json
warden activity --days 7 --hub --json
Flag Purpose
--days N Look back N days (default 7)
--kind sign|access|worker|hub Filter by event kind
--json Stable JSON array for automation
--hub Include recent State Hub progress notes mentioning ops-warden

Linger and login independence

The coordination worker can run under a systemd --user timer with linger enabled (WARDEN-WP-0021). Audit events from worker ticks appear with kind: worker.

Full logged-out operational value still depends on State Hub and tunnels being reachable without an interactive login (State Hub on railiance01, cust-wp-0011). The audit trail is local-first; --hub adds narrative context when the hub is up.


See also

  • wiki/OperatorAccessAssist.md — metadata-only principle for access proxy
  • wiki/PolicyGatedSigning.mdpolicy_decision_id on sign events
  • wiki/playbooks/scheduled-worker.md — worker timer and review loop