ADR-0016: Candidate build modes — how a proposal becomes a measured artifact
Status: proposed | Date: 2026-07-09
References: ADR-0001, ADR-0005, ADR-0008, ADR-0009, ADR-0014, ADR-0015, RFC-0001
Context
The step between "agent edited a file" and "judge read a score" is undocumented. Three modes exist in practice: no artifact (compile and run in place), no rebuild (config tuning only), and build and roll (derive-layer for Python, full image build for compiled). Two critical properties are unenforceable without naming the modes: compile errors should be free (not spend a candidate), and unchanged components should not rebuild.
Decision
Name the modes, declare per component, engine enforces preconditions. mode is a typed per-component manifest field (none/derive-layer/image). crucible check enforces preconditions (same-registry for derive-layer, no compiled sources in derive-layer paths, frozen Containerfile for image mode). The build recipe is part of the judge (Containerfile must be a frozen inject). Modes live in the contract, not only the ADR. Per-iteration builds stay on-cluster (dispatch latency rules out GH Actions for per-turn builds).
Consequences
Positive: mode becomes readable, checkable, and reviewable in the manifest. Silent 20-minute or no-op failure modes become crucible check errors. The reward-hacking hole in the build recipe closes (Containerfile must be a frozen inject). ADR-0015's P5 gains its precondition.
Negative: mode is a new per-component field every domain must declare. crucible check's precondition enforcement adds validation complexity. The closed set of modes (none/derive-layer/image) may not cover future build strategies.