Issue 178: a routed name resolves to a provider merely told it, and flips between plans (fixed, controller PR 181)

This commit is contained in:
2026-10-01 02:04:55 +02:00
parent cf8134e318
commit e1f2c6bd5b
@@ -0,0 +1,59 @@
---
status: resolved
opened: 2026-10-01
located-in: [mesh-controller cmd/mesh-controller/plan.go (routeNamesInTheMesh), mesh-controller internal/catalogue (NamesServed)]
fixed-by: mesh-controller PR 181 (every node's resolution read first, names attributed across them to the terminus, in order; the many shape of contributions counted)
amended-design:
---
# 178 — A routed name resolves to a provider that was merely told it, and flips between plans
## What was observed
From the home server, the dashboard's public name resolved inside the mesh to the control node, where
no proxy serves it, and TLS failed; from outside it resolved to the home server and worked. Filed
first in the forge's tracker on the hq repository (its issue 227), on 2026-09-30. The same night,
two plans of the same machine taken a minute apart differed in exactly one resource — the mesh's
names region — with the dashboard's name on one node's address and then on the other's.
A second thing hid behind it: no module that is routed under several names — the photo service's
six, the invoicing service's two, the mail server's five — had any of them in the names region at
all.
## Why this is here
The names region is composed from every contribution the mesh gave a name to. A consumer that is
routed contributes its label to its route, and the proxy serves the composed name. A consumer that
also uses an identity provider contributes the same label there, because the provider must know the
consumer's public name to compose a redirect — and by the rule that two readers must agree
([issue 122](../122-a-module-cannot-ask-for-its-own-public-name/00-report.md)) it is
given the same composed name. So one name reaches two providers, and the code attributed it to the
node of whichever contribution a map yielded last. Map order is not stable between runs; the region
was not either.
The second fault is older: the single-value reading of a module's contributions is deliberately
empty when the module contributes several times to one requirement
([ADR 0094](../../02-DECISIONS/0094-a-module-may-hold-several-secrets-from-one-provider.md)'s
sibling), and the names region used that reading, so a module with several routes named none.
## Resolved, 2026-10-01
Every node's resolution is read first, and the names are attributed across them at once. **The
terminus serves the name**: among the providers a name reaches, the one that is not itself published
under a labelled name through another provider. An identity provider is routed through the proxy and
so is a consumer of names, not their end; the proxy contributes no label to anyone and is. The rule
knows nothing of what "route" means — it reads the graph the modules declared — and it walks nodes,
requirements and contributions in order, so one mesh yields one region. Every shape of contribution
is counted, so a module routed under several names has every one of them resolved.
*How it is checked:* the two-node mesh of the report, resolved and attributed twenty-five times — the
dashboard's name on the home server, the identity provider's own name on the control node, no name
leaked to the identity provider; a module with two routes yields two names; and, live, two plans of
the home server after the roll-out identical in the names region, with the dashboard's name at the
home server's address and the several-routed modules' names present.
## Note on where this was filed
The symptom was filed in the forge's issue tracker, which is not where hq's issues live: a tracker
issue carries no status the mesh's records read, and its numbers collide with hq's pull request
numbers in conversation. It is closed there pointing here.