Skip to content

feat: artifact update & audit — advisory revise + staleness/audit layer - #44

Merged
MCKRUZ merged 2 commits into
MCKRUZ:masterfrom
splashthree:artifact-updating
Aug 6, 2026
Merged

feat: artifact update & audit — advisory revise + staleness/audit layer#44
MCKRUZ merged 2 commits into
MCKRUZ:masterfrom
splashthree:artifact-updating

Conversation

@splashthree

Copy link
Copy Markdown
Contributor

What

An additive, advisory layer for changing a pre-Build artifact after the fact and auditing the trail. It connects two facts the tool already has — when each artifact changed (SHA-256) and what depends on what (declared traceability) — so staleness falls out for free.

Pieces

File What it does
scripts/artifact_model.py Ledger entry shape + staleness disposition state machine (OPEN → REFRESHED | ACKNOWLEDGED | NOT_AFFECTED) with honest counting. REFRESHED is derived-only, never a typed word.
scripts/artifact_lineage.py Harvests upstream → downstream edges (declared + labeled coarse phase-order fallback), cycle-safe.
scripts/audit_artifacts.py record / impact / report engine — exit 0 always; its own JSONL ledger, never inside gate_results.
commands/sdlc-revise.md Change one artifact by id/section → record why (+ DL-NN) → re-gate → show downstream staleness.
commands/sdlc-audit-artifacts.md Read-only sibling to /sdlc-audit: freshness dashboard, --impact, --history.
references/artifact-lifecycle.md Tier-3 reference doc.

Wiring (additive touches): /sdlc-status stale rollup, /sdlc-next advisory record --scan, command counts 21 → 23 in CLAUDE.md / README.md / docs/commands.md.

Guarantees

  • Protected core byte-for-byte unchanged (check_spec.py, check_gates.py, phase_model.py, advance_phase.py, section-evaluator, harness/**, phase-registry.yaml, /sdlc-coach, /sdlc-spec).
  • No phantom rows — ledger is a standalone JSONL; /sdlc-audit output is byte-identical with or without it.
  • Advisory — staleness is a candidate a human dispositions, never a gate.

Verification

  • 512 tests pass (65 new).
  • End-to-end staleness lifecycle verified in both --repo and --state modes.
  • Adversarial review (7 lenses): 6 confirmed defects found and fixed (incl. a HIGH — a typed REFRESHED clearing debt; now rejected).

🤖 Generated with Claude Code

splashthree and others added 2 commits August 6, 2026 10:22
Add an additive, advisory layer for changing a pre-Build artifact after the
fact and auditing the trail. Connects "when each artifact changed" (SHA-256)
with "what depends on what" (declared traceability) so staleness falls out.

- artifact_model.py: change-ledger entry shape + staleness disposition state
  machine (OPEN -> REFRESHED|ACKNOWLEDGED|NOT_AFFECTED) with honest counting;
  REFRESHED is derived-only, never a recordable word.
- artifact_lineage.py: upstream->downstream edge harvest (declared + labeled
  coarse phase-order fallback), cycle-safe; id-ownership restricted to
  .sdlc/artifacts/ so a stem-collision can't reverse an edge.
- audit_artifacts.py: record / impact / report engine, exit 0 always; own
  JSONL ledger (never gate_results), tz-safe --since, corrupt-ledger and
  unreadable-file safe.
- /sdlc-revise + /sdlc-audit-artifacts commands; references/artifact-lifecycle.md.
- Wiring: /sdlc-status stale rollup, /sdlc-next advisory record --scan.
- Counts 21 -> 23 in CLAUDE.md / README.md / docs/commands.md.

Protected core byte-for-byte unchanged; /sdlc-audit output identical with or
without the ledger. 512 tests pass.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The advisory surface promises exit 0 always, and broke that promise on the
happy path. `_format_freshness` printed two glyphs a default Windows console
(cp1252) cannot encode: the arrow on every stale line and the check on every
signed-off phase. Printing either raises UnicodeEncodeError and kills the
process with exit 1 — so `/sdlc-audit-artifacts` worked right up until it had
something to report, then crashed instead of reporting it.

Both glyphs now degrade to ASCII when, and only when, the console can't encode
them; a UTF-8 terminal is byte-for-byte unchanged. Resolved per call rather
than at import because stdout gets replaced after load.

The suite could not have caught this: capsys buffers as UTF-8 and CI is Linux,
so both instruments are blind to it by construction. The three new tests bind
stdout to a real cp1252 stream — the first in the suite that reproduces what a
Windows user actually sees — and one pins the UTF-8 rendering so the fallback
can't silently become the default.

Verified against the reproduction: both crashing commands now exit 0 and
render. 514 passed, 1 skipped.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@MCKRUZ
MCKRUZ merged commit 127c920 into MCKRUZ:master Aug 6, 2026
2 of 3 checks passed
MCKRUZ added a commit that referenced this pull request Aug 6, 2026
#44 added /sdlc-revise and /sdlc-audit-artifacts to the Additional Commands
table but left the sentence above it reading "Ten commands" — the count the
consistency check calls authoritative, and the one a reader trusts.

Invisible to the PR: its branch predates the check that asserts this, so the
branch was green and only the merge result is red. CI tests the merge, which
is exactly the gap the Actions outage left open.

658 passed, 7 skipped.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants