feat(confidence-engine): preserve initial reconstruction relationships

This commit is contained in:
2026-09-05 11:53:58 +01:00
parent 13fbceee7a
commit 7472b6ecb0
7 changed files with 485 additions and 23 deletions
+42 -9
View File
@@ -22,6 +22,12 @@ export function buildInitialGraph(analysisData) {
}
const nodeMap = new Map(); // label -> node
const sourceIdToNodeId = new Map();
function mapSourceId(sourceId, node) {
if (sourceId) sourceIdToNodeId.set(sourceId, node.id);
return node;
}
// ── Helper: register or get a node by label ────────────
@@ -97,14 +103,17 @@ export function buildInitialGraph(analysisData) {
obs.confidence || "medium",
);
if (obs.id) node.evidenceIds.push(obs.id);
if (obs.id) {
node.evidenceIds.push(obs.id);
mapSourceId(obs.id, node);
}
}
}
// Actors as states/nodes
if (reconstruction.actors) {
for (const actor of reconstruction.actors) {
ensureNode(
mapSourceId(actor.id, ensureNode(
actor.description || actor.label,
"observation",
"supported",
@@ -112,13 +121,13 @@ export function buildInitialGraph(analysisData) {
null,
null,
actor.confidence || "medium",
);
));
}
}
if (reconstruction.systemsOrObjects) {
for (const sys of reconstruction.systemsOrObjects) {
ensureNode(
mapSourceId(sys.id, ensureNode(
sys.description || sys.label,
"metric",
"known",
@@ -126,7 +135,7 @@ export function buildInitialGraph(analysisData) {
null,
null,
sys.confidence || "medium",
);
));
}
}
@@ -142,6 +151,7 @@ export function buildInitialGraph(analysisData) {
null,
diff.confidence || "medium",
);
mapSourceId(diff.id, node);
}
}
@@ -157,6 +167,7 @@ export function buildInitialGraph(analysisData) {
null,
c.confidence || "medium",
);
mapSourceId(c.id, node);
}
}
@@ -173,6 +184,7 @@ export function buildInitialGraph(analysisData) {
null,
unk.confidence || "low",
);
mapSourceId(unk.id, node);
unknownNodes.push(node);
}
}
@@ -180,7 +192,7 @@ export function buildInitialGraph(analysisData) {
// Plausible interpretations
if (reconstruction.plausibleInterpretations) {
for (const interp of reconstruction.plausibleInterpretations) {
ensureNode(
mapSourceId(interp.id, ensureNode(
interp.description || interp.label,
"assumption",
"provisional",
@@ -188,14 +200,14 @@ export function buildInitialGraph(analysisData) {
null,
null,
interp.confidence || "low",
);
));
}
}
// Known transitions
if (reconstruction.knownTransitions) {
for (const trans of reconstruction.knownTransitions) {
ensureNode(
mapSourceId(trans.id, ensureNode(
`${trans.entity}: ${trans.previousState}${trans.currentState}`,
"transition",
trans.explanationStatus === "confirmed" ? "known" : "provisional",
@@ -204,7 +216,7 @@ export function buildInitialGraph(analysisData) {
null,
null,
trans.confidence || "medium",
);
));
}
}
@@ -247,6 +259,27 @@ export function buildInitialGraph(analysisData) {
}
}
const edgeIds = new Set(edges.map((edge) => edge.id));
for (const relationship of reconstruction.relationships ?? []) {
const fromNodeId = sourceIdToNodeId.get(relationship.fromId);
const toNodeId = sourceIdToNodeId.get(relationship.toId);
const id = `e-rel-${relationship.id}`;
if (!fromNodeId || !toNodeId || edgeIds.has(id)) continue;
edges.push(
situationEdgeSchema.parse({
id,
fromNodeId,
toNodeId,
relationship: relationship.relationship,
confidence: relationship.confidence,
description: relationship.description,
}),
);
edgeIds.add(id);
}
return { nodes: nodeArr, edges };
}