Tutorials · Lesson 3 of 7
3 · Declare the negative space
You'll add the two things emission can't derive: the artifacts
that make lineage real, and the residual surface — what you did NOT establish.
You need: your curated trace.json.
Declare artifacts (so lineage is real)
An artifact is a typed thing the work produced — a verification result, a decomposition, a test suite, a diff. Declaring one and pointing it at the action that produced it makes the lineage graph real, so later a goal can resolve "done" by finding the evidence, not by reading prose.
ponens trace artifact trace.json --type VerificationResult \
--name "no double-charge" --producer-action-id 12 Declare the residuals (the honest gaps)
The residual surface is the negative space — everything the trace did not establish. This is the most valuable thing you contribute as the producer: it tells a reviewer exactly where to look. A trace with no declared residuals is suspicious, not clean.
ponens trace residual add trace.json --kind assumption --severity high \
--statement "Assumes the gateway sends a stable idempotency key" \
--suggested-check "confirm the retry contract with the gateway team" The --kind vocabulary names the type of gap:
- assumption — a premise the result rests on.
- unverified — a claim you did not check.
- out_of_scope — deliberately excluded.
- limitation — a known boundary of the approach.
- open_question — a decision left for a human.
- defeater — counter-evidence against a claim (you'll meet this in Lesson 6).
Give each a --severity (info | low | medium | high | critical) and,
where you can, a --suggested-check — a cheap way for a reviewer to close it.
Read the surface back
ponens trace residuals trace.json # the declared gaps, by severity What you learned
- Artifacts make lineage real — evidence a goal can resolve against.
- The residual surface is the honest negative space; disclosing it is the point.
- Every residual has a
kindand aseverity; add asuggested_checkwhen you can.