Issue 172: the ssh client block matches one spelling of a machine's name
Reported by the operator: ssh by the bare name logs in, by the mesh name is refused. The predecessor's generator writes the bare name only; the mesh's ssh-client roster already matches both and is not yet shipped.
This commit is contained in:
@@ -0,0 +1,55 @@
|
|||||||
|
---
|
||||||
|
status: located
|
||||||
|
opened: 2026-09-30
|
||||||
|
located-in:
|
||||||
|
- the predecessor's terminal module (still generating the operator's ssh client blocks on every workstation)
|
||||||
|
- mesh-controller internal/catalogue (the ssh-client roster, tested and not yet a catalogue module)
|
||||||
|
fixed-by:
|
||||||
|
amended-design:
|
||||||
|
---
|
||||||
|
|
||||||
|
# 172 — The ssh client block for a machine matches one spelling of its name, and the other gets the wrong user
|
||||||
|
|
||||||
|
## What was observed
|
||||||
|
|
||||||
|
On a workstation, 2026-09-30, reported by the operator. `ssh home-server` logs in; `ssh
|
||||||
|
home-server.internal` is refused with `Permission denied (publickey)`. The operator expected the
|
||||||
|
opposite, if either: the full mesh name is the one the resolver serves.
|
||||||
|
|
||||||
|
The name is not the fault. Both spellings resolve to the machine's private address — the mesh's roster
|
||||||
|
region in the hosts file carries `<node>.internal <node>` on one line, and the resolver answers
|
||||||
|
anything under the node's name. What differs is the login: the generated client configuration has a
|
||||||
|
`Host home-server` block naming the account to log in as, and `home-server.internal` matches no block,
|
||||||
|
so ssh falls back to the operator's local username, which has no account on that machine. Spelled
|
||||||
|
`account@home-server.internal` it works.
|
||||||
|
|
||||||
|
The file is the predecessor's. `~/.ssh/config.d/mesh` says in its own header that it is generated by
|
||||||
|
the predecessor's terminal module, which only ever wrote the bare name. The mesh's own ssh-client
|
||||||
|
roster — every other machine's Host block, written as a marked region of the operator's `~/.ssh/config`
|
||||||
|
with the account the mesh knows for that machine (to-be 29) — already matches both spellings, and a
|
||||||
|
controller test holds `Host marge marge.internal`. It is composed and tested in the controller and is
|
||||||
|
not a module in the catalogue, so no machine receives it; every workstation still runs the
|
||||||
|
predecessor's generator.
|
||||||
|
|
||||||
|
## Why it matters beyond this instance
|
||||||
|
|
||||||
|
**A name the mesh serves and a name a person can use are not the same set**, and the difference is
|
||||||
|
silent. The resolver, the hosts file and the certificate authority all treat `<node>.internal` as the
|
||||||
|
machine's name; the one file that decides who you log in as does not know it. A person who learns the
|
||||||
|
mesh's name from `status` or from a certificate and types it is refused with an error that says
|
||||||
|
nothing about a missing Host block.
|
||||||
|
|
||||||
|
**It is the migration story for the operator's own tooling, arriving as a symptom.** The mesh has the
|
||||||
|
right file and does not ship it. Until the ssh-client roster is a module and is assigned to the
|
||||||
|
workstations, the predecessor's generator keeps writing a file the mesh has already superseded, and
|
||||||
|
every such file is one the mesh cannot correct.
|
||||||
|
|
||||||
|
## Open questions
|
||||||
|
|
||||||
|
- Should the ssh-client roster become a catalogue module now, assigned to every workstation, and take
|
||||||
|
the predecessor's `config.d/mesh` out of the operator's `Include`? Its content is settled; what is
|
||||||
|
not is the takeover of a file in a person's home that another generator still writes.
|
||||||
|
- Should the block match a third spelling — the machine's public name, where it has one — or is that
|
||||||
|
a different key and a different account?
|
||||||
|
- What checks it? A controller test holds the two spellings; nothing checks that the file a workstation
|
||||||
|
actually has is the mesh's rather than the predecessor's.
|
||||||
Reference in New Issue
Block a user