Comments naming records that no longer exist now point at the consolidated record holding their reasoning -- the four lab records are 0016, a test defends a decision is 0017.
89 lines
4.2 KiB
TypeScript
89 lines
4.2 KiB
TypeScript
/**
|
|
* The lab, placing tier 0 inside a machine it raised.
|
|
*
|
|
* This is the seam that ends the lab being infrastructure with no consumer
|
|
* (novox/hq 03-DESIGN/00-as-is/11-the-lab.md). It needs a built host binary; without one it
|
|
* skips with a reason rather than passing having checked nothing.
|
|
*/
|
|
|
|
import { test, after } from "node:test";
|
|
import assert from "node:assert/strict";
|
|
import { existsSync } from "node:fs";
|
|
import { loadScenario } from "../../src/declaration/parse.ts";
|
|
import { raise } from "../../src/lifecycle/raise.ts";
|
|
import { destroy, exec } from "../../src/lifecycle/operate.ts";
|
|
import { hostBinaryPath, HOST_PATH } from "../../src/lifecycle/place.ts";
|
|
import { labIsUsable, destroyAll } from "./harness.ts";
|
|
|
|
const capability = await labIsUsable();
|
|
const binary = hostBinaryPath();
|
|
|
|
const skip = !capability.usable
|
|
? `lab not usable: ${capability.why}`
|
|
: !binary
|
|
? "MESH_LAB_HOST_BINARY is not set — build novox/mesh-host and point at it"
|
|
: !existsSync(binary)
|
|
? `MESH_LAB_HOST_BINARY points at ${binary}, which does not exist`
|
|
: false;
|
|
|
|
let instanceId = "";
|
|
|
|
after(async () => {
|
|
if (instanceId) await destroy(instanceId);
|
|
await destroyAll("bootstrap-single-");
|
|
}, { timeout: 400_000 });
|
|
|
|
test("a raised machine contains the host", { skip, timeout: 900_000 }, async () => {
|
|
const raised = await raise(loadScenario("scenarios/bootstrap-single.yml"), {});
|
|
instanceId = raised.instanceId;
|
|
|
|
const { stdout } = await exec(instanceId, "anchor", [HOST_PATH, "version"]);
|
|
assert.ok(stdout.trim().length > 0, "the host is on the machine but does not run there");
|
|
});
|
|
|
|
test("the host reports the MACHINE, not the workstation that placed it", { skip, timeout: 120_000 }, async () => {
|
|
// The check that proves detection detects rather than reporting a constant. A raised VM and
|
|
// the workstation differ in every capability, so a host that reported the workstation's
|
|
// answers would be obvious here and invisible anywhere else.
|
|
const { stdout } = await exec(instanceId, "anchor", [HOST_PATH, "profile", "--json"]);
|
|
const profile = JSON.parse(stdout) as {
|
|
capabilities: { name: string; present: boolean; detail: string }[];
|
|
};
|
|
const by = new Map(profile.capabilities.map((c) => [c.name, c]));
|
|
|
|
// A machine raised by the lab is root and has a clean init. The workstation session is
|
|
// neither, so these are the two that would flip if the wrong machine were being read.
|
|
assert.equal(by.get("privileged")?.present, true, "a raised machine should be root");
|
|
assert.equal(by.get("service-manager")?.present, true, "a raised machine should have an init");
|
|
|
|
for (const [name, verdict] of by) {
|
|
assert.ok(verdict.detail.trim().length > 0, `${name} was reported with no reason`);
|
|
}
|
|
});
|
|
|
|
test("ADR 0016 — the host confirms the machine carries no overlay", { skip, timeout: 120_000 }, async () => {
|
|
// The lab provides the underlay and NOTHING of the overlay. Asserted elsewhere by looking
|
|
// for wireguard interfaces; here the placed host reports it independently, which is a
|
|
// second witness rather than the same check twice.
|
|
const { stdout } = await exec(instanceId, "anchor", [HOST_PATH, "profile", "--json"]);
|
|
const profile = JSON.parse(stdout) as { capabilities: { name: string; present: boolean }[] };
|
|
const overlay = profile.capabilities.find((c) => c.name === "overlay");
|
|
|
|
assert.equal(overlay?.present, false, "a freshly raised machine already had an overlay");
|
|
});
|
|
|
|
test("the host's inventory is of the raised machine", { skip, timeout: 120_000 }, async () => {
|
|
const { stdout } = await exec(instanceId, "anchor", [HOST_PATH, "inventory", "--json"]);
|
|
const inv = JSON.parse(stdout) as {
|
|
machine: string; cpus: number; memory_kb: number; observed_at: string; unreadable?: string[];
|
|
};
|
|
|
|
assert.ok(inv.machine.length > 0, "the machine did not report a name");
|
|
assert.ok(inv.cpus > 0 && inv.memory_kb > 0, "the machine reported no cpus or no memory");
|
|
assert.deepEqual(inv.unreadable ?? [], [], "something could not be read on a machine we raised");
|
|
|
|
// The scenario gives each machine 1GiB and 2 cpus. A host reporting the workstation's
|
|
// 24 cpus would pass every check above.
|
|
assert.ok(inv.cpus <= 4, `reported ${inv.cpus} cpus — that is not the raised machine`);
|
|
});
|