No container is given the mesh's names; it resolves them
novox/hq ADR 0148, step 3. Every container got the whole roster as --add-host entries at creation and nothing re-read them (issues 109, 135); once the roster was in the digest so that could be caught, one name moving anywhere replaced every container in the mesh (issue 151). A container resolves through its machine's resolver, which the resolver module tells the runtime about once per machine. A module's own hosts entries stay exactly as declared. Also brings the resolver tests up to the catalogue as it now is: the runtime is reloaded (never restarted) and given live-restore, and the resolver answers by address, not by interface (issue 110).
This commit is contained in:
@@ -48,7 +48,7 @@ func TestTheResolverForwardsToFixedUpstreamsAndNeverReadsResolvConf(t *testing.T
|
||||
}
|
||||
for _, want := range []string{
|
||||
"\nno-resolv\n", "\nserver=1.1.1.1\n", "\nserver=8.8.8.8\n",
|
||||
"\nlisten-address=127.0.0.1\n", "\ninterface=mesh0\n", "\nbind-dynamic\n",
|
||||
"\nlisten-address=127.0.0.1\n", "\nlisten-address=${machine:address}\n", "\nbind-dynamic\n",
|
||||
"\ndomain-needed\n", "\nbogus-priv\n",
|
||||
"\nconf-file=" + m.Facts["node-zones"].Path + "\n",
|
||||
} {
|
||||
@@ -56,6 +56,14 @@ func TestTheResolverForwardsToFixedUpstreamsAndNeverReadsResolvConf(t *testing.T
|
||||
t.Errorf("the resolver's configuration lacks %q:\n%s", strings.TrimSpace(want), config)
|
||||
}
|
||||
}
|
||||
// By address and never by interface: dnsmasq admits a query by the interface it arrives on
|
||||
// when told one, and a container's query to the private address arrives on the runtime's
|
||||
// bridge — `interface=mesh0` dropped every such query, silently (novox/hq issue 110).
|
||||
for _, line := range strings.Split(config, "\n") {
|
||||
if strings.HasPrefix(line, "interface=") {
|
||||
t.Errorf("the resolver answers by interface, so a container's query on a bridge is dropped: %s", line)
|
||||
}
|
||||
}
|
||||
// Not .53 or .54, which systemd-resolved holds; and not .55 any more, which was a convention
|
||||
// beside the one every machine already followed — the predecessor's resolv.conf says .1.
|
||||
for _, taken := range []string{"127.0.0.53", "127.0.0.54", "127.0.0.55"} {
|
||||
@@ -137,23 +145,39 @@ func TestTheResolverAndWhatAsksItComposeOnOneMachine(t *testing.T) {
|
||||
t.Errorf("the daemon does not restart on its configuration and the machines file both: %v", service["restart-on"])
|
||||
}
|
||||
|
||||
// The runtime's own file, written into (novox/hq ADR 0102) with the one key this module states.
|
||||
// The runtime's own file, written into (novox/hq ADR 0102) with the keys this module states:
|
||||
// where containers resolve, and that a restart keeps them running — because the runtime reads
|
||||
// `dns` only when it starts, and the one restart that needs is the operator's (issue 110).
|
||||
runtime := ids["dnsmasq.runtime-dns"]
|
||||
if runtime == nil || runtime["path"] != "/etc/docker/daemon.json" || runtime["into"] != "json" {
|
||||
t.Fatalf("the runtime's dns is not written into its file: %v", runtime)
|
||||
}
|
||||
var keys map[string][]string
|
||||
var keys map[string]any
|
||||
if err := json.Unmarshal([]byte(runtime["content"].(string)), &keys); err != nil {
|
||||
t.Fatalf("the runtime's keys are not JSON: %v", err)
|
||||
}
|
||||
if len(keys) != 1 || len(keys["dns"]) != 1 || keys["dns"][0] != "10.42.0.1" {
|
||||
t.Errorf("the runtime is pointed at %v; containers resolve at this machine's own private-network address, and nothing else is written", keys)
|
||||
dns, _ := keys["dns"].([]any)
|
||||
if len(keys) != 2 || len(dns) != 1 || dns[0] != "10.42.0.1" || keys["live-restore"] != true {
|
||||
t.Errorf("the runtime is given %v; containers resolve at this machine's own private-network address, a restart keeps them, and nothing else is written", keys)
|
||||
}
|
||||
// The runtime is reloaded when that file changes, and never restarted: a restart stops every
|
||||
// container on the machine (ADR 0102), and a reload is what turns live-restore on.
|
||||
var reloaded bool
|
||||
for _, r := range out {
|
||||
if r["type"] == "service" && r["unit"] == "docker.service" && r["id"] != "" &&
|
||||
strings.HasPrefix(r["id"].(string), "dnsmasq.") {
|
||||
t.Errorf("the resolver orders the runtime restarted or reloaded, which stops every container (ADR 0102) or does nothing for dns: %v", r)
|
||||
if r["type"] != "service" || r["unit"] != "docker.service" {
|
||||
continue
|
||||
}
|
||||
if _, restarts := r["restart-on"]; restarts {
|
||||
t.Errorf("the resolver orders the runtime restarted, which stops every container (ADR 0102): %v", r)
|
||||
}
|
||||
for _, on := range asStrings(r["reload-on"]) {
|
||||
if on == "dnsmasq.runtime-dns" {
|
||||
reloaded = true
|
||||
}
|
||||
}
|
||||
}
|
||||
if !reloaded {
|
||||
t.Errorf("the runtime is not reloaded when its file changes, so live-restore never takes effect")
|
||||
}
|
||||
|
||||
resolv := ids["resolv-conf.resolv"]
|
||||
|
||||
Reference in New Issue
Block a user