- cloud/attempt_ledger.py: separate task_attempts table (not tasks
columns) with per-attempt rows, MAX+1 attempt_no, append-only
intent; interrupted rows kept but never counted; is_defect is
explicit, never inferred from failure; first defect category
wins; no-ledger tasks stay unknown (None), never backfilled.
SQLite DDL is CREATE TABLE IF NOT EXISTS (idempotent); PG_DDL
is the verbatim manual step for production Postgres, kept out
of POSTGRES_SCHEMA on purpose (migrations coverage untouched).
- cloud/server.py GET /metrics-report: aggregates the ledger
into compute_metrics records; missing ledger table degrades to
unknown rates, not an error. Cost dual-column code untouched.
- cloud/metrics.py: docstring only (ledger is now the source);
compute_metrics logic and all #238 semantics unchanged.
- Tests: 16 ledger tests (store/aggregate/metrics/PG adapter
evidence) + 3 endpoint tests (real rates, old task beside
ledger task, interrupted status non-terminal).
- cloud/arch_conformance.py: contract-version (+1 only, approved
change record), forbidden-directory (own dir only, .. and symlink
escapes resolved), forbidden-import layer bans audited against the
baseline (foundation/execution/driver, server sqlite3 Row adapters
deliberately allowed), G2 frozen-stack swap guard; skill-project
one-call check.
- cloud/metrics.py: first-pass/defect/rework rates over terminal
tasks, unknown rates as None (never 0), #212 dual-column per-task
cost (total None when incomplete), pure feedback rules
(tighten/route-with-extra-audit/recalibrate, auto_apply False),
golden-set gate: unapproved sample set is never decision-ready.
- GET /metrics-report (authenticated, member-scoped, same as
/metrics): attempts/defects are None until an attempt ledger
exists, so rates stay unknown rather than fabricated.
- Tests: 29 arch + 15 metrics + 3 endpoint, each check with
positive and negative cases; repo-level scan pins zero layer
violations on the baseline so a future violation fails CI via the
existing host-verify discover run (no workflow change).