kerfmaster pin list · UI / workflow decisions
rulingclosed d19A decision by Aristide or Jordan. True because it was decided; it can be superseded, but it cannot be stale.
Content last changed 2026-08-06 — computed from the item itself, not typed.
Contract — Cross-cutting stage
This contract states a decision, not an implementation.
takes —
makes —
fails if A screen designed before the stage it shows is defined; a pin's record content changed in a different commit from the code it describes.
Contract last changed 2026-08-06 — computed, not typed. Dated separately from the text above, so neither date can speak for the other.
1 open question blocks this pin
⚠ Known defects
This item's subject has a known defect in the code. Source: cadmaster/defects.json → cadmaster/KNOWN_DEFECTS.md, not this page — the text below is generated from the register so the two can never disagree.
Aristide, 2026-08-06: “the end goal is that we then can use the edit/pin list to create the actual interface for the software. We are hashing out input and output details, figuring out the steps we need to take to have consistent results. We will then reverse engineer the interface.”
This settles what the pin list is for, and it is stronger than “a record we keep tidy”:
4c37cf6), viewed from the other end.record items describe what already exists to wire up,
intent items are the build list, ruling items are the
constraints it must not break, and question items are the screens
that cannot be designed yet.Aristide, 2026-08-06: “how else can I give you direction so that this step does NOT get skipped.” The honest answer is that direction was never the missing piece: the same-commit rule was already written down, and it was broken five commits running. What was missing is that skipping it cost nothing at the moment of skipping. So three mechanisms now do the work that an instruction could not:
.githooks/commit-msg). A commit that
changes cadmaster code or written material without moving
pins.json or defects.json is refused. The
escape hatch is deliberate and noisy — a RECORD: none —
<reason> line in the commit message lets it through and leaves the
reason in the history. Skipping is allowed; skipping silently is what is
stopped. Installed with git config core.hooksPath .githooks.pinlist/record_debt.py). Lists every
commit since the rule existed that changed code and left the record behind. The
rule's start date is found by searching the history for the sentence
itself, not typed, so the epoch cannot drift away from the rule. First run: six commits owed — one more than had been admitted by hand. Debt is settleable: a later commit clears an older one by naming it — RECORD: settles <sha> — <where it is now written> — and since that commit passes through the gate itself, paying a debt means actually moving the record. Without settlement the bar would be red permanently, and a permanent warning is furniture.⚑ Dates are automatic too:
the page's updated date and each item's own last-changed date are
computed at build time from the item's content
(pinlist/stamps.json), not typed. The header had drifted two days
and five commits behind by 2026-08-06 — typed by hand, so forgotten by
hand.
src — Aristide, 2026-08-06.
Aristide, 2026-08-06: “How else can we organize things better so we end up with good specs for writing the software?” Two changes went in, and they are fields on the data plus generated views — not one line of any pin's argument was rewritten.
1. Every pin carries a CONTRACT. Four fields, alongside the type:
stage (which step of the pipeline it governs), in
(what that step consumes), out (what it produces), and
gate (what makes it fail there). A pin on its own states a
decision; the contract states the step's obligations. The contract
inherits the item's type and says so on the page — a contract under
an intent pin describes a stage that does not exist, and letting a
reader take that for the code is the exact defect the typing scheme exists to
stop.
2. The pipeline is a second axis. The pipeline view renders the same items grouped by stage — intake, scale, heal, QC, bridges, starts & leads, cut order, nest, post, report, plus cross-cutting rules. The sections on the subject view sort by kind of thing, which is right for an argument and wrong for a spec: bridges, start points and cut order sit in three different sections, so the pipeline could not be read off the page at all. The interface is reverse-engineered from the stages, so the stages have to be visible.
⚑ The payoff is that gaps became computable.
in and out use a controlled vocabulary of artifact
names (build_pins.ARTIFACTS), so the page can ask what a stage needs
that nothing upstream makes, and grade the answer: absent (nothing
produces it at all), unrecorded (a record pin consumes it and
no record pin produces it — either the code does not make it,
or it does and this list never said so), planned (no record pin either
end), backwards (its only built producer sits later in the line than a
consumer). A name outside the vocabulary renders red rather than inventing a
phantom hole.
First run, 8 holes, and four of them are gaps in this list
rather than in the code: cut-order, machine-profile,
material-table and true-size are all produced by
working code (emit._cut_order, emit.MACHINE_DEFAULT,
emit.SLUG_TAB_125_STEEL, $INSUNITS in
dxf_io) and no pin typed record claims any of them.
stack-up is genuinely absent — assembly connectivity and the
concealed envelope both consume it and nothing produces it.
Contract dates are hashed and stamped separately from the prose
(build_pins.contract_hash). Folding them together would have
restamped all 76 items on the day contracts were added, claiming every pin's
argument changed when what changed was the machine-readable shape around it.
src — Aristide, 2026-08-06; implemented the same day.