mesh-config: read config declarations from each placed module's own manifests on the bus, never from the controller (issue 1953) #558

Merged
mesh-tools merged 2 commits from fix/1953-config-from-builds into main 2026-10-29 19:47:56 +00:00
Member

Why

On novox, de-spiegel has been held since the node began composing its own modules: "nothing sets the required config value praktijk-name". The operator set that value and its three siblings on 2026-10-28 (Approve on Telegram), and mesh-config holds them under set, but nothing under resolved. mesh-config read each module's declarations from the controller's mesh-controller.declared-config and its assignments from mesh-controller.assignments, and silently skipped an assigned module whose declarations that mirror lacked. de-spiegel lives in its own repository and its keys came with novox/de-spiegel #6; the controller's mirror never held them. The hold then spread to mailu and route-proxy, so every site behind route-proxy has stayed down.

The operator, 2026-10-29: "the controller should have never had anything to do with module assignment and configuration"; "the configuration should live on the nats broker"; "no more code in the controller that touches build, delivery and config"; switch at once, no dark phase.

What changes

  • Assignments: read from placement alone (mesh-delivery-assigner.placement, key placement.<node>); the controller's assignments are no longer read.
  • Declarations: each placed module's trunk manifest from the indexer (mesh-delivery-indexer.modules, .manifests), with the manifest of the build its want names (mesh-delivery-assigner.wants, mesh-delivery-builder.builds) laid over it key by key, as the node composer picks manifests. Only config and settings are read. Manifests are cached by digest.
  • A placed module whose manifest cannot be read is listed under unresolved with why (config list), logged, and keeps its last resolved values; it never blocks another module and is never skipped silently.
  • Event-driven: watches placement, wants, the indexer's modules and the predefined list; no timer added.
  • Manifest reads: drop mesh-controller.assignments and mesh-controller.declared-config; add the four bus reads above. README updated.
  • This departs from ADR 0565 §4 (build dark beside the controller's mirrors, switch on a take-over): the operator chose to switch at once; the correction is proposed to the knowledge base.

Quick fix or thorough fix

  • Quick: add de-spiegel to the controller's declared-config mirror. One module, and it keeps the controller on the config path.
  • Thorough, chosen: every module's declarations from its own manifests on the bus, for any repository, and an unreadable one said loudly; the controller leaves the config path.

How it is checked

  • One table-driven test with four cases on de-spiegel's real config replaces three tests of the assignments mirror (38 test functions, was 40; budget 500/50). go build, go vet -tags integration and go test pass.
  • Reviewed live: all 328 resolved values on 89 node/module pairs today are placed and unchanged against their trunk manifests; de-spiegel's four keys resolve on novox.
  • Live after delivery: mesh-config.config {action:list, module:de-spiegel} shows the four keys under resolved; de-spiegel, mailu and route-proxy are no longer held on novox; de-spiegel and link2pay get wants; the sites behind route-proxy answer.

Still reading controller state, not changed here: the predefined list, the hand-act log and pull-request declarations (ADR 0565 §2, §10-11).

Reopened 2026-10-29 as recovery only

The operator said yes (17:56 CET) to this change as a temporary fix so de-spiegel returns today; design 47's config model replaces it. The checker did not take the reopened pull request back as a candidate, so one empty commit (0d71d8b) moves the head; the tree is identical to the reviewed 96a37f58.

Reviewed-by: rev-config@shanks at 96a37f58ca
Reviewed-by: lead-47@shanks at 0d71d8b56c (empty commit on the reviewed tree)

## Why On novox, de-spiegel has been held since the node began composing its own modules: "nothing sets the required config value praktijk-name". The operator set that value and its three siblings on 2026-10-28 (Approve on Telegram), and mesh-config holds them under `set`, but nothing under `resolved`. mesh-config read each module's declarations from the controller's `mesh-controller.declared-config` and its assignments from `mesh-controller.assignments`, and silently skipped an assigned module whose declarations that mirror lacked. de-spiegel lives in its own repository and its keys came with novox/de-spiegel #6; the controller's mirror never held them. The hold then spread to mailu and route-proxy, so every site behind route-proxy has stayed down. The operator, 2026-10-29: "the controller should have never had anything to do with module assignment and configuration"; "the configuration should live on the nats broker"; "no more code in the controller that touches build, delivery and config"; switch at once, no dark phase. ## What changes - Assignments: read from placement alone (`mesh-delivery-assigner.placement`, key `placement.<node>`); the controller's assignments are no longer read. - Declarations: each placed module's trunk manifest from the indexer (`mesh-delivery-indexer.modules`, `.manifests`), with the manifest of the build its want names (`mesh-delivery-assigner.wants`, `mesh-delivery-builder.builds`) laid over it key by key, as the node composer picks manifests. Only `config` and `settings` are read. Manifests are cached by digest. - A placed module whose manifest cannot be read is listed under `unresolved` with why (`config list`), logged, and keeps its last resolved values; it never blocks another module and is never skipped silently. - Event-driven: watches placement, wants, the indexer's modules and the predefined list; no timer added. - Manifest `reads`: drop `mesh-controller.assignments` and `mesh-controller.declared-config`; add the four bus reads above. README updated. - This departs from ADR 0565 §4 (build dark beside the controller's mirrors, switch on a take-over): the operator chose to switch at once; the correction is proposed to the knowledge base. ## Quick fix or thorough fix - Quick: add de-spiegel to the controller's declared-config mirror. One module, and it keeps the controller on the config path. - Thorough, chosen: every module's declarations from its own manifests on the bus, for any repository, and an unreadable one said loudly; the controller leaves the config path. ## How it is checked - One table-driven test with four cases on de-spiegel's real config replaces three tests of the assignments mirror (38 test functions, was 40; budget 500/50). `go build`, `go vet -tags integration` and `go test` pass. - Reviewed live: all 328 resolved values on 89 node/module pairs today are placed and unchanged against their trunk manifests; de-spiegel's four keys resolve on novox. - Live after delivery: `mesh-config.config {action:list, module:de-spiegel}` shows the four keys under `resolved`; de-spiegel, mailu and route-proxy are no longer held on novox; de-spiegel and link2pay get wants; the sites behind route-proxy answer. Still reading controller state, not changed here: the predefined list, the hand-act log and pull-request declarations (ADR 0565 §2, §10-11). ## Reopened 2026-10-29 as recovery only The operator said yes (17:56 CET) to this change as a temporary fix so de-spiegel returns today; design 47's config model replaces it. The checker did not take the reopened pull request back as a candidate, so one empty commit (0d71d8b) moves the head; the tree is identical to the reviewed 96a37f58. Reviewed-by: rev-config@shanks at 96a37f58ca76d5af3f8d1d9de36af52d6e2e7b02 Reviewed-by: lead-47@shanks at 0d71d8b56c55effc73dc813389268794b876a5f4 (empty commit on the reviewed tree)
mesh-tools added 1 commit 2026-10-29 14:29:13 +00:00
mesh-config: read declarations from each placed module's own manifests as built, and placement alone, so a module from its own repository resolves (issue 1953)
mesh/delivery closed: the pull request closed unmerged
mesh/check pass 96a37f58ca76 on 030f9ee4e780 | unit 1173 run, 3272 kept, 13 skipped | integration 1212 run, 3274 kept, 22 skipped | over bound: unit, …
96a37f58ca
The controller's declared-config mirror never held de-spiegel's keys, and Resolve skipped
an assigned module it held no declarations of, silently: de-spiegel stayed held on novox
with its values set. Declarations now come from the indexer's trunk manifest with the
wanted build's laid over it per node; which module runs where from the seat
mesh-placement alone. A placed module with no readable manifest is listed as unresolved
with why, logged, and keeps its last resolved values.
Author
Member

Delivery novox/mesh-catalog@0d71d8b56c55 — merged since 2026-10-29T19:47:59Z

Source — source.main moved to novox/mesh-catalog@96b129e544. Whether it reached the machines is mesh-delivery-view's, derived from source.main, the wants and the haves.

Transitions

  • 2026-10-29 17:10 (new) → proposed (announced): novox/mesh-catalog#558's head announced
  • 2026-10-29 17:10 proposed → ready (accepted): a verdict names this commit and the trunk's head as its trunk commit, the gate passed or warned, and the repository's own check did not fail; or the check gates no merge (check-gates-merge false)
  • 2026-10-29 19:47 ready → merged (merged): on the trunk its modules follow: merged there

The commit's note under refs/notes/mesh-plan keeps every transition of this change up to its merge: git log --notes=mesh-plan.

<!-- mesh-delivery:view --> **Delivery** `novox/mesh-catalog@0d71d8b56c55` — **merged** since 2026-10-29T19:47:59Z **Source** — source.main moved to novox/mesh-catalog@96b129e54441. Whether it reached the machines is `mesh-delivery-view`'s, derived from `source.main`, the wants and the haves. **Transitions** - 2026-10-29 17:10 (new) → proposed (announced): novox/mesh-catalog#558's head announced - 2026-10-29 17:10 proposed → ready (accepted): a verdict names this commit and the trunk's head as its trunk commit, the gate passed or warned, and the repository's own check did not fail; or the check gates no merge (check-gates-merge false) - 2026-10-29 19:47 ready → merged (merged): on the trunk its modules follow: merged there The commit's note under `refs/notes/mesh-plan` keeps every transition of this change up to its merge: `git log --notes=mesh-plan`.
mesh-tools closed this pull request 2026-10-29 14:32:18 +00:00
mesh-tools reopened this pull request 2026-10-29 16:56:34 +00:00
jschoubben added 1 commit 2026-10-29 17:10:30 +00:00
Move the head so the checker takes #558 again: a reopened pull request is not taken back as a candidate (recovery of de-spiegel, operator's yes 2026-10-29 17:56 CET)
mesh/check being carried to 0d71d8b56c55 on 96b129e54441 | from 030f9ee4e780
mesh/delivery merged: source.main moved to novox/mesh-catalog@96b129e54441
0d71d8b56c
mesh-tools merged commit 96b129e544 into main 2026-10-29 19:47:56 +00:00
mesh-tools deleted branch fix/1953-config-from-builds 2026-10-29 19:47:56 +00:00
Sign in to join this conversation.
No Reviewers
2 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: novox/mesh-catalog#558