Files
hq/04-ISSUES/129-nothing-makes-a-machine-trust-the-meshs-authority/00-report.md
T
jschoubben 1f72e82b84 Issue 129 is resolved: a workstation trusts the mesh, and stops when told to
Registered ca-trust from the catalogue — it was merged and had never been
registered, which is why "assign it to one machine" had no module to name
— assigned it to the workstation, and verified.

Verified in the form ADR 0147 prescribes, against the authority's own API
so the handshake needs nothing else in the mesh to be right: 200, issuer
Mesh Internal CA, Verify return code 0. Four routed internal names verify
too, and `git ls-remote https://…` works, which is the consequence the
report named.

Removal exercised for the first time. Unassign and push removes the
anchor, empties the trust store of the mesh's authority, and returns the
plain client to the original error; assigning again restores it. That is
the half 0147 claimed and nothing had shown.

One thing it found that is not in the module: removal works only because
the host removes the service before the script. Stopping the unit is what
deletes the certificate and refreshes the bundles, and it needs the script
to still exist. The symmetry rests on an ordering nothing states.

0147's "written, and not yet run" now carries a progressive insight
saying it has run, where, and that it ran on one machine of four.
2026-09-30 02:18:21 +02:00

3.6 KiB

status, opened, located-in, fixed-by
status opened located-in fixed-by
resolved 2026-09-26
mesh-catalog modules/ca-trust
the ca-trust module registered from the catalogue and assigned to a workstation; verified in both directions 2026-09-30 (02-resolution.md)

129 — nothing makes a machine trust the mesh's own certificate authority

What was observed

On an enrolled, adopted workstation — on the private network, resolving the mesh's names through the mesh's resolver — every HTTPS name the mesh serves internally fails verification:

curl https://<a name the mesh routes internally>/
curl: (60) SSL certificate OpenSSL verify result: unable to get local issuer certificate (20)

The route proxy presents a certificate issued by the mesh's internal authority (step-ca, the internal-acme-ca provision). The machine's trust store holds the predecessor's authority and a developer tool's local root, and nothing of the mesh's. No module installs the mesh's root, and no fact carries it: step-ca's only consumers are proxies, which obtain certificates over ACME and never need the root on the machine they run on.

Issue 048 found the same shape for the mesh's registry and resolved it by treating the private network as the transport security (ADR 0082): the runtime pulls in the clear, over the tunnel. That answer does not carry over. A browser, git over HTTPS, a package manager and every TLS client a person or a module uses verify the certificate chain, and there is no "insecure registries" for them — nor should there be.

Consequences today, all silent until someone tries:

  • a person on a workstation cannot open any internal HTTPS name without a warning;
  • git over HTTPS to the mesh's forge fails, so the working clone URL is ssh-only;
  • a module on a non-hub machine that calls another module's internal HTTPS name fails verification unless its image happens to carry the root;
  • the predecessor's authority cannot be retired from any machine while anything there still speaks TLS to a mesh name, because it is the only authority those machines trust.

What would have prevented it

  • A mesh fact carrying the internal authority's root (public material; the controller or the step-ca module is its source), written onto every machine on the private network — the same reasoning that has the private network write the registry trust and the names: being on the network is what makes a machine one that speaks to the mesh's names.
  • A resource that puts it where the machine's TLS clients look — on Arch, /etc/ca-certificates/trust-source/anchors/ — and refreshes the extracted bundles (update-ca-trust). The refresh is the open design question: it is a command, and the link may not carry an action (ADR 0005). A declared one-shot unit, or a host primitive for "trust this anchor", are the obvious candidates.
  • Removal symmetric to arrival: undeclared, the anchor goes and the bundles are refreshed again, so a machine leaving the mesh stops trusting it.

Evidence to carry into diagnosis

  • step-ca module: provides acme-ca / internal-acme-ca, listens on 9000 for proxies; no resource writes its root anywhere but its own state directory.
  • The private network's generator writes /etc/hosts and the registry trust, and nothing about certificates.
  • On the workstation, the trust anchors present are the predecessor's authority and a local development root; trust list shows no entry for the mesh.