decree by example
Six governance scenarios follow one change — editing a file under src/auth/ —
through its whole life. A final operational example shows the v3 sprint execution flow.
Each runs real decree commands against a throwaway git corpus and prints the real
output. Nothing below is mocked; every block is captured from an actual run.
Each scenario ends on its own VALUE: line (what you gain) and HONESTY: line (where
decree refuses to overclaim). The exit code is the contract:
-
exit 1a finding you can gate CI on — a blocking finding you can gate CI on: a conflict, a live overlap, dead governance. -
exit 0clean · advisory-only — clean, or advisory / corpus-hygiene only. Suggestions, editing a decree doc, and the governance-quality signals never block. -
exit 2config error — a config error, kept apart from findings on purpose.
intent-check types every finding (blocking_findings / advisory_findings /
corpus_hygiene_findings) and leads its human output with a Block now / Clean later
split, so the exit code is a summary and the JSON is the detail.
You can run the whole arc yourself:
git clone https://github.com/doruksahin/decree && cd decreebash examples/run-all.shBefore you code
Section titled “Before you code”1 · Which decision explains this file?
Section titled “1 · Which decision explains this file?”Before editing src/auth/tokens.py, ask what governs it — and watch decree abstain on a
file nothing governs. exit 0 clean · advisory-only
── The corpus: one decision that governs the auth tokens file ──[index] rebuilding into .decree/index.sqlite[index] decisions=1 refs=0 governs=1 acs=0 commits=0[index] git_sync_ms=81✓ index rebuilt in 139ms
── Ask which decision governs the file you're about to touch ──
$ decree why src/auth/tokens.pysrc/auth/tokens.py — 1 governing decision
▸ SPEC-00000000000000000000000001 implemented 2026-05-10 exact JWT token storage governs: src/auth/tokens.py→ exit 0
$ decree why src/auth/tokens.py --json{ "query": "src/auth/tokens.py", "match_count": 1, "matches": [ { "decision_id": "SPEC-00000000000000000000000001", "type": "spec", "status": "implemented", "date": "2026-05-10", "title": "JWT token storage", "match_kind": "exact", "matched_path": "src/auth/tokens.py", "symbol": null } ]}→ exit 0
── The honesty beat: a file no decision governs ──
$ decree why src/auth/charge.pysrc/auth/charge.py — no governing decisions→ exit 0VALUE: git blame + grep + Slack archaeology → one command that returns the exact governing decision.HONESTY: why answers ONLY from declared 'governs:' frontmatter — never git, never semantic guessing.HONESTY: An empty result is a valid abstention (exit 0), not a failure. decree won't invent a decision.2 · Will my plan collide with a decision?
Section titled “2 · Will my plan collide with a decision?”Two decisions claim the same file, and the in-flight one has open acceptance criteria.
decree surfaces it at planning time, not in code review — the conflict under Block now,
the unchecked criteria under Clean later. exit 1 a finding you can gate CI on
── The corpus: two decisions claim the same file (one shipped, one in-flight) ──[index] rebuilding into .decree/index.sqlite[index] decisions=2 refs=0 governs=2 acs=2 commits=0[index] git_sync_ms=28✓ index rebuilt in 52ms
── Check the plan BEFORE coding (exit 1 = a finding you can gate CI on) ──
$ decree intent-check --plan Change token refresh storage --files src/auth/tokens.py[intent-check] exit 1: findings present (conflicts, live-session overlaps, or stale governance).Intent check — pre-PR governance map Plan: Change token refresh storage
Block now (1): ✗ resolve_conflict_first: src/auth/tokens.py is governed by SPEC-00000000000000000000000001, SPEC-00000000000000000000000002. Decide which decision is authoritative before implementing.
Clean later (3): ~ update_spec_first [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 (Token rotation policy) governs planned files and has unchecked acceptance criteria. Check off or amend ACs before implementing on top. ~ check_ac [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 has an unchecked AC under 'Acceptance Criteria': Rotation job runs on schedule ~ check_ac [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 has an unchecked AC under 'Acceptance Criteria': Old tokens revoked on rotation
Recommended next command: decree intent-check --under SPEC-00000000000000000000000001 --plan "..." --files ... (name the authoritative decision; treat the other governors as contextual)
Planned files (1): • src/auth/tokens.py
Governing decisions (2): ▸ SPEC-00000000000000000000000001 implemented exact governs src/auth/tokens.py JWT token storage ▸ SPEC-00000000000000000000000002 draft exact governs src/auth/tokens.py Token rotation policy
Stale governance (0): (none)
Unchecked acceptance criteria (2): ☐ SPEC-00000000000000000000000002 [Acceptance Criteria] Rotation job runs on schedule ☐ SPEC-00000000000000000000000002 [Acceptance Criteria] Old tokens revoked on rotation
Conflicts (1): ✗ src/auth/tokens.py: SPEC-00000000000000000000000001, SPEC-00000000000000000000000002
Live-session conflicts (0): (none)
Recommended actions (4): → update_spec_first [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 (Token rotation policy) governs planned files and has unchecked acceptance criteria. Check off or amend ACs before implementing on top. → check_ac [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 has an unchecked AC under 'Acceptance Criteria': Rotation job runs on schedule → check_ac [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 has an unchecked AC under 'Acceptance Criteria': Old tokens revoked on rotation → resolve_conflict_first: src/auth/tokens.py is governed by SPEC-00000000000000000000000001, SPEC-00000000000000000000000002. Decide which decision is authoritative before implementing.→ exit 1VALUE: Discover a two-decision collision in code review (late) → see it at planning time: the conflict, the in-flight SPEC, its unchecked acceptance criteria, and a non-zero exit.HONESTY: intent-check reports the STRUCTURAL conflict (two decisions declare the path). It does NOT judge whether they truly contradict — that semantic call is the agent's/reviewer's job.While you code
Section titled “While you code”3 · Is another agent about to touch this same file?
Section titled “3 · Is another agent about to touch this same file?”Two agent sessions independently plan the same file. Given the other live session’s
planned paths, decree flags the overlap before either starts. exit 1 a finding you can gate CI on
── The corpus: one decision governing the contested file ──[index] rebuilding into .decree/index.sqlite[index] decisions=1 refs=0 governs=1 acs=0 commits=0[index] git_sync_ms=61✓ index rebuilt in 127ms
── This session plans tokens.py — we tell decree session-b also plans it ──
$ decree intent-check --plan Edit token storage --files src/auth/tokens.py --other-active-files {"session-b": ["src/auth/tokens.py"]}[intent-check] exit 1: findings present (conflicts, live-session overlaps, or stale governance).Intent check — pre-PR governance map Plan: Edit token storage
Block now (1): ✗ isolate_session: src/auth/tokens.py is also planned by active session(s) session-b. Run in a dedicated worktree, or split this file out of one plan, before starting.
Clean later (0): (none)
Recommended next command: Run in a dedicated worktree, or split the overlapping file out of one plan, before starting.
Planned files (1): • src/auth/tokens.py
Governing decisions (1): ▸ SPEC-00000000000000000000000001 implemented exact governs src/auth/tokens.py JWT token storage
Stale governance (0): (none)
Unchecked acceptance criteria (0): (none)
Conflicts (0): (none)
Live-session conflicts (1): ⇄ src/auth/tokens.py: also planned by session-b
Recommended actions (1): → isolate_session: src/auth/tokens.py is also planned by active session(s) session-b. Run in a dedicated worktree, or split this file out of one plan, before starting.→ exit 1VALUE: Two parallel agents edit the same file blind and you reconcile the wreck later → the live collision is flagged before either starts, with an 'isolate_session' recommendation (exit 1).HONESTY: decree owns NO session state. The caller supplies the other sessions' planned paths; decree only computes the overlap. It reports THAT two sessions claim the file, not who should win.After you code
Section titled “After you code”4 · Does this diff collide with governance?
Section titled “4 · Does this diff collide with governance?”The code is written and a diff exists. Before a human reviews, gate the diff against the
decision corpus — a deterministic, CI-shaped pass. exit 1 a finding you can gate CI on
── The corpus: same two decisions claiming src/auth/tokens.py ──[index] rebuilding into .decree/index.sqlite[index] decisions=2 refs=0 governs=2 acs=0 commits=0[index] git_sync_ms=70✓ index rebuilt in 91ms
── Make a change, then review the diff against governance (CI-shaped, exit 1) ──
$ decree intent-review --diff change.diff[intent-review] exit 1: findings present (conflicts or stale governance).Intent review — file:change.diff
Changed paths (1): • src/auth/tokens.py
Governing decisions (2): ▸ SPEC-00000000000000000000000001 implemented exact governs src/auth/tokens.py JWT token storage ▸ SPEC-00000000000000000000000002 draft exact governs src/auth/tokens.py Token rotation policy
Stale governance (0): (none)
Unchecked acceptance criteria (0): (none)
Conflicts (1): ✗ src/auth/tokens.py: SPEC-00000000000000000000000001, SPEC-00000000000000000000000002
Recommended actions (2): → resolve_conflict: src/auth/tokens.py is governed by SPEC-00000000000000000000000001, SPEC-00000000000000000000000002. Decide which decision is authoritative or supersede the others. → add_implements_trailer [SPEC-00000000000000000000000002]: Changes touch files governed by in-flight SPEC-00000000000000000000000002. Consider `decree commit --implements SPEC-00000000000000000000000002` so the commit links to the SPEC.→ exit 1VALUE: Governance review that depends on a human remembering every decision → a build gate that fails when a diff collides with the decision corpus.HONESTY: Reports structural intersection + conflict/stale findings; makes NO judgment about whether the change is correct. Exit 1 means 'a human/agent must look', not 'this is wrong'.Over time
Section titled “Over time”5 · Did the decision’s declared scope rot?
Section titled “5 · Did the decision’s declared scope rot?”Months in, a SPEC still claims a file no trailer-linked commit ever touched, while its
commits keep editing a helper it never declared. decree flags the dead governance (a
finding) and, separately, the suggested governance (advisory). exit 1 a finding you can gate CI on
── The corpus: a SPEC governing two files, with real trailer-linked history ──[index] rebuilding into .decree/index.sqlite[index] decisions=1 refs=0 governs=2 acs=0 commits=2[index] git_sync_ms=60✓ index rebuilt in 78ms
── Health: declared scope no commit touched (a finding, exit 1) + scope the code grew into (advisory) ──
$ decree healthStale decisions: none (all governed paths quiet).
Ungoverned hotspots: none above threshold.
Dead governance (declared governs paths no trailer-linked commit has touched):
SPEC-00000000000000000000000001 untouched by its 2 linked commit(s): src/auth/legacy_sso.py
Suggested governance (advisory — ungoverned files with a proposed owner; does not affect exit status):
SPEC-00000000000000000000000001 from 2 linked commit(s) touching 2 path(s): src/auth/helper.py (touched in 2 commits)
observed as of 2026-07-07T17:47:21+00:00; 0 decision(s) have no trailer-linked commits (governance unobservable).
Lifecycle drift (1) — advisory: ~ SPEC-00000000000000000000000001 [terminal_but_governance_dead]: SPEC-00000000000000000000000001 is implemented (terminal) but its declared governance is dead (unobserved in commits).
Thresholds: --threshold-commits=10 --threshold-days=30→ exit 1VALUE: A decision's 'governs' list rots into fiction unnoticed → decree flags declared scope no trailer-linked commit ever touched (DEAD governance, exit 1) and, separately, scope the code grew into but never declared (SUGGESTED, advisory).HONESTY: Convention-bounded: the commit→decision link is the Implements: TRAILER convention, not a git guarantee — deterministic but not certain (needs 'decree commit' discipline).HONESTY: Asymmetry by design: DEAD is a finding (exit 1); SUGGESTED is advisory (exit 0, never feeds why()). A SPEC with zero trailered commits is reported 'unobserved, not dead' (fail-safe).While you code, governed
Section titled “While you code, governed”6 · Am I editing a file my decision doesn’t own?
Section titled “6 · Am I editing a file my decision doesn’t own?”In a governed session under a SPEC, you plan to edit a helper the SPEC’s own commits keep touching but never declared. decree nudges you to declare it — advisory, never blocking.
exit 0 clean · advisory-only
── The corpus: SPEC-…0001's own commits repeat-touch a helper it never declares ──[index] rebuilding into .decree/index.sqlite[index] decisions=1 refs=0 governs=1 acs=0 commits=2[index] git_sync_ms=118✓ index rebuilt in 145ms
── In a governed session under SPEC-…0001, planning to edit the helper (advisory, exit 0) ──
$ decree intent-check --plan edit auth helper --files src/auth/helper.py --under SPEC-00000000000000000000000001Intent check — pre-PR governance map Plan: edit auth helper
Block now (0): (none)
Clean later (2): ~ add_governance: src/auth/helper.py has no governing decision. Consider writing a SPEC or amending an existing one's `governs:` list before starting. ~ declare_governs [SPEC-00000000000000000000000001]: SPEC-00000000000000000000000001's commits repeat-touch src/auth/helper.py, which is not in its `governs:`. Consider declaring it (advisory).
Recommended next command: Proceed; address the advisory / corpus-hygiene items when convenient.
Active decision: SPEC-00000000000000000000000001 Owned files (0): (none)
Planned files (1): • src/auth/helper.py
Governing decisions (0): (none — ungoverned plan)
Stale governance (0): (none)
Unchecked acceptance criteria (0): (none)
Conflicts (0): (none)
Live-session conflicts (0): (none)
Recommended actions (2): → add_governance: src/auth/helper.py has no governing decision. Consider writing a SPEC or amending an existing one's `governs:` list before starting. → declare_governs [SPEC-00000000000000000000000001]: SPEC-00000000000000000000000001's commits repeat-touch src/auth/helper.py, which is not in its `governs:`. Consider declaring it (advisory).→ exit 0VALUE: Governance scope drifts and you catch it in a quarterly audit → 'this file is yours in practice but undeclared' surfaces at the exact moment you touch it.HONESTY: Advisory by construction: declare_governs NEVER blocks (exit stays 0) and NEVER feeds why() — it is not a governance fact until a human adds it to 'governs:'. Squash-immune (needs commit_count >= 2).Typed findings & governance quality
Section titled “Typed findings & governance quality”The same commands, read with sharper eyes. intent-check now classes every finding and
frames a multi-decision file around the decision you’re working under, and health adds
two advisory signals for governance quality. None of these change an exit code.
The plan edits a SPEC’s own markdown and a new helper. Neither blocks: the self-edit is
corpus maintenance, the new file an advisory add_governance. Both land under
Clean later, and the check exits exit 0 clean · advisory-only . exit 0 clean · advisory-only
$ decree intent-check --plan Refine the SPEC and add a helper --files decree/spec/spec-00000000000000000000000001-token-storage.md src/auth/helper.pyIntent check — pre-PR governance map Plan: Refine the SPEC and add a helper
Block now (0): (none)
Clean later (2): ~ add_governance: src/auth/helper.py has no governing decision. Consider writing a SPEC or amending an existing one's `governs:` list before starting. ~ corpus_maintenance [decree/spec/spec-00000000000000000000000001-token-storage.md]: decree/spec/spec-00000000000000000000000001-token-storage.md is a decree document; run `decree lint` (and `decree index rebuild` after governs:/frontmatter edits) — no governance needed.
Recommended next command: Proceed; address the advisory / corpus-hygiene items when convenient.
Planned files (2): • decree/spec/spec-00000000000000000000000001-token-storage.md • src/auth/helper.py
Governing decisions (0): (none — ungoverned plan)
Stale governance (0): (none)
Unchecked acceptance criteria (0): (none)
Conflicts (0): (none)
Live-session conflicts (0): (none)
Recommended actions (1): → add_governance: src/auth/helper.py has no governing decision. Consider writing a SPEC or amending an existing one's `governs:` list before starting.→ exit 0Two decisions claim src/auth/tokens.py. --under SPEC-…01 marks it as owned and
SPEC-…02 as a contextual overlap — the recommended next command says work under
your decision and treat the other as context, not a wall. exit 1 a finding you can gate CI on
$ decree intent-check --plan Change token refresh storage --files src/auth/tokens.py --under SPEC-00000000000000000000000001[intent-check] exit 1: findings present (conflicts, live-session overlaps, or stale governance).Intent check — pre-PR governance map Plan: Change token refresh storage
Block now (1): ✗ resolve_conflict_first: src/auth/tokens.py is governed by SPEC-00000000000000000000000001, SPEC-00000000000000000000000002. Decide which decision is authoritative before implementing.
Clean later (3): ~ update_spec_first [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 (Token rotation policy) governs planned files and has unchecked acceptance criteria. Check off or amend ACs before implementing on top. ~ check_ac [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 has an unchecked AC under 'Acceptance Criteria': Rotation job runs on schedule ~ check_ac [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 has an unchecked AC under 'Acceptance Criteria': Old tokens revoked on rotation
Recommended next command: Proceed under SPEC-00000000000000000000000001; the other governors are contextual — resolve only if their acceptance criteria contradict your plan.
Active decision: SPEC-00000000000000000000000001 Owned files (1): src/auth/tokens.py Contextual overlaps (1): ~ src/auth/tokens.py — also governed by SPEC-00000000000000000000000002 (context, not a contradiction)
Planned files (1): • src/auth/tokens.py
Governing decisions (2): ▸ SPEC-00000000000000000000000001 implemented exact governs src/auth/tokens.py JWT token storage ▸ SPEC-00000000000000000000000002 draft exact governs src/auth/tokens.py Token rotation policy
Stale governance (0): (none)
Unchecked acceptance criteria (2): ☐ SPEC-00000000000000000000000002 [Acceptance Criteria] Rotation job runs on schedule ☐ SPEC-00000000000000000000000002 [Acceptance Criteria] Old tokens revoked on rotation
Conflicts (1): ✗ src/auth/tokens.py: SPEC-00000000000000000000000001, SPEC-00000000000000000000000002
Live-session conflicts (0): (none)
Recommended actions (4): → update_spec_first [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 (Token rotation policy) governs planned files and has unchecked acceptance criteria. Check off or amend ACs before implementing on top. → check_ac [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 has an unchecked AC under 'Acceptance Criteria': Rotation job runs on schedule → check_ac [SPEC-00000000000000000000000002]: SPEC-00000000000000000000000002 has an unchecked AC under 'Acceptance Criteria': Old tokens revoked on rotation → resolve_conflict_first: src/auth/tokens.py is governed by SPEC-00000000000000000000000001, SPEC-00000000000000000000000002. Decide which decision is authoritative before implementing.→ exit 1A SPEC at 100% acceptance criteria with a commit attached, still marked draft, and a
governs: list grown to 26 paths. lifecycle_drift and broad_governance name both —
advisory, so the four coherence signals stay clean and health exits exit 0 clean · advisory-only . exit 0 clean · advisory-only
$ decree health✓ health: clean.Stale decisions: none (all governed paths quiet).
Ungoverned hotspots: none above threshold.
Dead governance: none (every declared path with a commit basis was touched).
Suggested governance: none (no repeat-touched undeclared paths).
observed as of 2026-07-07T17:47:34+00:00; 0 decision(s) have no trailer-linked commits (governance unobservable).
Lifecycle drift (1) — advisory: ~ SPEC-00000000000000000000000001 [complete_but_not_terminal]: SPEC-00000000000000000000000001 has 2/2 primary ACs done and 1 commit(s) attached, but status is 'draft'. Transition it, or move incomplete work to a deferred section.
Broad governance (1) — advisory: ~ SPEC-00000000000000000000000001: governs 26 (26 exact / 0 dir), 0 shared hot file(s), ratio 26.0
Thresholds: --threshold-commits=10 --threshold-days=30→ exit 0Sprint execution
Section titled “Sprint execution”7 · Can sprint tracking survive parallel work?
Section titled “7 · Can sprint tracking survive parallel work?”The v3 sprint store keeps membership in state.yaml, one live/<DOC-ID>.yaml per
document, and closed/<SPRINT-ID>.yaml. Routine work touches one membership file, so
different worktrees can add or finish different documents without creating one YAML
conflict hotspot. exit 0 clean · advisory-only
In practice, a human orchestrator can refresh the local HTML board when they want a
snapshot, pick one open sprint item, and hand that document ID to a worker agent. The
agent does not need the HTML; it starts from decree ddd --doc DOC-ID, runs
intent-check before editing, and records its own sprint complete outcome when the
acceptance criteria are done. A second worker can do the same from another worktree on a
different DOC-ID. If the item was waiting in backlog or draft pool, the orchestrator
promotes it first with decree sprint move DOC-ID --to active.
$ decree sprint status✓ sprint status reportedSprint mode: activeActive: SPRINT-00000000000000000000000001 Sprint 1 (1 items)
Tasks: SPEC-00000000000000000000000001 (manual)Backlog: 0 itemsDraft pool: 0 items→ exit 0$ decree sprint complete SPEC-00000000000000000000000001 --commit abc1234[sprint] recorded completed outcome for SPEC-00000000000000000000000001 (primary 2/2)✓ sprint item completed→ exit 0$ decree sprint status✓ sprint status reportedSprint mode: activeActive: SPRINT-00000000000000000000000001 Sprint 1 (1 items)
Done (awaiting rollover): SPEC-00000000000000000000000001 (completed)Backlog: 0 itemsDraft pool: 0 items→ exit 0That’s the governance arc: before you code (why, intent-check), while you code
(parallel intent-check, governed --under), after you code (intent-review), and
over time (health). Each answer comes only from declared facts — and each scenario
names its own boundary. Sprint execution adds the operational loop around that work:
scope it, finish it, and fold it into the archive at rollover. That asymmetry, finding
versus advisory, is the point.
Start from the capabilities, or install decree and run the arc yourself.