184 lines
5.8 KiB
TypeScript
184 lines
5.8 KiB
TypeScript
import type { UnifiedRetrievalResult } from "../types/assistant";
|
|
import type { AssistantExecutionPlanItem } from "./assistantQueryPlanning";
|
|
import { normalizeRetrievalResult } from "./retrievalResultNormalizer";
|
|
|
|
export interface AssistantLiveTemporalHint {
|
|
as_of_date: string | null;
|
|
period_from: string | null;
|
|
period_to: string | null;
|
|
source: string | null;
|
|
}
|
|
|
|
export interface AssistantRetrievalCallRecord {
|
|
fragment_id: string;
|
|
requirement_ids: string[];
|
|
route: string;
|
|
status: "skipped" | "executed" | "failed";
|
|
query_text: string;
|
|
reason: string | null;
|
|
}
|
|
|
|
export type AssistantRetrievalScalar = string | number | boolean | null;
|
|
export type AssistantRetrievalFieldValue =
|
|
| AssistantRetrievalScalar
|
|
| AssistantRetrievalFieldValue[]
|
|
| { [key: string]: AssistantRetrievalFieldValue };
|
|
export type AssistantRetrievalRecord = Record<string, AssistantRetrievalFieldValue>;
|
|
|
|
export interface AssistantRetrievalRawResultLike {
|
|
status: "ok" | "empty" | "partial" | "error";
|
|
result_type: "list" | "summary" | "object" | "chain" | "ranking";
|
|
items: AssistantRetrievalRecord[];
|
|
summary: AssistantRetrievalRecord;
|
|
evidence: AssistantRetrievalRecord[];
|
|
why_included: string[];
|
|
selection_reason: string[];
|
|
risk_factors: string[];
|
|
business_interpretation: string[];
|
|
confidence: "high" | "medium" | "low";
|
|
limitations: string[];
|
|
errors: string[];
|
|
}
|
|
|
|
export type AssistantRetrievalRawListItem = AssistantRetrievalFieldValue;
|
|
export type AssistantRetrievalRawList = AssistantRetrievalFieldValue[];
|
|
|
|
export type AssistantRetrievalRawResult =
|
|
| AssistantRetrievalRawResultLike
|
|
| AssistantRetrievalRawList
|
|
| string
|
|
| number
|
|
| boolean
|
|
| null;
|
|
|
|
export interface AssistantRetrievalRawResultRecord {
|
|
fragment_id: string;
|
|
route: string;
|
|
raw_result: AssistantRetrievalRawResult;
|
|
}
|
|
|
|
export interface AssistantDeepTurnRetrievalExecutionInput {
|
|
executionPlan: AssistantExecutionPlanItem[];
|
|
liveTemporalHint: AssistantLiveTemporalHint | null;
|
|
executeRouteRuntime: (
|
|
route: string,
|
|
fragmentText: string,
|
|
options: {
|
|
temporalHint: AssistantLiveTemporalHint | null;
|
|
}
|
|
) => Promise<AssistantRetrievalRawResult>;
|
|
mapNoRouteReason: (reason: string | null) => string;
|
|
buildSkippedResult: (item: AssistantExecutionPlanItem) => UnifiedRetrievalResult;
|
|
normalizeRetrievalResultFn?: typeof normalizeRetrievalResult;
|
|
}
|
|
|
|
export interface AssistantDeepTurnRetrievalExecutionOutput {
|
|
retrievalCalls: AssistantRetrievalCallRecord[];
|
|
retrievalResultsRaw: AssistantRetrievalRawResultRecord[];
|
|
retrievalResults: UnifiedRetrievalResult[];
|
|
}
|
|
|
|
function buildRouteExecutorErrorRawResult(route: string, message: string): AssistantRetrievalRawResult {
|
|
return {
|
|
status: "error",
|
|
result_type: "summary",
|
|
items: [],
|
|
summary: {
|
|
route
|
|
},
|
|
evidence: [],
|
|
why_included: [],
|
|
selection_reason: [],
|
|
risk_factors: [],
|
|
business_interpretation: [],
|
|
confidence: "low",
|
|
limitations: ["Route executor failed."],
|
|
errors: [message]
|
|
};
|
|
}
|
|
|
|
function normalizeRawResult(
|
|
value: AssistantRetrievalRawResult | object | null | undefined
|
|
): AssistantRetrievalRawResult {
|
|
if (value === null || value === undefined) {
|
|
return null;
|
|
}
|
|
if (typeof value === "string" || typeof value === "number" || typeof value === "boolean") {
|
|
return value;
|
|
}
|
|
if (Array.isArray(value)) {
|
|
return value as AssistantRetrievalRawList;
|
|
}
|
|
if (typeof value === "object") {
|
|
return value as AssistantRetrievalRawResultLike;
|
|
}
|
|
return null;
|
|
}
|
|
|
|
export async function executeAssistantDeepTurnRetrievalPlan(
|
|
input: AssistantDeepTurnRetrievalExecutionInput
|
|
): Promise<AssistantDeepTurnRetrievalExecutionOutput> {
|
|
const normalizeRetrievalResultSafe = input.normalizeRetrievalResultFn ?? normalizeRetrievalResult;
|
|
const retrievalCalls: AssistantRetrievalCallRecord[] = [];
|
|
const retrievalResultsRaw: AssistantRetrievalRawResultRecord[] = [];
|
|
const retrievalResults: UnifiedRetrievalResult[] = [];
|
|
|
|
for (const planItem of input.executionPlan) {
|
|
if (!planItem.should_execute) {
|
|
retrievalCalls.push({
|
|
fragment_id: planItem.fragment_id,
|
|
requirement_ids: planItem.requirement_ids,
|
|
route: planItem.route,
|
|
status: "skipped",
|
|
query_text: planItem.fragment_text,
|
|
reason: input.mapNoRouteReason(planItem.no_route_reason)
|
|
});
|
|
retrievalResults.push(input.buildSkippedResult(planItem));
|
|
continue;
|
|
}
|
|
|
|
retrievalCalls.push({
|
|
fragment_id: planItem.fragment_id,
|
|
requirement_ids: planItem.requirement_ids,
|
|
route: planItem.route,
|
|
status: "executed",
|
|
query_text: planItem.fragment_text,
|
|
reason: null
|
|
});
|
|
|
|
try {
|
|
const raw = await input.executeRouteRuntime(planItem.route, planItem.fragment_text, {
|
|
temporalHint: input.liveTemporalHint
|
|
});
|
|
const normalizedRaw = normalizeRawResult(raw);
|
|
retrievalResultsRaw.push({
|
|
fragment_id: planItem.fragment_id,
|
|
route: planItem.route,
|
|
raw_result: normalizedRaw
|
|
});
|
|
retrievalResults.push(
|
|
normalizeRetrievalResultSafe(planItem.fragment_id, planItem.requirement_ids, planItem.route, normalizedRaw)
|
|
);
|
|
} catch (error) {
|
|
const message = error instanceof Error ? error.message : String(error);
|
|
retrievalCalls[retrievalCalls.length - 1].status = "failed";
|
|
retrievalCalls[retrievalCalls.length - 1].reason = message;
|
|
const rawError = buildRouteExecutorErrorRawResult(planItem.route, message);
|
|
retrievalResultsRaw.push({
|
|
fragment_id: planItem.fragment_id,
|
|
route: planItem.route,
|
|
raw_result: rawError
|
|
});
|
|
retrievalResults.push(
|
|
normalizeRetrievalResultSafe(planItem.fragment_id, planItem.requirement_ids, planItem.route, rawError)
|
|
);
|
|
}
|
|
}
|
|
|
|
return {
|
|
retrievalCalls,
|
|
retrievalResultsRaw,
|
|
retrievalResults
|
|
};
|
|
}
|