refactor(confidence-engine): extract focused deconstruction seam

This commit is contained in:
2026-10-06 17:06:44 +01:00
parent 8e3f4388d6
commit 9362c78f81
3 changed files with 209 additions and 46 deletions
@@ -1,9 +1,5 @@
import { getProvider, getProviderModelName } from "@/lib/llm/provider";
import {
buildFocusedDeconstructPrompt,
focusedDeconstructJsonSchema,
validateFocusedDeconstructSchema,
} from "@/lib/graph/focused-investigation";
import { focusedDeconstruct } from "@/lib/graph/focused-investigation";
import { withAuthenticatedApi } from "@/lib/supabase/api-auth.js";
async function post(request) {
@@ -67,14 +63,6 @@ async function post(request) {
}
}
const prompt = buildFocusedDeconstructPrompt({
targetLabel: body.targetLabel,
targetDescription: body.targetDescription,
centralStatement: body.centralStatement,
question: body.question,
answer: body.answer,
});
const provider = getProvider();
const modelName = getProviderModelName();
startedAt = Date.now();
@@ -84,36 +72,21 @@ async function post(request) {
providerMode: process.env.CONFIDENCE_ENGINE_EXPERIMENT_PROVIDER ?? "ollama",
startedAt,
});
const wrapper = await provider.generateReconstruction(
prompt,
const result = await focusedDeconstruct({
provider,
modelName,
focusedDeconstructJsonSchema,
);
targetNodeId,
targetLabel: body.targetLabel,
targetDescription: body.targetDescription,
centralStatement: body.centralStatement,
question: body.question,
answer: body.answer,
});
const elapsedMs = Date.now() - startedAt;
// Unwrap the semantic deconstruction from the provider envelope.
const deconstruction = wrapper.response;
console.info("[api/focused-investigation/deconstruct] provider success", {
targetNodeId,
elapsedMs,
providerApiPath: wrapper.providerApiPath ?? null,
responsePresent: Boolean(deconstruction),
responseKeys: deconstruction && typeof deconstruction === "object"
? Object.keys(deconstruction)
: [],
});
// Validate schema (required fields present, no graph-mutation fields)
const validationErrors = validateFocusedDeconstructSchema(deconstruction);
console.info("[api/focused-investigation/deconstruct] validation", {
targetNodeId,
schemaValid: validationErrors.length === 0,
responseKeys: deconstruction && typeof deconstruction === "object"
? Object.keys(deconstruction)
: [],
validationErrors,
});
if (validationErrors.length > 0) {
if (!result.success) {
console.info("[api/focused-investigation/deconstruct] end", {
targetNodeId,
status: 502,
@@ -123,7 +96,7 @@ async function post(request) {
{
success: false,
error: "Focused deconstruction result did not match expected schema",
validationErrors,
validationErrors: result.errors,
targetNodeId: body.targetNodeId,
elapsedMs,
},
@@ -134,11 +107,11 @@ async function post(request) {
const response = Response.json({
success: true,
targetNodeId: body.targetNodeId,
observations: deconstruction.observations,
uncertainties: deconstruction.uncertainties,
assumptions: deconstruction.assumptions,
relationships: deconstruction.relationships,
possibleFollowUpQuestions: deconstruction.possibleFollowUpQuestions,
observations: result.observations,
uncertainties: result.uncertainties,
assumptions: result.assumptions,
relationships: result.relationships,
possibleFollowUpQuestions: result.possibleFollowUpQuestions,
elapsedMs,
});
console.info("[api/focused-investigation/deconstruct] end", {