Reconcile with hq 128: hosts template is the region form, node-names is shared
The merge commit took only the staged index; these reconciliation edits sat unstaged in the working tree. Integrate the template mechanism with #79's region write (hq 128): RosterFile gains Shared, FactsInto sets into:block for a shared fact, /etc/hosts becomes the region form (no floor) and node-names is marked shared. Without this the merge would have regressed /etc/hosts back to a whole-file write, replacing the operator's own lines.
This commit is contained in:
@@ -161,21 +161,17 @@ func (g *Generator) Nodes() []Node { return g.nodes }
|
||||
// Graph is the peer list per node, for showing.
|
||||
func (g *Generator) Graph() Graph { return g.graph }
|
||||
|
||||
// hostsTemplate is the `/etc/hosts` the network module asks the mesh to write — every machine's
|
||||
// mesh name at its private address, so a service binding the name it was given stays reachable from
|
||||
// everywhere else. It is a roster template like any module's (catalogue.RosterFile): the mesh owns
|
||||
// the data, this owns the format.
|
||||
// hostsTemplate is the mesh's region of `/etc/hosts` — every machine's mesh name at its private
|
||||
// address, written into a marked region and merged (RosterFile.Shared → `into: block`), so the rest
|
||||
// of the file (localhost, the machine's own name, other tools' blocks) is kept byte for byte
|
||||
// (novox/hq issue 128). It is a roster template like any module's: the mesh owns the data, this owns
|
||||
// the format, and the control plane holds no formatter.
|
||||
//
|
||||
// - The loopback floor stays, or things with nothing to do with the mesh break.
|
||||
// - `127.0.1.1 <node>` only when there is a node, the ordinary Debian self-name line.
|
||||
// - No floor: no header, no localhost, no `127.0.1.1` — those are the machine's, above the region.
|
||||
// - A machine's own line is marked, and its mesh name resolves to its mesh address, not loopback.
|
||||
// - `.Names` is every name the mesh serves (issue 111), so a container reaching a routed name
|
||||
// finds the machine serving it; machines with no address yet are already left out of the set.
|
||||
const hostsTemplate = "# Generated by the mesh. Do not edit — this file is replaced whenever a machine\n" +
|
||||
"# joins or leaves, and an edit would survive until then and vanish.\n\n" +
|
||||
"127.0.0.1\tlocalhost\n" +
|
||||
"::1\t\tlocalhost ip6-localhost ip6-loopback\n" +
|
||||
"{{if .Node}}127.0.1.1\t{{.Node}}\n{{end}}\n" +
|
||||
const hostsTemplate = "# The mesh's names. This region is replaced whenever a machine joins or leaves.\n" +
|
||||
"{{range .Names}}{{.Address}}\t{{.FQDN}}\t{{.Name}}{{if eq .Name $.Node}}\t# this machine{{end}}\n{{end}}"
|
||||
|
||||
// Manifest is the module the mesh provides for itself.
|
||||
@@ -194,9 +190,10 @@ func Manifest() map[string]any {
|
||||
// mesh knows which machines exist and where; writing that into a hosts file is not a thing
|
||||
// that needs a module to run nowhere. The format is a template like any other roster fact —
|
||||
// the mesh's own module owns the `/etc/hosts` layout the way dnsmasq owns its zones, and the
|
||||
// control plane holds no formatter (see catalogue.RosterFile).
|
||||
// control plane holds no formatter (see catalogue.RosterFile). `shared`: the mesh owns only
|
||||
// its region of the file and keeps the rest (novox/hq issue 128).
|
||||
"facts": map[string]any{
|
||||
"node-names": map[string]any{"path": "/etc/hosts", "template": hostsTemplate},
|
||||
"node-names": map[string]any{"path": "/etc/hosts", "template": hostsTemplate, "shared": true},
|
||||
},
|
||||
"claims": []map[string]any{{"name": TheNetwork, "scope": "node"}},
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user