DR-0020 — Slim the machinery slice: the engine ships as artefact only
- Status: accepted
- Date: 2026-08-11
- Supersedes: amends DR-0001's engine clause; completes the direction set by DR-0016
Context
DR-0001 committed the framework to identity copies at every hop of the tier chain, "including the framework's own engine, which downstream publishers vendor rather than install." That sentence was written when the engine was interpreted Python: the vendored source was the executable, so vendoring it put the engine under the same manifest, checksum and review regime as every other slice file at zero extra cost.
Two later decisions removed that identity. DR-0017 replaced the Python engine
with a compiled Go binary, and DR-0016 moved execution to a released,
per-platform, checksummed artefact that consumers pin by version and sha256 —
explicitly rejecting both go run from the vendored checkout (a toolchain on
every runner) and vendoring the binary itself (bloat and churn). The Go
sources entered the export declaration during the DR-0017 transition,
alongside the Python reference they replaced, and simply stayed after the
cutover; no DR ever re-justified them.
The result is a dual distribution channel. The pinned binary is what every
scaffolded pipeline actually fetches, verifies and runs. The exported source
(cmd/**, internal/**, assets.go, go.mod, go.sum) is inert in every
consumer tree: nobody downstream builds it, and engine correctness is enforced
upstream by the golden vectors and the scenario kit, not by downstream review.
Meanwhile the inert copy has real costs:
- Every engine-internal refactor churns the manifest and lands a sync PR of Go diffs in every downstream tree — review noise with no decision content.
- Any dependency bump touches
go.mod/go.sum, so mechanical PRs (Dependabot and the like) fail the manifest freshness gate unless someone regenerates the manifest by hand on each such branch. - Consumer trees carry dozens of Go files whose only realistic fate is to be ignored.
Decision
The machinery slice exports what consumers actually consume in-tree, and nothing else:
scaffold/*/*.tmpl— the consumer pipeline scaffoldsconformance/core-rules.yml— the default wiring rulesLICENSE
The engine's Go sources, assets.go, go.mod and go.sum leave the export.
The engine's sole distribution channel is the DR-0016 release artefact:
per-platform binaries plus a checksum file, pinned by engine: {version, sha256} in each consumer's slice config and re-asserted by self-verify.
DR-0001's identity-copy rule continues to hold for all slice content, at every hop. This DR re-classes the engine from content to executor: its integrity story is the consumer-held checksum pin and tag-anchored release provenance (DR-0005), not the vendored-tree manifest.
Alternatives considered
- Status quo — keep exporting the source. Preserves DR-0001's letter, but the reviewability it buys is theoretical: downstream publishers neither build nor meaningfully review engine internals, and parity is already ratcheted upstream (DR-0017). The dual channel makes every internal refactor a downstream event and every dependency bump a gate failure. Rejected.
- Drop only
go.mod/go.sum. Stops the dependency-bump churn but leaves an unbuildable source export — worse than either a complete source slice or none. Rejected. - Vendor the engine binary instead of the source. Already considered and rejected in DR-0016 (tens of MB per platform, churn on every release).
- Keep source as the execution path (
go run). Already rejected in DR-0016 (compiler on every runner, larger supply-chain surface than a checksummed static binary).
Consequences
- The manifest shrinks from ~60 entries to a handful; engine-internal changes
no longer generate downstream sync PRs, and
go.mod/go.sumchanges no longer touch the manifest, so dependency-only PRs pass the freshness gate without hand-regeneration. - Tier chains still hold the engine's integrity at every hop — as the checksum pin in each consumer's slice config rather than as source bytes in the tree. Downstream publishers re-export scaffolds and rules; the engine reaches every hop as the same tag-anchored artefact.
- Air-gapped consumers keep the DR-0016 story (mirror the artefacts, override the fetch URL; the pin still decides trust) but lose the in-tree source fallback. Building from a tagged framework-repo checkout remains available to anyone who needs it.
- DR-0001 is amended, not edited: its engine sentence is historical as of this DR (DRs are immutable once accepted).
- Obligations: the export declaration and regenerated manifest change with this DR; architecture §4's self-hosting paragraph is updated to match. Removing vendored engine sources from existing consumer trees is a normal release delta — consumers pick it up as an ordinary sync PR whose diff is deletions.
- Bootstrap is unchanged: the release freshness pre-gate needs only the working tree.