The lattice model
The problem
Section titled “The problem”A change to a repository rarely stays in one place. Add a configuration flag, and the parser, the default config file, the documentation, and the tests each owe you an edit. Add a user-facing string, and every translation file owes you one. Agree on a team convention, and every module it governs owes you one — eventually.
Today those obligations live in prose and memory: a line in CONTRIBUTING.md, a
// keep in sync with … comment, an item on the pull-request checklist, or nothing at
all. Every one of them is a note asking a person to remember, written because no tool
owns the relation the note is describing.
Worse, the order you work in changes the result. Decide what a feature should do and then build it; or build it and write down what it does afterwards; or work both ends at once. All three are legitimate, all three are used, and they do not produce work of the same quality.
The mechanism is context. Whoever writes the spec first has to reason the problem out: which cases exist, which inputs are legal, what should happen at the edges. Whoever backfills it from working code has one solution already in front of them, and writes the spec that fits that solution. Cases the code never handled are the cases nobody writes down. Afterwards nothing looks wrong, because the two artifacts agree, and the spec has quietly become a transcript of the implementation rather than a statement of intent. Research hit the same effect hard enough to name it, which is what preregistration exists to prevent.
The path is leaking into the outcome.
Which leaves a remedy nobody keeps. Work spec-first every time, and every small change buys the full ceremony: the component looks wrong, so amend the design record before you touch the padding; you spot an off-by-one, so open a change request before you fix it. The changes people most want to make on sight are the ones the ceremony taxes hardest. So the discipline holds on work big enough to deserve it and lapses everywhere else, and the spec ends up covering the features while missing everything smaller.
Nobody should have to go back to the drawing board to move a button.
The guarantee
Section titled “The guarantee”cyber-truss makes the settled state independent of which artifact you changed first — and lets you change it without stopping.
Two halves, and both matter.
Path independence. Whichever artifact you touch first, the repository settles into a state that meets the same criteria. This is the order-theoretic reading of the lattice, taken over criteria: criteria arriving by different routes join to the same set whichever arrives first, even though several states can meet that set. Confluence is the property; the rest of the model is how it is bought.
Uninterrupted focus. The ceremony is deferred, not skipped. A designer prototypes in dumb HTML without stopping to write a spec. The obligations to spec, implementation, and documentation are raised and discharged out-of-band.
Reading order
Section titled “Reading order”| Page | What it establishes |
|---|---|
| The lattice | The concept the design is worked out from — three readings, and the one this page leans on |
| Artifact-sets | The unit the model reasons about, on two orthogonal axes, and what controls each |
| Specification | What a specification is, why it is a role rather than a layer, and what connections actually relate |
| Connections | The relation between sets, why nothing owns it today, and the kinds of strain |
| Join | How criteria arriving by different routes combine, and where they conflict |
| Workflow | What a workflow declares, the three roles a set can hold in it, and how a change finds the workflows it needs |
| Controller | What holds one set consistent, how it differs from a workflow, and what a workflow hands it |
| Confluence | What path-independence means precisely, and what it is claimed over |
| Canonical execution | How confluence is bought: distill, ask the controllers above, replay, reconcile |
| Relationship to SDD | SDD as the two-set instance of this model |
| Formal workflows | Staged processes across eight fields, and the four parameters they all reduce to |
| Waterfall in the model | One of them worked in full — and the half of it that turns out to be unnecessary |
| Open questions | What is unresolved, and what breaks if it resolves badly |
| Glossary | Every term the model defines, and the ones it deliberately avoids |
What this model is not
Section titled “What this model is not”- Not a linter. A linter reports independent violations. A truss redistributes coupled ones. The distinguishing property throughout is coupling.
- Not a test suite. Tests assert behaviour. This asserts consistency between artifacts.
- Not a mission engine. SDD runs from a change request to a handoff and retires. Convergence is a property of repository state, held continuously — including across changes no mission produced.