Conversation
afogel
force-pushed
the
slice/v7
branch
2 times, most recently
from
August 10, 2026 07:13
dbf156f to
9e03ab3
Compare
afogel
force-pushed
the
slice/v7
branch
2 times, most recently
from
August 11, 2026 11:07
550e7c2 to
6b84c70
Compare
…ables disagreeing with their own graph Fix round 1. The split's consequence for V8 was recorded only in a gitignored report, and three tables said things their neighbours did not. **The obligation the split created is now written where a reader meets it.** Adding N53 to SS V8's table left V8's own affordance list short an entry -- item 6c's defect reproduced one slice over, discoverable only by diffing two tables. SS V8 now carries a note saying N53 is new scope added by V7's split, that this slice's affordances are U31, N45, N46, N53, S12, and that `slices/v8/README.md` carries the same five. SS V7's split note says the split reaches V8 rather than only that the row sits elsewhere: until now U31 was rendered by a function V7 built and V8 inherited. Detail C's N53 row says "V8 builds it and V8 renders it" with the reason -- its only input is V8's `diffSurfaces()`, so V7 can neither build nor test it. **N40's `Wires Out` was missing `→ N49`, and predates this task.** Verified against `d3601d2`, the V7 scaffold commit: both affordance tables have said `→ N41, → N42, → N43, → N44` since before round 4, while the mermaid at `shaping.md:497` has carried `N40 --> N49` all along. A reader working from the table alone wires four checks, never runs the trace-pillar check, and the Trace non-claim drops out of the published matrix -- which is D10's whole deliverable. The tables now match the graph. Not caused here; fixed here because this task's subject is that these two surfaces agree. **SS V7 declares the store it reads.** V6's slice table lists three stores and V7's listed none, though the mermaid has `S10 -.-> N41`, `-.-> N42` and `-.-> N48`, Detail C's shared-store row names all three as readers, and this slice's own commitment 2 names S10 by ID. V7 declares no store of its own, which is the honest reason -- so the row it gains is the shared one, in the form SS V1 uses, and the README's affordance line says both halves rather than being silently asymmetric with its sibling. Two smaller ones. `README.md:58` scoped V7 as a coverage matrix and dropped the mapping table (U32/N48) that C5 names as half the published artifact; it now uses the two-noun form this branch already wrote at `shaping.md:153`. `slices.md:404` still said `N49` measures and `U33` renders, the one sentence item 6c quotes -- reading it before the table collapses N52 out and inverts commitment 4. It now names all three.
…t yet meet The note added to close the split's cross-slice gap ended by asserting that slices/v8/README.md already carries the five affordances. It does not -- it was written before the split and lists four -- so the sentence meant to prevent an under-declared README was itself the reason a reader would skip fixing it.
Commitment 2 of slices/v7/README.md splits three names apart: mapping.yaml declares, the matrix measures, and neither may wear the other's job. Four sentences still collapsed them, one of them in the runtime's own source. - README.md's V7 row said "the matrix is the declaration". R5.3 is a statement this project makes and can be wrong about; the matrix is what catches it. Now the declaration, with a measurement attached to each line. - §V7 said "R5.3 lands here: the matrix *is* the profile declaration", which is where the README's line came from. Retraction recorded there. - C5 said "test matrix" -- a third name for the 8 x 5, in the one commitment whose subject is which two artifacts get published. - The order rationale still said V7 "can only be green", the success name §V7 retracted for making the matrix redefine its own claim. - map-verdict.ts, server.ts and server.test.ts each said the intervention_points table is what V7's conformance matrix publishes. It is what V7's mapping table publishes; the matrix measures round trips through it. Two freezes added ahead of the first V7 file: 5. The harness imports the Guardian and calls it, and the Inspector's import ban does not transfer -- R5.1/R5.2 are claims about a third party reading the wire, C2/R5.3 are claims about this runtime, and calling the runtime is the evidence for those. The bound runs the other way: the 8 rows and 5 columns come from the pinned SDK's own InterventionPoint and Decision consts, never from a list the Guardian hardcodes, or the matrix measures the Guardian against itself. 6. N43 is a recomputation check, and nothing here is named for a field ACS v0.1.0 does not have. Two findings recorded in §V7, both measured while answering the freeze: R1.4's cell resolves green-for-the-Guardian, red-for-a-wire-consumer like the warn column and D10's Trace attributes -- v0.1.0 carries no action-identity field on any of its 43 schemas -- and N43 has no input today, because PolicyBridge.evaluate drops the identities the SDK returns. 795 pass / 1 skip / 0 fail, typecheck clean. Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
The plan is a projection of §V7, not a second place to decide things, so every decision it took is amended back into the slices doc in this commit. N43's seam -- a second message on the role, not a fatter answer. PolicyBridge gains evaluateWithEvidence(), and evaluate() is implemented in terms of it: one call into the SDK, the narrow answer provably a projection of the wide one, and server.ts untouched. Widening evaluate's RETURN would re-create the bag the PR #10 review removed, with the harness as its only new reader. A separate factory would create a second path to AGT, and a conformance harness certifying the path production does not take. Upstream issues -- not V7's. The slice lands the measured cells and the stated consequence; filing stays a separate deliberate act. Measured while planning, against the pinned SDK rather than read from AGT's docs: the identity is SHA-256 of key-sorted, whitespace-free JSON of the policy input, and enforced_identity is the same hash after replacing policy_target.value ALONE. The snapshot's copy of that leaf is not updated -- so AGT's identity binds to the policy target it rewrote, not to the document the host executes. That makes R1.4 the third finding to resolve green-for-the-Guardian / red-for-a-wire-consumer, after R1.3's annotations and D10's Trace attributes, and it sharpens the v0.2 ask: adding enforced_identity to AcsResult is necessary and not sufficient, because the wire never carries the policy input a host would check it against. The (a)/(b) fork is recorded rather than resolved. Also amended: R1.4 now reads "Must-have, qualified" on R1.3's precedent, with a Fit Check note; a cell has three answers and guardian_only is named; the handshake response is unexpressible against response-envelope.json and the validator reports rather than throws; N40's runner is `conformance`, since every other package here is a bare noun; N47's retired name is gated rather than merely retired; and risk row 7 no longer implies the Node SDK alone made N43 reachable. 795 pass / 1 skip / 0 fail, typecheck clean. Slice: #8 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
… reporter Task 2 review round 1 fixes: - unexpressible is now reported on stderr (naming method and reason), matching what the comment claims rather than being computed and discarded - the response-validation reporter in handleAcsRequest is wrapped in try/catch, matching envelope-log-sink.ts's own "total means total" - reworded both report messages so the composite line stays true whether a response actually failed the schema or was never checked at all - moved isServerHelloResponse inside validateResponse's own try/catch, so "reports, never throws" covers the whole function body - corrected the strictRequired mechanism comment: Ajv's check does see across the not/oneOf boundary via inherited definedProperties: false positive is a keyword-compile-order artifact (not/oneOf compile before properties), not a boundary the check cannot see across - fixed test 2's fixture to use a schema-valid request_id and assert on pointer/message, so it fails for the reason its name claims - added a fixture proving isServerHelloResponse's AND is load-bearing: a decision response missing only `decision` reports invalid, not unexpressible Slice: #8 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
Slice: #8 · N41 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
Slice: #8 · N43 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
…e S10 declares Slice: #8 · N44, N48 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
Slice: #8 · N47 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
Slice: #8 · N49, N52 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
…ement caught The shaping round recorded that `AcsResult` has no `evaluator` field, and that `confidence`, `evaluator_version` and `model_id` do not exist on it either. That propagated into V7's plan and into this task's brief. It is wrong. `response-envelope.json`'s `$defs.AcsResult.properties.metadata` declares exactly `evaluator`, `evaluator_version`, `evaluation_duration_ms`, `model_id` and `confidence`, and says why: "ACS-defined evaluator and observability metadata -- keeping the split clean lets Trace consumers key on a stable shape." The fields exist, and they exist for this. The cells stay red. Neither `metadata` nor its members are required, and `AcsResult.required` is `[type, acs_version, request_id, decision]`. So the attributes are unemittable by a wire consumer for the reason `acs.capability` is -- present but optional -- and not for the reason four documents gave. That changes what V7 publishes, in the direction of a sharper claim. The shape the three findings share is optionality, not absence: R1.3's `annotations`, D10's Trace attributes and R1.4's identity are all things the envelope may carry and is never obliged to. Only the identity is genuinely missing. The v0.2 ask narrows from "add these fields" to "require the ones already there, and add the one that is not." And this implementation leaves the slot empty: `AcsDecision` declares no `metadata` member and `mapVerdict` never sets one, so every decision this Guardian sends omits an evaluator identity the spec already has a home for. Available today, not a v0.2 ask -- filed for a later slice rather than absorbed here. N49 resolves each row against the schema at runtime rather than transcribing the expected answers, which is the only reason this surfaced. Slice: #8 · N49 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
…ribute name
The facts file said acs.evaluator, acs.confidence, acs.evaluator_version and
acs.model_id have no property on AcsResult at all. That was derived from a
top-level property listing and never descended into metadata, and it was
wrong: response-envelope.json's $defs.AcsResult.properties.metadata declares
all four. checkTracePillar's own decision-attribute site derivation
(attribute.slice("acs.".length)) reproduced that wrong answer mechanically
for the same four, because it assumed every decision_event attribute is a
direct AcsResult sibling.
The verdict does not move -- metadata is optional on AcsResult and declares
no required list of its own, so all four stay unemittable -- but the reason
does, from "absent entirely" to "present but optional", the distinction this
task's whole rule turns on. Replaced the mechanical derivation with an
explicit, throwing site table (decisionAttributeSite), mirroring
stepAttributeSite: a future decision_event attribute this table does not
name now throws instead of silently degrading to "no wire source".
Two tests pinned the wrong answer and now pin the right one. Two more were
weaker than their names: the row-count test now asserts the exact span
multiset, not just the total; a new test ties the frozen six-method scope to
mapping.yaml's own non-null acs_method values so it is self-checking rather
than true-for-now. render.ts's own doc comment cited acs.evaluator as its
example of the null-wireSource case, which stopped being true once the fix
landed -- none of today's 17 rows takes that branch any more, so the
RenderOptions.color test now uses a synthetic fixture that does, and the
comment says so instead of citing a row that no longer demonstrates it.
Documented, not modeled: resolveField still does not walk AcsResult's allOf
(acs.reasoning reads "optional" under the rule as stated, true only for
`allow`), and acs.provenance.origin is measured under a narrower,
now-explained rule than the other 16.
Slice: #8 · N49, N52 · review round 1 fix
Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
…each line Slice: #8 · R5.3 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
…nt retired them Three sites in the shaping doc, the slices doc and this slice's plan still carried numbers V7's own measurement had replaced. Each is corrected against the capture in docs/demos/v7-runbook.md rather than against the sentence beside it. - Shaping doc, D10's decision row: "two of its required span attributes are declared on the wire but never required there" -- the evidence table three lines below it has three rows covering five attributes, and N49 measured six once acs.reasoning is included. Corrected to six, with both prior wordings named, since this row has now been corrected twice. - Slices doc, sec V7: "Expect two cells to be honestly red -- now four" was a planning expectation the published matrix superseded, and it counted D10's Trace attributes as two of the four. Both halves retired. A point with no ACS v0.1.0 target is red at all five AGT verdicts, so D4's two model-call points are ten unexpressed cells rather than two; four more are unexpressed at transform, where the point declares no modifications rule. Counted off the capture: 18 expressed, 8 guardian_only, 14 unexpressed. And a Trace attribute is a U33 row, not a cell of the 8 x 5 -- commitment 4 froze that distinction after this sentence was written. - The plan's embedded cells.ts comment, which no longer matched the file after the same phrase was corrected in packages/conformance/src/cells.ts. Two review passes read the slices-doc sentence and cleared it, both asking whether its phrase belonged to the stale-count class rather than whether the whole sentence survived the measurement. It did not. Slice: #8 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
…opped line
The whole-branch review found the matrix itself sound but the prose around it
carrying sentences that outlived their own measurement. Three classes of fix:
Retracted vocabulary still in use. The demo sentence in four places (both
READMEs, the master slices doc's summary table, the runbook's quote) still
said "green"/"red" after this slice retracted those as status names in favor
of expressed/guardian_only/unexpressed; the same slip recurred in the Detail C
affordance table's N49 row ("a cell is green"), which also called a trace row
a "cell" when a trace row is not a cell of the 8x5 (commitment 4).
Stale counts, re-measured. Ten `it` blocks in test/invariants.test.ts, not
eight -- the ninth is V5's own review-round-3 hookmap gate, the tenth is V7's
renderMatrix gate; both README.md's tally and its enumeration now say so. The
three-independent-findings split (warn/Trace/identity) is one optionality and
two absences, not "two optionality, one absence" -- both documents of record
said it backwards, and the shaping doc's copy gets an explicit second-
correction note since this is its second miscount. D10's own evidence table
has three red rows covering five attributes, not two; four of those five sit
under `metadata`, not three. `identity` occurs four times across two spec
files, not twice. Inbound requests compile against three schemas, not "all
43" -- validate-response.ts had newly written the phrasing its own sibling
module had just retracted; the master doc's parallel claim gets the same
correction, credited to this slice's own measurement.
Evidence gaps closed. verify:zero-diff's root-README claims read as though the
check currently passes; it proves R3.4 only with HEAD at slice/v5, and a bare
run from any later HEAD -- including this one -- fails for reasons later
slices legitimately added, which the runbook already captures. The runbook's
own capture of that failure was itself short one line (the wrapper's own exit
message), fixed by re-running the command rather than hand-editing the block.
The matrix's escalate column and two transform cells publish a check-mark
under the matrix's stated subject (ACS's expressive power) with no footnote
saying this Guardian's own ask/modify responses are separately measured
schema-invalid; the runbook's "What was not verified" section now says so.
Plus a page of one-line corrections in the same vein: a trace-pillar row
count, a dead import, an "above" that should read "below", a test name
claiming more than its stub measures, a citation to a slice README that does
not exist yet, and a few dangling cross-references.
Verified: bun test (880 pass), bun run typecheck, bun run verify:pin all
clean; bun run conformance and verify:zero-diff both re-run and diffed
byte-identical against their runbook captures.
Slice: #8
Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
…m a third time The final review named four sites carrying the retracted green/red status names and two carrying verify:zero-diff in the present tense. Fixing those surfaced three more of the same, in documents this slice had already amended. - README's V5 status paragraph said verify:zero-diff "checks mechanically", the same present tense the review corrected in the Verify section and the V1 claims table. It checked, with HEAD at slice/v5, which is the only place the claim is measurable. - The shaping doc's two Fit Check notes described a V7 matrix cell as "green for the Guardian, red for a wire consumer". The matrix publishes no green and no red; the status is guardian_only. Same in the slices doc's own warn paragraph, which is where one of the three findings is defined. - R1.4's Fit Check note ended "the identity half of the claim is the only one where the field is genuinely missing". R1.3's annotations input is missing too: no ACS v0.1.0 payload carries a field a drift score could be derived from. So one of the three findings is optionality and two are absence. This is the third pass on that sentence -- it first said absence, was corrected to optionality during Task 8, and was over-corrected in the process. What the three share is not one mechanism but one consequence: a wire consumer cannot rely on the evidence, twice because it is absent and once because it is optional. Left alone deliberately: the same green/red shorthand in V6's plan, in packages/guardian/src/ifc-labels.ts, and in the slices doc's V6 section. Those describe V6's finding in V6's vocabulary and are that slice's to retire. Slice: #8 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
…ine number The scoped re-review of the previous fix found five residuals, four of them in the paragraphs immediately beside text that round had just corrected. - Two live sentences still called a V7 matrix cell "green for the Guardian, red for a wire consumer" -- the shaping doc's R1.3 evidence note and the slices doc's R1.4 paragraph. The status is guardian_only. - D10's evidence table headed its third column "Cell" and its prose called its rows cells. They are U33 trace rows, which commitment 4 keeps out of the 8 x 5 entirely. The column now asks the question it answers, and the note says which marks belong to which table. - Two citations in slices/v7/README.md pointed at slices-doc line numbers that the previous commit's own inserted paragraph pushed down by two, so both addressed the wrong note. They now cite the paragraphs by their titles. A line number into another file is a citation that goes stale when anything above it is edited, which is what happened here within one commit. Slice: #8 Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
Comments across packages/conformance, three files in packages/guardian, and
test/invariants.test.ts carried review archaeology ("PR #10 review, Critical",
"review round 1, Important N", "the brief's Step 3"), internal shaping
identifiers (N40-N52, R1.x, R2.4, R3.2, R5.3, C2, D4, U21/U30/U32/U33,
commitment N, §V1-V7) that resolve only against documents not in front of a
reader, and prose dense enough to need decoding. Test names lost the same
identifiers, restated in words where dropping them would leave the name
vague.
Every measured fact this slice depends on is untouched: cell-status names,
coordinate and row counts, the rendered coverage-matrix and trace-pillar text
the tests compare against, and every string literal used as fixture data or
an assertion value. Thrown-error messages and one console.error kept their
diagnostic and lost only the bare identifier prefix.
Verified: bun run typecheck clean, bun test 880 pass / 1 skip / 0 fail,
bun run conformance exits 0 with output unchanged.
Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
Sixteen comments pointed at other files by line number. Every one checked was already wrong: server.ts:664 named extractId rather than evaluateStep's catch, validate-envelope.ts:359 was a blank line, and guardian-client.ts:70 pointed at a struct field in the original slice too. A citation that drifts is worse than none, because a reader trusts it. Each now names the function or constant it means, which does not move when the lines above it change. Claude-Session: https://claude.ai/code/session_019qZbQWyJHrYG7UodpyKjYr
Critical -- the response check reported four different facts through a boolean called valid. The catch arm put "never checked" into valid: false, the same shape as "checked and rejected", so a deployment whose schema registry cannot build looked like one sending invalid responses. It is now a status: checked_valid, checked_invalid, unexpressible, unchecked, and server.ts reports each on its own line. The function is checkResponse, not validateResponse, because inbound validateEnvelope throws and stops the request while this reports and still sends -- and the claim that the coverage matrix carries the same cell is dropped, since a handshake is not a point-by-verdict coordinate and unexpressible is not the matrix's unexpressed. The intervention-point check never read a verdict, yet stamped every resolved point expressed across all five columns; mergeCells then hid those stamps behind a worse status, which made the published grid honest and that check's own output a lie if read alone. It answers per point now, and coverageCellsFromInterventionPoints emits cells only where the question resolves the whole column set. Two more names hid a second job. roundTrip reclassified warn as guardian_only, which is a drift-score coverage finding rather than part of a round trip; it is a named second step. One function was one name over two measurements, now checkInputIdentity and checkEnforcedBinding over one shared evaluation, with coverageCellsFromIdentity named as the projection stage it is. PolicyBridge and EvidenceBridge are separate roles. Production tells evaluate and nothing else, so a Guardian stand-in no longer implements a measurement question production never asks; createBridge answers with both. checkDenyFailsClosed is named for what it returns, is told a StartedGuardian and the already-loaded mapping rather than a URL string and a second read of mapping.yaml, and imports the dispatch code from the Guardian instead of copying the number it is measuring. CoverageMatrix and MappingTable now occupy their nouns, and PINNED_AGT_CLONE stops spending the upstream stem on the pinned ref. The same pass retires the planning identifiers from this package. They were worst here because the harness PRINTS them: the four checks were called N41 to N44 in measuredBy and in the legs report, the section headings named U30, U32 and U33, and a published footnote cited a domain number defined only in a module header. Every one of them is now the thing it names, so the published matrix can be read by someone who has never seen a planning document.
Renaming the clone's environment variable to PINNED_AGT_CLONE moved the reader but not the writer: scripts/run-conformance.sh still exported UPSTREAM_AGT_CLONE, so `bun run conformance` reported the policy-input schema check as DID NOT RUN while looking like a complete run. That is the failure mode this check is built to avoid -- the module self-skips by design when the variable is absent, so a stale writer degrades silently instead of erroring. Caught by running the script rather than the suite: `bun test` never sets the variable, so no test could have seen it. The script now reports RAN -- validated pre_tool_call, post_tool_call. Two comments in server.test.ts pointed at validate-response.ts and a validateResponse function, neither of which exists after the rename.
The coverage matrix filed both under `unexpressed`, and the exit rule matched that status together with the one literal reason `mergeCells` writes for an untouched coordinate. So the only thing that could ever fail `bun run conformance` was a bug in the merge's own wiring: a verdict that stopped surviving its own round trip, a point whose declared ACS method resolved somewhere else, a resolver that threw -- each carried a different reason and was counted as a resolved cell. `mapping.yaml` could ship broken and the instrument that exists to measure it exited 0. Split the classes where they are decidable rather than flipping the rule, which would have failed the honest gaps too and pressed the matrix towards being all-expressed. `CellStatus` gains `contract_violated`, ranked worst in the merge; `verdicts.ts` and `intervention-points.ts` resolve a checked declaration that does not hold to it and keep `unexpressed` for the answers that are about ACS. Which of the two a mapVerdict throw is comes from reading the declaration -- a row with no `modifications` rule predicts the refusal, and mapping.yaml says so in the table -- never from matching the error's text. `resolveExitCode` now compares statuses and reads a hole off `measuredBy` being empty, so no rewording can silence either half, and an `expressed` cell no check claims fails too. The renderer shows the new status with its own glyph and says on the table's face which one exits non-zero; the real `mapping.yaml` still exits 0, and both halves of that are now asserted.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Closes #8
Stacked on
slice/v6. Review the diff against that base, notmain. Slice 7 of 8.What this slice is for
Eight AGT intervention points × five AGT verdicts, every cell resolved: expressed, guardian-only, or unexpressed with a named reason. Trace is measured as something this implementation does not claim.
Without it, you have demos and anecdotes. There is no scorecard a reader can argue with, and no declared “we claim this / we do not claim that.”
V1–V6 are what the harness measures. This slice is the deliverable those slices exist to make possible. V8 is what keeps the matrix from silently rotting when AGT moves.
What a reviewer is looking at
bun run conformancestarts an in-process Guardian, talks to the pinned AGT bridge, and prints three separate artifacts: a coverage matrix, a mapping table, and trace-pillar rows. The mapping inmapping.yamlis a declaration this repo authored; the matrix is what the harness measured against the live runtime. They are not the same table.Honest gaps stay named:
pre_model_call/post_model_callhave no ACS v0.1.0 target; several Trace attributes have no required wire field, so a downstream consumer of the ACS wire cannot emit a conformant trace; AGTwarnis guardian-only (the stock gate reads a drift score no v0.1.0 payload carries).This implementation does not claim
acs-trace,acs-inspect,acs-provenance,acs-crypto, oracs-audit. It does not build an OTel exporter.What ships
packages/conformance/— intervention-point and verdict round trips, identity check, failure-domain split, Trace-pillar checkrenderMatrix, so an upstream diff cannot later arrive as a column of this table)scripts/run-conformance.shCaptured run:
docs/demos/v7-runbook.md.