/** * Deterministic signal-intake stage logic. * * The fast intake path is a fixed funnel, so stages are driven here rather than * by an agent loop: round 1 comes from the precomputed pack, round 2 is one * structured call, round 3 is a deterministic client-side picker, and synthesis * is one structured call. This module owns no I/O. */ import type { BaseLanguageModelInput } from "@langchain/core/language_models/base"; import type { Runnable } from "@langchain/core/runnables"; import { z } from "zod"; import { type IntakePackQuestion } from "./intake.pack.generator.js"; /** One answered intake round. */ export interface IntakeAnswer { selectedOptions: string[]; freeText?: string; } /** One answered intake round, in order (round 1 first). */ export interface IntakeRound { prompt: string; answer: IntakeAnswer; } /** Everything synthesis needs to write the signal. */ export interface SynthesisInput { brief: string; rounds: IntakeRound[]; /** Free-text place/community constraint from the where round. */ whereText?: string; /** * Free-text correction the user typed against a draft they already saw. * Distinct from {@link SynthesisInput.whereText}: feedback rewrites the * signal, it does not constrain where to look. */ feedback?: string; } /** Planning input for one follow-up generation call. */ export interface FollowUpPlanInput { brief: string; /** Answered rounds in order (round 1 first). */ rounds: IntakeRound[]; /** Hard cap on questions returned by THIS call. */ maxFollowUps: number; /** Locked interview plan on continuation calls; echoed unchanged. */ plannedFollowUpCount?: number; } /** The model's follow-up batch plus its total follow-up plan. */ export interface FollowUpPlan { questions: IntakePackQuestion[]; plannedFollowUpCount: number; } /** Synthesized signal text plus its summary fields. */ export interface SynthesisResult { description: string; lookingFor: string; youBring: string; } declare const followUpPlanSchema: z.ZodObject<{ questions: z.ZodArray; title: z.ZodString; prompt: z.ZodString; answerGroundedOptions: z.ZodArray, "many">; multiSelect: z.ZodBoolean; }, "strip", z.ZodTypeAny, { prompt: string; title: string; multiSelect: boolean; missingAxis: "purpose" | "desired_attributes" | "exchange" | "constraint"; answerGroundedOptions: { label: string; description: string; }[]; }, { prompt: string; title: string; multiSelect: boolean; missingAxis: "purpose" | "desired_attributes" | "exchange" | "constraint"; answerGroundedOptions: { label: string; description: string; }[]; }>, "many">; plannedFollowUpCount: z.ZodNumber; }, "strip", z.ZodTypeAny, { questions: { prompt: string; title: string; multiSelect: boolean; missingAxis: "purpose" | "desired_attributes" | "exchange" | "constraint"; answerGroundedOptions: { label: string; description: string; }[]; }[]; plannedFollowUpCount: number; }, { questions: { prompt: string; title: string; multiSelect: boolean; missingAxis: "purpose" | "desired_attributes" | "exchange" | "constraint"; answerGroundedOptions: { label: string; description: string; }[]; }[]; plannedFollowUpCount: number; }>; declare const profileBridgePlanSchema: z.ZodObject<{ bridges: z.ZodArray>; }, "strip", z.ZodTypeAny, { questionIndex: number; profileBridgeOption: { label: string; description: string; } | null; }, { questionIndex: number; profileBridgeOption: { label: string; description: string; } | null; }>, "many">; }, "strip", z.ZodTypeAny, { bridges: { questionIndex: number; profileBridgeOption: { label: string; description: string; } | null; }[]; }, { bridges: { questionIndex: number; profileBridgeOption: { label: string; description: string; } | null; }[]; }>; /** Static round-1 question used only when pack generation fails outright. */ export declare const FALLBACK_WHO_QUESTION: IntakePackQuestion; /** Static round-2 question used when live generation fails. */ export declare const FALLBACK_BRING_QUESTION: IntakePackQuestion; /** * Render an answer as a human-readable label. * * @param answer - Selected options plus optional free text * @returns Comma-joined non-empty parts */ export declare function answerLabel(answer: IntakeAnswer): string; /** Runs the two live stages of the fast intake funnel: follow-up planning and synthesis. */ export declare class SignalIntakeOrchestrator { private readonly plannerModel; private readonly profileBridgeModel; private readonly synthesisModel; /** * @param models - Optional injected structured models. Tests pass stubs. */ constructor(models?: { planner?: Runnable>; profileBridge?: Runnable>; synthesis?: Runnable; }); /** * Plan and write follow-up questions from the brief and answered rounds. * * @param input - Brief, answered rounds, per-call cap, and any locked plan * @returns Up to `maxFollowUps` renderable questions plus the total plan; * the static fallback question with count 1 when generation fails */ generateFollowUps(input: FollowUpPlanInput): Promise; /** * Write the signal from every answered round, any where-constraint, and any * revision feedback. * * @param input - Brief, ordered rounds, optional where constraint, optional feedback * @returns Description plus card summary fields * @throws Propagates model failure so the caller can mark the run failed */ synthesize(input: SynthesisInput): Promise; } export {};