Files
ThothII/backend/test/installation-external-probes.test.ts
T

44 lines
2.2 KiB
TypeScript

import { createServer } from "node:http";
import { mkdtempSync, writeFileSync, rmSync } from "node:fs";
import { tmpdir } from "node:os";
import { join } from "node:path";
import { expect, it } from "vitest";
import { probeBootstrapDependencies } from "../src/catalog/bootstrap-probes.js";
import { probePublicEvidenceUrl } from "../src/catalog/evidence-probe-http.js";
it("refuses loopback literals and DNS answers before sending an Evidence GET", async () => {
for (const hostname of ["[::1]", "127.0.0.1", "localhost", "[::ffff:127.0.0.1]"]) {
await expect(probePublicEvidenceUrl(new URL(`http://${hostname}/private`))).rejects.toThrow("Evidence network policy refused");
}
});
it("authenticates a bounded read-only REST probe and blocks unavailable credentials/services", async () => {
const directory = mkdtempSync(join(tmpdir(), "tht-probe-"));
const secret = join(directory, "key");
writeFileSync(secret, "PRIVATE_SENTINEL", { mode: 0o600 });
let status = 200;
const requests: string[] = [];
const server = createServer((req, res) => {
requests.push(`${req.method} ${req.url}`);
res.writeHead(req.headers.authorization === "Bearer PRIVATE_SENTINEL" ? status : 401);
res.end("PRIVATE_SERVER_RESPONSE");
});
await new Promise<void>((resolve) => server.listen(0, "127.0.0.1", resolve));
const address = server.address() as { port: number };
const document = { schemaVersion: 1, databases: [{ workspaceId: "demo", engine: "postgres", databaseName: "demo", schema: "public", binding: { transport: "rest_api", baseUrl: `http://127.0.0.1:${address.port}`, restPath: "/health", restAuth: "bearer" }, secretFiles: { apiKey: secret } }] };
try {
expect((await probeBootstrapDependencies(document)).ok).toBe(true);
status = 503;
const failed = await probeBootstrapDependencies(document);
expect(failed.ok).toBe(false);
expect(JSON.stringify(failed)).not.toContain("PRIVATE");
status = 200;
writeFileSync(secret, "rotated-but-invalid");
expect((await probeBootstrapDependencies(document)).ok).toBe(false);
expect(requests).toEqual(["GET /health", "GET /health", "GET /health"]);
} finally {
await new Promise<void>((resolve) => server.close(() => resolve()));
rmSync(directory, { recursive: true });
}
});