diff --git a/00-META/checks/README.md b/00-META/checks/README.md index 4a1e7c2..7189f02 100644 --- a/00-META/checks/README.md +++ b/00-META/checks/README.md @@ -26,6 +26,7 @@ indistinguishable from one that cannot. | `numbering` | the number in the filename is the number in the heading | — | | `topics` | every record names a topic the index knows | — | | *(index.py)* | the written reading order matches what the records say | — | +| `status-vs-code` | a to-be document naming specific code is not still `designed` | **ten documents**, several with a *What was built* section, describing lab-proven code | ## What is deliberately not checked diff --git a/00-META/checks/records.py b/00-META/checks/records.py index e36f96e..4469db8 100644 --- a/00-META/checks/records.py +++ b/00-META/checks/records.py @@ -284,6 +284,37 @@ def check_numbering(failures, records): ) +def check_status_against_code(failures): + """A design document naming specific code may not still call itself `designed`. + + **Naming a file is a claim that the file implements this**, so the two fields have to agree. + They drifted: ten to-be documents named working, lab-proven code — several with a *What was + built* or *Raised, and observed* section — while still saying nothing had been built. + + Deliberately weak, and that is the point of it being mechanical. It cannot tell whether the + prose is true, only that a document has stopped claiming to be unbuilt once it points at + something. `code: [mesh-control]` — a repository with no path — is a plan and stays + `designed`. + """ + for path in markdown_files(): + if not rel(path).startswith("03-DESIGN/01-to-be/") or path.endswith("README.md"): + continue + front = frontmatter(read(path)) + if front.get("status") != "designed": + continue + for entry in front.get("code") or []: + named = re.sub(r"\s*\(.*\)$", "", entry).strip().split(None, 1) + if len(named) > 1: + failures.add( + "status-vs-code", + rel(path), + f"`designed`, but names {named[1]!r} in {named[0]}. Naming a file claims " + f"it implements this — use `in-progress`, or `implemented` once it is " + f"defensible from that repository's main branch.", + ) + break + + def main(): failures = Failures() records = load_records() @@ -293,6 +324,7 @@ def main(): check_supersession_symmetry(failures, records) check_numbering(failures, records) check_topics(failures, records) + check_status_against_code(failures) print(f"records: {len(records)} decision records checked") return failures.report() diff --git a/03-DESIGN/01-to-be/04-lab-installation.md b/03-DESIGN/01-to-be/04-lab-installation.md index 30410d1..89e5954 100644 --- a/03-DESIGN/01-to-be/04-lab-installation.md +++ b/03-DESIGN/01-to-be/04-lab-installation.md @@ -1,8 +1,8 @@ --- layer: to-be -status: designed +status: in-progress code: [mesh-lab] -updated: 2026-08-28 +updated: 2026-08-31 decisions: - 02-DECISIONS/0016-the-lab.md - 02-DECISIONS/0010-delivery.md diff --git a/03-DESIGN/01-to-be/05-the-node-host.md b/03-DESIGN/01-to-be/05-the-node-host.md index 057043f..8efd176 100644 --- a/03-DESIGN/01-to-be/05-the-node-host.md +++ b/03-DESIGN/01-to-be/05-the-node-host.md @@ -180,7 +180,10 @@ what it is. No control plane, no declarations, no network. Verifiable immediatel the first node's path, and it is the claim the skeleton's Move 1 rests on and has never proved: that one host can raise the substrate alone. -Raising the substrate needs six shapes in the host's vocabulary, and **all six are built**: +Raising the substrate uses **four** shapes — `package`, `container`, `service`, `action` — +counted from the bundle that exists rather than reasoned about. `file` and `directory` are listed +below because they are the cheapest to be sure of and a substrate that needed them would find them +ready; the current bundle simply does not. **All of them are built:** | | | | |---|---|---| @@ -272,6 +275,34 @@ nowhere else to get it — the detector is the only thing that looked. most.** *This machine has no container runtime* is the answer; *docker is not installed* is why. The first is the mesh's to say and the second is only the machine's. +### The eight, and what each one is evidence of + +*Written 2026-08-31 from `internal/profile/detectors.go`, because the set was implemented and +enumerated in no document. A vocabulary a module writes against, that exists only in code, is one +nobody can write against without reading the code.* + +| capability | what a detection proves | +|---|---| +| `container-runtime` | a runtime is **running**, not installed | +| `package-manager` | the machine's own package manager works | +| `service-manager` | an init that can be asked for state — including *degraded*, which reports on stdout and exits non-zero | +| `firewall` | a filter this host can write rules into | +| `overlay` | the private network can be joined | +| `graphical-session` | a display server **is running** — state | +| `seat` | hardware where one **could** run — and assignment needs this one, not the row above | +| `privileged` | the host can change the machine | + +**`seat` and `graphical-session` are the pair worth reading twice**, because collapsing them is +the obvious economy and it is wrong in both directions: a machine with a seat and no session can +be given a display server, and a machine with a session running is not thereby able to host a +second one. + +**A detection runs something that only succeeds if the thing is *functioning*, never `--version`.** +A version string proves a binary is on disk, which +[`04-ISSUES/007`](../../04-ISSUES/007-an-installed-package-is-not-a-capability/00-report.md) +records as false in the way that matters: the package was installed and the daemon was not +running. + **Never reported and reported nothing stay different.** One machine has not run the host yet; the other ran it and can do nothing. Both refuse everything that requires a capability, and the remedies are not remotely alike. diff --git a/03-DESIGN/01-to-be/06-the-control-plane.md b/03-DESIGN/01-to-be/06-the-control-plane.md index 920846f..654acc7 100644 --- a/03-DESIGN/01-to-be/06-the-control-plane.md +++ b/03-DESIGN/01-to-be/06-the-control-plane.md @@ -1,9 +1,9 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-control -updated: 2026-08-29 +updated: 2026-08-31 decisions: - 02-DECISIONS/0001-mesh-brokers-nodes-host-agents-think.md - 02-DECISIONS/0005-the-node-host.md @@ -177,7 +177,7 @@ volume genuinely argues against a relational store. node except through the host. - **Not a surface.** Tier 3 is how people and agents reach it. It has one interface; the surfaces are what speak to that interface. -- **Not the substrate.** It *runs on* tier 1 — PostgreSQL, LavinMQ, MinIO, an OCI registry +- **Not the substrate.** It *runs on* tier 1 — PostgreSQL, LavinMQ, an OCI registry ([ADR 0006](../../02-DECISIONS/0006-the-substrate-and-the-control-plane.md)) — and cannot start without them, which is what makes them a lower tier. - **Not privileged on a node.** It has no more access to a machine than the declaration diff --git a/03-DESIGN/01-to-be/07-the-substrate.md b/03-DESIGN/01-to-be/07-the-substrate.md index 14601d3..02cd451 100644 --- a/03-DESIGN/01-to-be/07-the-substrate.md +++ b/03-DESIGN/01-to-be/07-the-substrate.md @@ -1,6 +1,6 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-host examples/substrate-first-node.lock - mesh-host internal/apply @@ -117,15 +117,20 @@ Being substrate and being in the bundle are two different questions: |---|---|---| | PostgreSQL | yes — the control plane's own state lives in it | **yes** — there is nowhere to put that state otherwise | | LavinMQ | yes — it cannot grant itself a virtual host | **yes** — the control plane reaches a node only over the link, and the link is the broker ([ADR 0006](../../02-DECISIONS/0006-the-substrate-and-the-control-plane.md)) | -| MinIO | yes — it cannot grant itself a bucket | no — nothing is delivered before the mesh exists | | the OCI registry | yes — it cannot grant itself a repository | no — the first node fetches upstream ([ADR 0006](../../02-DECISIONS/0006-the-substrate-and-the-control-plane.md)) | -The two on the bottom rows are **substrate by role and ordinary by delivery**: by the time they -are wanted there is a control plane, and it provisions them the way it provisions anything. -That keeps the bundle to two images rather than four, which is what makes it small enough for the -review [ADR 0005](../../02-DECISIONS/0005-the-node-host.md) requires. It was one until -[ADR 0006](../../02-DECISIONS/0006-the-substrate-and-the-control-plane.md) established that the broker has -to precede the control plane. +The registry is **substrate by role and ordinary by delivery**: by the time it is wanted there is +a control plane, and it provisions it the way it provisions anything. That keeps the bundle small +enough for the review [ADR 0005](../../02-DECISIONS/0005-the-node-host.md) requires — one +substrate image until +[ADR 0006](../../02-DECISIONS/0006-the-substrate-and-the-control-plane.md) established that the +broker has to precede the control plane, and two since. + +*Corrected 2026-08-31, from counting what the bundle holds rather than reasoning about it.* **It +carries three images, not two** — PostgreSQL, LavinMQ, and the control plane itself, which the +sentence above had overlooked by counting only substrate services. The control plane is what the +substrate exists to start, and it is in the bundle for the same reason they are: there is nothing +to fetch it with yet. It also carries seven actions, a package and a service. **Why pinned:** the bundle is applied when no mesh exists, so nothing can resolve a version, ask a registry, or check a constraint. What the host carries must already be exact. @@ -150,8 +155,8 @@ The order, from [research 011](../../01-RESEARCH/011-the-module-graph/worked-pro 5 a virtual host, a credential, and actions, run locally a self-signed certificate 6 the control plane starts and only now is there a mesh -7 MinIO, the registry, and everything the ordinary path - else are provisioned +7 the registry, and everything else the ordinary path + are provisioned ``` **Steps 4 and 5 are why the bundle is not one image** @@ -185,10 +190,13 @@ what it is called differs per system. It is: - a package, which needs the machine's own package manager and a network — both permitted by [ADR 0006](../../02-DECISIONS/0006-the-substrate-and-the-control-plane.md). -So the host's bootstrap vocabulary is six shapes: **package**, **container**, **file**, -**directory**, **service**, and **action**. **All six are built** -([`05-the-node-host.md`](05-the-node-host.md) stage 2), so nothing in this bootstrap is -blocked on the host any longer. +So the bootstrap uses four shapes: **package**, **container**, **service** and **action** — +*counted from `substrate-first-node.lock`, which is the only bundle there is*. It had said six, +adding `file` and `directory`, which this bootstrap never asks for. + +All four are built, as are the host's other four +([`05-the-node-host.md`](05-the-node-host.md) stage 2), so nothing in this bootstrap is blocked +on the host any longer — which is the claim that mattered, and it was true either way. **Steps 2 and 3 happen before there is a mesh to do them**, which is why provisioning is part of the bootstrap rather than a service consumers use later. They are **actions** the bundle @@ -220,7 +228,7 @@ host's vocabulary grows by one shape rather than by one resource type per substr question was whether the host must learn what a database is, and it must not. The bundle declares an **action**; the host runs it and verifies it, and what a database means stays with the module that provides one. -- **Whether one host can raise all four.** The claim under stage 2 of +- **Whether one host can raise all three.** The claim under stage 2 of [the node host](05-the-node-host.md), never proved. If it is false, the tier boundary moves. - **How the substrate is updated once a mesh exists.** Pinned by hand at bootstrap; afterwards the control plane could deliver it like anything else, and nothing says whether it does. diff --git a/03-DESIGN/01-to-be/08-connectivity.md b/03-DESIGN/01-to-be/08-connectivity.md index 2c8b300..41e059d 100644 --- a/03-DESIGN/01-to-be/08-connectivity.md +++ b/03-DESIGN/01-to-be/08-connectivity.md @@ -1,6 +1,6 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-control internal/catalogue/filtering.go - mesh-control examples/route-proxy diff --git a/03-DESIGN/01-to-be/09-the-node-lifecycle.md b/03-DESIGN/01-to-be/09-the-node-lifecycle.md index d4772c2..ab703ac 100644 --- a/03-DESIGN/01-to-be/09-the-node-lifecycle.md +++ b/03-DESIGN/01-to-be/09-the-node-lifecycle.md @@ -1,6 +1,6 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-host internal/link/run.go - mesh-host internal/link/enrol.go diff --git a/03-DESIGN/01-to-be/10-delivery.md b/03-DESIGN/01-to-be/10-delivery.md index 5d0073b..f1c97e6 100644 --- a/03-DESIGN/01-to-be/10-delivery.md +++ b/03-DESIGN/01-to-be/10-delivery.md @@ -1,6 +1,6 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-control internal/builder - mesh-control cmd/mesh-control (build, build --behind, push, status) diff --git a/03-DESIGN/01-to-be/11-a-board.md b/03-DESIGN/01-to-be/11-a-board.md index 235bb60..0a82e95 100644 --- a/03-DESIGN/01-to-be/11-a-board.md +++ b/03-DESIGN/01-to-be/11-a-board.md @@ -1,6 +1,6 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-control cmd/mesh-control/board.go - mesh-control cmd/mesh-control/readable.go diff --git a/03-DESIGN/01-to-be/12-a-module-repository.md b/03-DESIGN/01-to-be/12-a-module-repository.md index 317a5b0..127c231 100644 --- a/03-DESIGN/01-to-be/12-a-module-repository.md +++ b/03-DESIGN/01-to-be/12-a-module-repository.md @@ -1,6 +1,6 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-control internal/builder - mesh-control internal/catalogue/build.go diff --git a/03-DESIGN/01-to-be/13-credentials-and-their-rotation.md b/03-DESIGN/01-to-be/13-credentials-and-their-rotation.md index d368074..54ac2c6 100644 --- a/03-DESIGN/01-to-be/13-credentials-and-their-rotation.md +++ b/03-DESIGN/01-to-be/13-credentials-and-their-rotation.md @@ -1,6 +1,6 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-control internal/inventory/secrets.go - mesh-control cmd/mesh-control/rotate.go diff --git a/03-DESIGN/01-to-be/14-model-access.md b/03-DESIGN/01-to-be/14-model-access.md index 25b9f9d..0e19da7 100644 --- a/03-DESIGN/01-to-be/14-model-access.md +++ b/03-DESIGN/01-to-be/14-model-access.md @@ -1,6 +1,6 @@ --- layer: to-be -status: designed +status: in-progress code: - mesh-control internal/licences - mesh-control cmd/mesh-control/licence.go