mirror of
https://github.com/morluto/rea.git
synced 2026-10-22 13:52:32 -05:00
Keep explicitly selected Node Inspector targets observable when discovery cannot verify their file location. Resolve literal POSIX discovery paths without URI decoding, and retain lossy Windows or underscore paths as unresolved metadata. Validate scriptParsed file URLs independently. Preserve unknown target identity through runtime reconciliation, regenerate contracts, and verify real CLI/MCP behavior on Linux and Windows. Closes #530 Assisted-by: Kogasa (gensokyo-skills:kogasa-surprise-testing)
85 lines
3.2 KiB
TypeScript
85 lines
3.2 KiB
TypeScript
import { rm, writeFile } from "node:fs/promises";
|
|
import { join } from "node:path";
|
|
import { pathToFileURL } from "node:url";
|
|
|
|
import { expect, test } from "vitest";
|
|
|
|
import { analyzeJavaScriptApplication } from "../../../src/application/JavaScriptApplicationService.js";
|
|
import { createJavaScriptRuntimeObservationEvidence } from "../../../src/application/JavaScriptRuntimeObservationEvidence.js";
|
|
import { V8InspectorProvider } from "../../../src/browser/V8InspectorProvider.js";
|
|
import { reconcileJavaScriptRuntime } from "../../../src/domain/javascriptRuntimeReconciliation.js";
|
|
import { startFakeV8Inspector } from "../../fixtures/fakeV8Inspector.js";
|
|
import { createTestTempDirectory } from "../../fixtures/temporaryDirectory.js";
|
|
|
|
test("keeps unresolved target identity unknown while matching verified loaded scripts", async () => {
|
|
const root = await createTestTempDirectory("rea-unresolved-runtime-");
|
|
const entry = join(root, "entry.js");
|
|
const reportedUrl = "file://C:_tools_entry.js";
|
|
const fake = await startFakeV8Inspector({
|
|
targetUrl: reportedUrl,
|
|
scriptUrls: [pathToFileURL(entry).href],
|
|
});
|
|
try {
|
|
await writeFile(entry, "export const fixture = true;\n");
|
|
const analysis = await analyzeJavaScriptApplication({ input_path: root });
|
|
expect(analysis.ok).toBe(true);
|
|
if (!analysis.ok) throw analysis.error;
|
|
const provider = new V8InspectorProvider();
|
|
const input = {
|
|
inspector_endpoint: fake.endpoint,
|
|
target_id: fake.targetId,
|
|
observation_ms: 10,
|
|
};
|
|
const observed = await provider.observe(input);
|
|
expect(observed.ok).toBe(true);
|
|
if (!observed.ok) throw observed.error;
|
|
const evidence = createJavaScriptRuntimeObservationEvidence(
|
|
"observe_javascript_runtime",
|
|
input,
|
|
observed.value,
|
|
provider.identity(),
|
|
);
|
|
const result = reconcileJavaScriptRuntime({
|
|
static_layers: [{ role: "application", analysis: analysis.value }],
|
|
runtime_observations: [evidence],
|
|
});
|
|
expect(result.reconciliations).toEqual(
|
|
expect.arrayContaining([
|
|
expect.objectContaining({
|
|
entity_kind: "target",
|
|
status: "unknown",
|
|
basis: "none",
|
|
confidence: "unknown",
|
|
reason: "runtime-location-unresolved",
|
|
candidate_static_count: 0,
|
|
}),
|
|
expect.objectContaining({
|
|
entity_kind: "script",
|
|
status: "matched",
|
|
basis: "artifact-path",
|
|
}),
|
|
]),
|
|
);
|
|
expect(result.runtime_captures[0]?.target_location).toEqual({
|
|
kind: "unresolved",
|
|
reported_url: reportedUrl,
|
|
reason: "unverifiable-file-location",
|
|
});
|
|
const target = result.graph.nodes.find(({ kind }) => kind === "target");
|
|
expect(target?.observations[0]?.properties).toMatchObject({
|
|
reported_url: reportedUrl,
|
|
location_kind: "unresolved",
|
|
});
|
|
expect(target?.observations[0]?.properties).not.toHaveProperty("location");
|
|
expect(
|
|
result.graph.edges.filter(
|
|
({ relation, source_node_id }) =>
|
|
relation === "observed_as" && source_node_id === target?.node_id,
|
|
),
|
|
).toEqual([]);
|
|
} finally {
|
|
await fake.close();
|
|
await rm(root, { recursive: true, force: true });
|
|
}
|
|
});
|