import { describe, expect, test } from 'bun:test'; import { generateSharedInfraYaml } from './docker-compose-generator'; /** * Shared infrastructure must be self-contained. * * Shared infra starts BEFORE any per-test stack exists, so a shared service * that names a per-test address gets no answer at all until a test comes up. * That is celilo#1365: the celilo.computer simulator resolved ACME through * comcast-resolver (203.0.113.1, per-test) and Pebble validated challenges * through the same address, so Caddy could not obtain a cert during * shared-infra bringup. The bake then probed https://celilo.computer within * 30s, got whatever Caddy serves without an ACME cert, and failed TLS * verification — "unable to get local issuer certificate", which reads as a * CA-trust bug rather than a startup-order one. * * The check is derived, not hand-listed: every address shared infra POINTS AT * for name resolution must belong to a service shared infra itself defines. */ describe('shared infra is self-contained', () => { const yaml = generateSharedInfraYaml(); const compose = Bun.YAML.parse(yaml) as { services: Record< string, { dns?: string[]; command?: string; networks?: Record } >; }; const ownAddresses = new Set( Object.values(compose.services).flatMap((svc) => Object.values(svc.networks ?? {}) .map((n) => n.ipv4_address) .filter((ip): ip is string => Boolean(ip)), ), ); // Every resolver a shared service is pointed at, as {who, address}. const resolverRefs = Object.entries(compose.services).flatMap(([name, svc]) => { const refs = (svc.dns ?? []).map((ip) => ({ name, field: 'dns', ip })); const dnsserver = /-dnsserver\s+(\d+\.\d+\.\d+\.\d+):/.exec(svc.command ?? ''); if (dnsserver) refs.push({ name, field: '-dnsserver', ip: dnsserver[1] }); return refs; }); test('the generator actually emits resolver references to check', () => { expect(resolverRefs.length).toBeGreaterThan(0); }); test('no shared service resolves through an address shared infra does not own', () => { const foreign = resolverRefs.filter((ref) => !ownAddresses.has(ref.ip)); expect(foreign.map((r) => `${r.name}.${r.field} -> ${r.ip}`)).toEqual([]); }); });