102 lines
5.8 KiB
JavaScript
102 lines
5.8 KiB
JavaScript
import assert from "node:assert/strict";
|
|
import { Worker } from "node:worker_threads";
|
|
import { generateMap } from "../src/mapPipeline.js";
|
|
import { createWorldMap } from "../src/worldMap.js";
|
|
import { buildMaximumProductionLasso, derivePatchSeed } from "./production-fixtures.mjs";
|
|
|
|
const worldSeed = 114514;
|
|
const candidateVariant = 0;
|
|
|
|
const initial = generateMap(worldSeed);
|
|
const world = createWorldMap(initial);
|
|
const rect = buildMaximumProductionLasso(world);
|
|
|
|
const terrainType = initial.terrainTemplate?.terrainType || initial.terrainDebug?.terrainType || "auto";
|
|
const seed = derivePatchSeed(world.seed, terrainType, candidateVariant);
|
|
const candidatePlan = [{ candidateId: `r11-selection-native:${candidateVariant}`, candidateOrdinal: 1, variant: candidateVariant, seed }];
|
|
const worker = new Worker(new URL("./browser-worker-node-shim.mjs", import.meta.url), { type: "module" });
|
|
const timeoutMs = 90_000;
|
|
|
|
const result = await new Promise((resolve, reject) => {
|
|
const timer = setTimeout(() => reject(new Error(`r11 selection-native worker timed out after ${timeoutMs} ms`)), timeoutMs);
|
|
worker.on("message", (message) => {
|
|
if (message.id !== 1 || message.type === "progress") return;
|
|
clearTimeout(timer);
|
|
if (!message.ok) reject(new Error(message.error || message.code || "r11 worker failed"));
|
|
else resolve(message.result);
|
|
});
|
|
worker.on("error", (error) => {
|
|
clearTimeout(timer);
|
|
reject(error);
|
|
});
|
|
worker.postMessage({
|
|
id: 1,
|
|
world,
|
|
rect,
|
|
options: {
|
|
patchMode: "expansion",
|
|
terrainType,
|
|
variant: candidateVariant,
|
|
seed,
|
|
maxQualityRetries: 0,
|
|
qualityTerrainAttempts: 1,
|
|
acceptBestAvailableQuality: false,
|
|
includeSeamVisualization: false,
|
|
},
|
|
search: {
|
|
searchId: "r11-selection-native-production",
|
|
operationId: "r11-selection-native-production",
|
|
committedRevision: 1,
|
|
workerEpoch: 1,
|
|
executionAttempt: 1,
|
|
totalCandidateCount: 1,
|
|
candidatePlan,
|
|
},
|
|
});
|
|
});
|
|
|
|
try {
|
|
assert.equal(result?.ok, true, "candidate must complete successfully");
|
|
assert.equal(result?.searchStatus, "succeeded", "candidate search must succeed");
|
|
assert.equal(result?.selectionNativeProduction, true, "large Expansion must report selection-native production");
|
|
assert.equal(result?.patchGenerationMode, "selection-native-chunked-production-v1", "large Expansion must expose r11 generation mode");
|
|
assert.equal(result?.candidateQuality?.hardPass, true, "aggregate production quality gate must pass");
|
|
assert.equal(result?.candidateQuality?.finalMerge?.hardPass, true, "final merged production quality must pass");
|
|
assert.equal(result?.candidateQuality?.finalMerge?.transportHierarchyPass, true, "transport hierarchy Oracle must pass");
|
|
assert.equal(result?.candidateQuality?.finalMerge?.transportTopology?.hardPass, true, "transport topology/service quality must pass");
|
|
assert.equal(result?.candidateQuality?.finalMerge?.prefectureCoherence?.hardPass, true, "prefecture regional coherence quality must pass");
|
|
assert.equal(result?.seamDiagnostics?.hardPass, true, "whole-selection seam audit must pass");
|
|
|
|
const nativeTransport = result?.seamDiagnostics?.aggregateTransportRepair?.selectionNativeTransport;
|
|
assert.equal(nativeTransport?.policy, "whole-selection-post-admin-transport-v2-coherent-graph", "r11 whole-selection transport finalizer must be authoritative");
|
|
assert.equal(nativeTransport?.chunkPostAdminTransportDeferred, true, "private chunks must defer duplicate post-admin transport finalization");
|
|
assert.equal(nativeTransport?.fullResolutionRouting, true, "published transport must use full-resolution routing");
|
|
assert.ok((nativeTransport?.roadGraphRepair?.roadGraphAfterComponents || 0) <= (nativeTransport?.roadGraphRepair?.roadGraphBeforeComponents || 0), "whole-selection road graph repair must not increase fragmentation");
|
|
assert.ok((nativeTransport?.railGraphRepair?.railGraphAfterComponents || 0) <= (nativeTransport?.railGraphRepair?.railGraphBeforeComponents || 0), "whole-selection rail graph repair must not increase fragmentation");
|
|
for (const classDebug of Object.values(nativeTransport?.regionalTrunkTransport?.byClass || {})) {
|
|
if (!classDebug?.demand) continue;
|
|
assert.equal(classDebug.mandatoryServiceConnected, classDebug.mandatoryServiceNodes, "every mandatory major-city/capital trunk service must be connected");
|
|
if (classDebug.classGraph?.roadGraphBeforeComponents != null) assert.ok(classDebug.classGraph.roadGraphAfterComponents <= classDebug.classGraph.roadGraphBeforeComponents, "road hierarchy graph must not become more fragmented");
|
|
if (classDebug.classGraph?.railGraphBeforeComponents != null) assert.ok(classDebug.classGraph.railGraphAfterComponents <= classDebug.classGraph.railGraphBeforeComponents, "rail hierarchy graph must not become more fragmented");
|
|
}
|
|
|
|
const classes = result?.candidateQuality?.finalMerge?.transportClasses || {};
|
|
const requirements = result?.candidateQuality?.finalMerge?.transportRequirements || {};
|
|
for (const key of ["national", "expressway", "railTrunk"]) {
|
|
if (!requirements[key]?.demand) continue;
|
|
assert.ok((classes[key]?.cells || 0) >= (requirements[key]?.minCells || 0), `${key} routed-coverage floor must be met`);
|
|
assert.ok((classes[key]?.paths || 0) > 0, `${key} must still contain at least one production corridor when demanded`);
|
|
}
|
|
|
|
console.log(JSON.stringify({
|
|
ok: true,
|
|
patchGenerationMode: result.patchGenerationMode,
|
|
selectionNativePolicy: result.selectionNativePolicy,
|
|
finalScore: result.candidateQuality.finalMerge.score,
|
|
transportClasses: result.candidateQuality.finalMerge.transportClasses,
|
|
transportRequirements: result.candidateQuality.finalMerge.transportRequirements,
|
|
selectionNativeTransport: nativeTransport,
|
|
}, null, 2));
|
|
} finally {
|
|
await worker.terminate();
|
|
}
|