Verified and ratified: model-access stays one vendor-blind provision; per-vendor adapter keyed by licence.vendor (mirrors public-dns registrar providers); the sealing-vs-central-rotation carve-out bounded to refreshable-grant vendors / refresh token / manager node only. Status proposed -> accepted; index regenerated (records + index checks pass); design doc note updated. Claude-Session: https://claude.ai/code/session_01LrgweAeERJYBg88c5cKDzF
151 lines
9.2 KiB
Markdown
151 lines
9.2 KiB
Markdown
# 02-DECISIONS
|
||
|
||
Architecture decision records — the "why" trail behind the rules in
|
||
[`00-META`](../00-META/) and the specifications in [`03-DESIGN`](../03-DESIGN/).
|
||
|
||
**Numbered `02` because a decision precedes the design it authorises.** Research concludes,
|
||
the decision is recorded here, and only then is the design written. Following the folder
|
||
numbers walks the process in the order it happens.
|
||
|
||
One file per decision, numbered, never deleted. A superseded record has its `status:` changed
|
||
and gains a pointer to what replaced it — **its text is never edited**. The reasoning that was
|
||
rejected is the expensive half to rediscover.
|
||
|
||
The records run in the order the decisions were taken, oldest first.
|
||
|
||
**Every decision is a record.** There is no ledger and no index file — if a decision is worth
|
||
recording it is worth a record, and if it is not worth a record it is not recorded
|
||
([ADR 0019](0019-how-this-repository-works.md)). A "decision" small enough to be one line is
|
||
almost always a **rule**, and a rule belongs in
|
||
[`00-META/how-we-build.md`](../00-META/how-we-build.md), where it is enforced and keeps the
|
||
incident that earned it.
|
||
|
||
## Frontmatter
|
||
|
||
```yaml
|
||
---
|
||
status: proposed | accepted | superseded
|
||
date: YYYY-MM-DD # when the decision was taken, not when it was written down
|
||
deciders: name
|
||
reconstructed: true|false # true when the record was written after the fact from evidence
|
||
superseded-by: # 02-DECISIONS/NNNN-....md, when status is superseded
|
||
extends: # 02-DECISIONS/NNNN-....md, when this record widens an earlier one
|
||
---
|
||
```
|
||
|
||
## Body
|
||
|
||
```
|
||
# N. Title in plain language
|
||
|
||
## Context what was true, with evidence
|
||
## Considered Options numbered, each with why it was rejected
|
||
## Decision what was decided
|
||
## Consequences what follows, including what got harder
|
||
## References commits, pull requests, knowledge-base entries, prior art
|
||
```
|
||
|
||
State evidence, not assertion. *"Zero of 124 modules declare `brain` as a dependency"*
|
||
outranks *"the dependency rule is not followed"*.
|
||
|
||
## Reconstructed records
|
||
|
||
Records 0001–0014 were written on 2026-08-23, after the decisions they describe. Records 0015 onward were taken as records. Those
|
||
decisions were taken in implementation rather than in a document; the records state what was
|
||
decided and the evidence it was decided from, and each carries `reconstructed: true` and says
|
||
so in its first lines.
|
||
|
||
A reconstructed record is not a transcript. Where the deliberation is not recoverable, the
|
||
options section states what the alternatives were and why the chosen one won on the evidence
|
||
available — not a discussion that did not happen. Where a date is not establishable it says so
|
||
rather than guessing.
|
||
|
||
## Index
|
||
|
||
**A number identifies a record and never changes.** Records are referenced from outside this
|
||
repository — code comments, commit messages — so a number that moves invalidates them silently.
|
||
Renumbering once cost 96 references across two code repositories, and that is why the numbers
|
||
are now fixed.
|
||
|
||
So the folder is in creation order, and **the reading order lives here.** It is generated from
|
||
each record's `topic:` and written, because a reader looking at the folder on a forge sees the
|
||
folder rather than a command. The objection to a written index is that it drifts — which is
|
||
answered by checking it rather than by refusing to write one:
|
||
|
||
```
|
||
python3 00-META/checks/index.py --write regenerate
|
||
python3 00-META/checks/index.py fail if stale
|
||
```
|
||
|
||
<!-- index:start -->
|
||
|
||
### What the mesh is
|
||
|
||
- **0001** — [The mesh brokers capabilities; nodes host; agents think](0001-mesh-brokers-nodes-host-agents-think.md)
|
||
- **0002** — [Nodes communicate over a message broker, not over HTTP](0002-nodes-communicate-over-a-broker.md)
|
||
- **0003** — [An agent is a persistent employee, not an instance of a pool](0003-agents-are-persistent-employees.md)
|
||
|
||
### Its tiers, from the bottom up
|
||
|
||
- **0004** — [A node, and how it joins](0004-a-node-and-how-it-joins.md)
|
||
- **0005** — [The node host](0005-the-node-host.md)
|
||
- **0006** — [The substrate and the control plane](0006-the-substrate-and-the-control-plane.md)
|
||
- **0007** — [Connectivity](0007-connectivity.md)
|
||
- **0008** — [A context owns its store, exclusively](0008-a-context-owns-its-store.md)
|
||
- **0028** — [The substrate supplies the control plane and nothing else](0028-the-substrate-supplies-the-control-plane-and-nothing-else.md)
|
||
- **0029** — [A network is a shape, because an action cannot be undone](0029-a-network-is-a-shape-because-an-action-cannot-be-undone.md)
|
||
- **0030** — [Data outlives the mesh that declared it](0030-data-outlives-the-mesh-that-declared-it.md)
|
||
- **0031** — [The control plane authenticates nobody, so identity is a module](0031-the-control-plane-authenticates-nobody.md)
|
||
- **0033** — [The substrate is a store and a broker](0033-the-substrate-is-a-store-and-a-broker.md)
|
||
- **0036** — [Bootstrap ends at a usable mesh, and the first credential comes from a person](0036-bootstrap-ends-at-a-usable-mesh.md)
|
||
|
||
### What runs on them, and how it gets there
|
||
|
||
- **0009** — [Modules and the graph](0009-modules-and-the-graph.md)
|
||
- **0010** — [Delivery](0010-delivery.md)
|
||
- **0024** — [Model access is a provision, and a licence is a thing with a name](0024-model-access-is-a-provision.md)
|
||
- **0026** — [The mesh has a session of its own, and it is the node session's mechanism](0026-the-mesh-has-a-session-of-its-own.md)
|
||
- **0027** — [A provision names what the consumer is coupled to, not the role it plays](0027-a-provision-names-what-the-consumer-is-coupled-to.md)
|
||
- **0035** — [One implementation, several surfaces, and what that costs](0035-one-implementation-several-surfaces.md)
|
||
- **0038** — [The mesh assigns the port, and a module does not care](0038-the-mesh-assigns-the-port.md) *(proposed)*
|
||
- **0040** — [What a module is](0040-what-a-module-is.md)
|
||
- **0041** — [Events are a relationship, the lighter sibling of provisioning](0041-events-are-a-relationship.md)
|
||
- **0042** — [The shape of an event on the wire](0042-the-shape-of-an-event-on-the-wire.md)
|
||
- **0043** — [A module's broker account is scoped by what it emits and consumes](0043-a-module-broker-account-is-scoped-by-emits-and-consumes.md)
|
||
- **0044** — [A public name is provisioned, not registered by hand](0044-a-public-name-is-provisioned-like-any-capability.md)
|
||
- **0045** — [A machine's firewall is the sum of what its modules listen on](0045-a-machine-firewall-is-the-sum-of-what-it-listens-on.md)
|
||
- **0046** — [A module's configuration is its assignment's, not its manifest's](0046-a-module-configuration-is-its-assignments-not-its-manifest.md)
|
||
- **0047** — [A module runs its code as its own process, with its own account](0047-a-module-runs-its-code-as-its-own-process-with-its-own-account.md)
|
||
- **0048** — [A provider creates the credential the mesh minted, and seals nothing](0048-a-provider-creates-the-credential-the-mesh-minted.md)
|
||
- **0049** — [A consumer's identity is bounded by the tightest backend that must accept it](0049-a-consumers-identity-fits-the-tightest-backend.md)
|
||
- **0050** — [Model access is vendor-agnostic, and a vendor is an adapter](0050-model-access-is-vendor-agnostic.md)
|
||
|
||
### How it is built
|
||
|
||
- **0011** — [Managed files are generated onto nodes and never edited there](0011-managed-files-are-generated-never-edited.md)
|
||
- **0012** — [The mesh creates no symlinks — a derived file is a copy](0012-the-mesh-creates-no-symlinks.md)
|
||
- **0013** — [Schema and state changes are numbered migrations, in the same language as the code](0013-schema-changes-are-numbered-migrations.md)
|
||
- **0014** — [No workspace — each module is a standalone package consuming published dependencies](0014-no-npm-workspace.md)
|
||
- **0015** — [Applications live in their own repository; the monorepo is for the mesh](0015-applications-live-in-their-own-repository.md)
|
||
- **0016** — [The lab](0016-the-lab.md)
|
||
- **0037** — [Where a module lives](0037-where-a-module-lives.md) *(proposed)*
|
||
- **0039** — [What the SDK holds, and what it refuses](0039-what-the-sdk-holds-and-refuses.md)
|
||
|
||
### How it is checked
|
||
|
||
- **0017** — [A test defends a decision](0017-a-test-defends-a-decision.md)
|
||
- **0018** — [A picture of a system is read from the system, never from what asked for it](0018-a-picture-is-read-from-what-runs.md)
|
||
|
||
### How we work
|
||
|
||
- **0019** — [How this repository works](0019-how-this-repository-works.md)
|
||
- **0020** — [The mesh is governed by a constitution, injected where work is decided](0020-the-mesh-is-governed-by-a-constitution.md)
|
||
- **0021** — [HQ is the source of the mesh constitution](0021-hq-is-the-source-of-the-constitution.md)
|
||
- **0022** — [The constitution absorbs what is already enforced](0022-the-constitution-absorbs-what-is-enforced.md)
|
||
- **0023** — [The approval is the checkpoint, not the second pair of hands](0023-approval-is-the-checkpoint.md)
|
||
- **0025** — [The design record is read where it is written, never copied to be found](0025-the-design-record-is-read-not-copied.md)
|
||
- **0032** — [The local account owns the mesh; a surface delegates to a module](0032-the-local-account-owns-the-mesh.md) *(superseded)*
|
||
- **0034** — [The local account owns the mesh, and a web application's login is not that](0034-the-local-account-owns-the-mesh.md)
|
||
|
||
<!-- index:end -->
|