Unify trunk on main: initialization → main #3

Merged
jschoubben merged 95 commits from initialization into main 2026-09-05 01:13:46 +00:00
Showing only changes of commit 4726a51986 - Show all commits
+47 -9
View File
@@ -816,17 +816,14 @@ test("rotating a credential moves both ends, and the old one stops working", {
// As the role the provisioner made, into the database it made. The provisioner names a role
// after the machine and a database after what the module asked for — which is the contract, and
// getting it wrong here made the test fail against a provisioner that had done its job.
// By address, resolved on the machine itself. A container does not inherit its host's
// /etc/hosts, so a name the mesh wrote there resolves for the machine and not for anything it
// runs — which fails as "could not translate host name" and reads like a mesh that never wrote
// the name.
const where = (await must("laptop",
`getent hosts anchor.internal | head -1 | cut -d' ' -f1`)).trim();
assert.match(where, /^[0-9.]+$/, `the mesh's name for anchor does not resolve here: ${where}`);
// **By name, from inside the container.** This used to resolve the address on the machine and
// pass it in, because a container does not inherit its host's /etc/hosts and the name failed as
// "could not translate host name" — which reads like a mesh that never wrote the name. The mesh
// now gives every container the names it knows, so the workaround is gone and its absence is
// the assertion.
const login = async (password: string) =>
await on("laptop", `docker run --rm -e PGPASSWORD=${quote(password)} ` +
`${pinned("postgres")} psql -h ${where} -p 5433 -U mesh_laptop ` +
`${pinned("postgres")} psql -h anchor.internal -p 5433 -U mesh_laptop ` +
`-d realapp -qAt -c "select 1"`, 120_000);
const diagnostics = async () =>
@@ -1257,3 +1254,44 @@ test("the hub can be filtered without severing the mesh", {
await mesh("unassign laptop stillworks");
await mesh("push");
});
test("a container reaches another machine by the name the mesh gave it", {
skip, timeout: 900_000,
}, async () => {
// Internal names are written to the machine's hosts file, which serves the machine and not what
// the machine runs: a container gets its own hosts file holding only its own hostname. So every
// name the mesh wrote was invisible to the majority of things that need one.
//
// Checked from inside a container rather than on the machine, because on the machine it has
// always worked — and that is exactly what made this easy to miss.
await must("anchor", `printf %s '{"module":"resolves","version":"1",` +
`"capabilities":["container-runtime"],` +
`"resources":[{"id":"idle","type":"container","name":"resolves",` +
`"image":"${pinned("registry")}"}]}' > /tmp/resolves.json`);
await must("anchor", `docker cp /tmp/resolves.json mesh-control:/resolves.json`);
await mesh("module add /resolves.json");
await mesh("assign laptop resolves");
await mesh("push laptop");
await new Promise((r) => setTimeout(r, 15_000));
// The names are in the container's own hosts file, written by the runtime.
const inside = await must("laptop", `docker exec resolves cat /etc/hosts`);
assert.match(inside, /anchor\.internal/,
`the container cannot see the other machine's name:\n${inside}`);
assert.match(inside, /laptop\.internal/,
`the container cannot see its own machine's name:\n${inside}`);
// And the name actually reaches the machine, which is the part that matters: a hosts entry
// pointing at the wrong address resolves perfectly and connects to nothing.
const reached = await on("laptop",
`docker exec resolves sh -c 'getent hosts anchor.internal'`);
assert.ok(reached.ok, `the name does not resolve inside the container:\n${reached.out}`);
const address = reached.out.trim().split(/\s+/)[0];
const onTheMachine = (await must("laptop",
`getent hosts anchor.internal | head -1 | cut -d' ' -f1`)).trim();
assert.equal(address, onTheMachine,
"the container and its machine disagree about where the other machine is");
await mesh("unassign laptop resolves");
await mesh("push laptop");
});