import crypto from "node:crypto"; import fs from "node:fs"; import path from "node:path"; import { fileURLToPath } from "node:url"; const repoRoot = path.resolve(path.dirname(fileURLToPath(import.meta.url)), "../.."); const inventoryPath = path.join(repoRoot, "tests/golden/M12-05A/format-inventory.json"); const outputArgument = process.argv.indexOf("--output"); const outputPath = outputArgument === -1 ? path.join(repoRoot, "tests/golden/M12-05B/capability-matrix.json") : path.resolve(process.argv[outputArgument + 1] ?? ""); if (!outputPath) throw new Error("--output requires a file"); const inventoryBytes = fs.readFileSync(inventoryPath); const inventory = JSON.parse(inventoryBytes); const runtimeInventorySha256 = crypto.createHash("sha256").update(inventoryBytes).digest("hex"); const formatOrder = ["GLTF", "GLB", "OBJ", "STL", "PLY", "USD", "ALEMBIC"]; const blocked = (code = "IO_FORMAT_UNSUPPORTED") => ({ status: "BLOCKED", execution: "NONE", code }); const feature = (status, evidence) => ({ status, evidence }); const operation = (format, name) => { const glbExport = format === "GLB" && name === "EXPORT"; const bounded = glbExport ? feature("PARTIAL", "bounded GLB export gate exists; full format round-trip remains M12-06") : feature("UNVERIFIED", "no verified Web executor for this format/operation"); return { local: glbExport ? { status: "READY", execution: "LOCAL", code: null } : blocked(), server: blocked(), geometry: bounded, material: bounded, animation: bounded, }; }; const byFormat = new Map(inventory.formats.map((entry) => [entry.format, entry])); const formats = formatOrder.map((format) => { const runtime = byFormat.get(format); if (!runtime) throw new Error(`inventory is missing ${format}`); return { format, runtimeImportStatus: runtime.import.runtimeStatus === "AVAILABLE" ? "AVAILABLE" : "OPERATOR_UNREGISTERED", runtimeExportStatus: runtime.export.runtimeStatus === "AVAILABLE" ? "AVAILABLE" : "OPERATOR_UNREGISTERED", operations: { IMPORT: operation(format, "IMPORT"), EXPORT: operation(format, "EXPORT") }, }; }); const matrix = { schemaVersion: 1, task: "M12-05B", runtimeInventorySha256, formats }; fs.mkdirSync(path.dirname(outputPath), { recursive: true }); fs.writeFileSync(outputPath, `${JSON.stringify(matrix, null, 2)}\n`); process.stdout.write(`io-format-capability-matrix-generated formats=${formats.length} output=${outputPath}\n`);