@illuma-ai/agents 1.1.15 → 1.1.16

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (64) hide show
  1. package/dist/cjs/common/enum.cjs +13 -13
  2. package/dist/cjs/common/enum.cjs.map +1 -1
  3. package/dist/cjs/graphs/MultiAgentGraph.cjs +146 -150
  4. package/dist/cjs/graphs/MultiAgentGraph.cjs.map +1 -1
  5. package/dist/cjs/main.cjs +2 -2
  6. package/dist/cjs/types/graph.cjs.map +1 -1
  7. package/dist/esm/common/enum.mjs +12 -12
  8. package/dist/esm/common/enum.mjs.map +1 -1
  9. package/dist/esm/graphs/MultiAgentGraph.mjs +147 -151
  10. package/dist/esm/graphs/MultiAgentGraph.mjs.map +1 -1
  11. package/dist/esm/main.mjs +1 -1
  12. package/dist/esm/types/graph.mjs.map +1 -1
  13. package/dist/types/common/enum.d.ts +11 -11
  14. package/dist/types/graphs/MultiAgentGraph.d.ts +38 -36
  15. package/dist/types/types/graph.d.ts +13 -7
  16. package/package.json +1 -1
  17. package/src/common/__tests__/enum.test.ts +14 -6
  18. package/src/common/enum.ts +11 -11
  19. package/src/graphs/MultiAgentGraph.ts +148 -152
  20. package/src/graphs/__tests__/multi-agent-delegate.test.ts +44 -44
  21. package/src/graphs/__tests__/multi-agent-edges.test.ts +83 -85
  22. package/src/scripts/multi-agent-chain.js +1 -1
  23. package/src/scripts/multi-agent-chain.ts +1 -1
  24. package/src/scripts/multi-agent-document-review-chain.js +1 -1
  25. package/src/scripts/multi-agent-document-review-chain.ts +1 -1
  26. package/src/scripts/multi-agent-hybrid-flow.js +3 -3
  27. package/src/scripts/multi-agent-hybrid-flow.ts +3 -3
  28. package/src/scripts/multi-agent-parallel.js +2 -2
  29. package/src/scripts/multi-agent-parallel.ts +2 -2
  30. package/src/scripts/multi-agent-sequence.js +2 -2
  31. package/src/scripts/multi-agent-sequence.ts +2 -2
  32. package/src/scripts/multi-agent-supervisor.js +5 -5
  33. package/src/scripts/multi-agent-supervisor.ts +5 -5
  34. package/src/scripts/poc-multi-agent-comprehensive.ts +7 -7
  35. package/src/scripts/sequential-full-metadata-test.js +1 -1
  36. package/src/scripts/sequential-full-metadata-test.ts +1 -1
  37. package/src/scripts/test-custom-prompt-key.js +3 -3
  38. package/src/scripts/test-custom-prompt-key.ts +3 -3
  39. package/src/scripts/test-handoff-input.js +1 -1
  40. package/src/scripts/test-handoff-input.ts +1 -1
  41. package/src/scripts/test-handoff-preamble.js +1 -1
  42. package/src/scripts/test-handoff-preamble.ts +1 -1
  43. package/src/scripts/test-handoff-steering.js +3 -3
  44. package/src/scripts/test-handoff-steering.ts +3 -3
  45. package/src/scripts/test-multi-agent-list-handoff.js +1 -1
  46. package/src/scripts/test-multi-agent-list-handoff.ts +1 -1
  47. package/src/scripts/test-parallel-agent-labeling.js +2 -2
  48. package/src/scripts/test-parallel-agent-labeling.ts +2 -2
  49. package/src/scripts/test-parallel-handoffs.js +2 -2
  50. package/src/scripts/test-parallel-handoffs.ts +2 -2
  51. package/src/scripts/test-thinking-handoff-bedrock.js +1 -1
  52. package/src/scripts/test-thinking-handoff-bedrock.ts +1 -1
  53. package/src/scripts/test-thinking-handoff.js +1 -1
  54. package/src/scripts/test-thinking-handoff.ts +1 -1
  55. package/src/scripts/test-thinking-to-thinking-handoff-bedrock.js +1 -1
  56. package/src/scripts/test-thinking-to-thinking-handoff-bedrock.ts +1 -1
  57. package/src/scripts/test-tool-before-handoff-role-order.js +1 -1
  58. package/src/scripts/test-tool-before-handoff-role-order.ts +1 -1
  59. package/src/scripts/test-tools-before-handoff.js +1 -1
  60. package/src/scripts/test-tools-before-handoff.ts +1 -1
  61. package/src/specs/agent-handoffs-bedrock.integration.test.ts +6 -6
  62. package/src/specs/agent-handoffs.test.ts +35 -35
  63. package/src/specs/thinking-handoff.test.ts +9 -9
  64. package/src/types/graph.ts +13 -7
@@ -1 +1 @@
1
- {"version":3,"file":"graph.mjs","sources":["../../../src/types/graph.ts"],"sourcesContent":["// src/types/graph.ts\nimport type {\n START,\n StateType,\n UpdateType,\n StateGraph,\n StateGraphArgs,\n StateDefinition,\n CompiledStateGraph,\n BinaryOperatorAggregate,\n} from '@langchain/langgraph';\nimport type { BindToolsInput } from '@langchain/core/language_models/chat_models';\nimport type {\n BaseMessage,\n AIMessageChunk,\n SystemMessage,\n} from '@langchain/core/messages';\nimport type { RunnableConfig, Runnable } from '@langchain/core/runnables';\nimport type { ChatGenerationChunk } from '@langchain/core/outputs';\nimport type { GoogleAIToolType } from '@langchain/google-common';\nimport type {\n ToolMap,\n ToolEndEvent,\n GenericTool,\n LCTool,\n ToolApprovalConfig,\n} from '@/types/tools';\nimport type { Providers, Callback, GraphNodeKeys } from '@/common';\nimport type { StandardGraph, MultiAgentGraph } from '@/graphs';\nimport type { ClientOptions } from '@/types/llm';\nimport type {\n RunStep,\n RunStepDeltaEvent,\n MessageDeltaEvent,\n ReasoningDeltaEvent,\n} from '@/types/stream';\nimport type { TokenCounter } from '@/types/run';\n\n/** Interface for bound model with stream and invoke methods */\nexport interface ChatModel {\n stream?: (\n messages: BaseMessage[],\n config?: RunnableConfig\n ) => Promise<AsyncIterable<AIMessageChunk>>;\n invoke: (\n messages: BaseMessage[],\n config?: RunnableConfig\n ) => Promise<AIMessageChunk>;\n}\n\nexport type GraphNode = GraphNodeKeys | typeof START;\nexport type ClientCallback<T extends unknown[]> = (\n graph: StandardGraph,\n ...args: T\n) => void;\n\nexport type ClientCallbacks = {\n [Callback.TOOL_ERROR]?: ClientCallback<[Error, string]>;\n [Callback.TOOL_START]?: ClientCallback<unknown[]>;\n [Callback.TOOL_END]?: ClientCallback<unknown[]>;\n};\n\nexport type SystemCallbacks = {\n [K in keyof ClientCallbacks]: ClientCallbacks[K] extends ClientCallback<\n infer Args\n >\n ? (...args: Args) => void\n : never;\n};\n\nexport type BaseGraphState = {\n messages: BaseMessage[];\n /**\n * Structured response when using structured output mode.\n * Contains the validated JSON response conforming to the configured schema.\n */\n structuredResponse?: Record<string, unknown>;\n};\n\nexport type MultiAgentGraphState = BaseGraphState & {\n agentMessages?: BaseMessage[];\n};\n\nexport type IState = BaseGraphState;\n\nexport interface EventHandler {\n handle(\n event: string,\n data:\n | StreamEventData\n | ModelEndData\n | RunStep\n | RunStepDeltaEvent\n | MessageDeltaEvent\n | ReasoningDeltaEvent\n | { result: ToolEndEvent },\n metadata?: Record<string, unknown>,\n graph?: StandardGraph | MultiAgentGraph\n ): void | Promise<void>;\n}\n\nexport type GraphStateChannels<T extends BaseGraphState> =\n StateGraphArgs<T>['channels'];\n\nexport type Workflow<\n T extends BaseGraphState = BaseGraphState,\n U extends Partial<T> = Partial<T>,\n N extends string = string,\n> = StateGraph<T, U, N>;\n\nexport type CompiledWorkflow<\n T extends BaseGraphState = BaseGraphState,\n U extends Partial<T> = Partial<T>,\n N extends string = string,\n> = CompiledStateGraph<T, U, N>;\n\nexport type CompiledStateWorkflow = CompiledStateGraph<\n StateType<{\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n }>,\n UpdateType<{\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n }>,\n string,\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n StateDefinition\n>;\n\nexport type CompiledMultiAgentWorkflow = CompiledStateGraph<\n StateType<{\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n agentMessages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n }>,\n UpdateType<{\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n agentMessages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n }>,\n string,\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n agentMessages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n agentMessages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n StateDefinition\n>;\n\nexport type CompiledAgentWorfklow = CompiledStateGraph<\n {\n messages: BaseMessage[];\n },\n {\n messages?: BaseMessage[] | undefined;\n },\n '__start__' | `agent=${string}` | `tools=${string}`,\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n StateDefinition,\n {\n [x: `agent=${string}`]: Partial<BaseGraphState>;\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n [x: `tools=${string}`]: any;\n }\n>;\n\nexport type SystemRunnable =\n | Runnable<\n BaseMessage[],\n (BaseMessage | SystemMessage)[],\n RunnableConfig<Record<string, unknown>>\n >\n | undefined;\n\n/**\n * Optional compile options passed to workflow.compile().\n * These are intentionally untyped to avoid coupling to library internals.\n */\nexport type CompileOptions = {\n // A checkpointer instance (e.g., MemorySaver, SQL saver)\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n checkpointer?: any;\n interruptBefore?: string[];\n interruptAfter?: string[];\n /**\n * Human-in-the-loop tool approval configuration.\n * When set, tools matching the policy will trigger an interrupt()\n * before execution, pausing the graph for human approval.\n * Requires a checkpointer to be set for interrupt/resume to work.\n */\n toolApprovalConfig?: ToolApprovalConfig;\n};\n\nexport type EventStreamCallbackHandlerInput =\n Parameters<CompiledWorkflow['streamEvents']>[2] extends Omit<\n infer T,\n 'autoClose'\n >\n ? T\n : never;\n\nexport type StreamChunk =\n | (ChatGenerationChunk & {\n message: AIMessageChunk;\n })\n | AIMessageChunk;\n\n/**\n * Data associated with a StreamEvent.\n */\nexport type StreamEventData = {\n /**\n * The input passed to the runnable that generated the event.\n * Inputs will sometimes be available at the *START* of the runnable, and\n * sometimes at the *END* of the runnable.\n * If a runnable is able to stream its inputs, then its input by definition\n * won't be known until the *END* of the runnable when it has finished streaming\n * its inputs.\n */\n input?: unknown;\n /**\n * The output of the runnable that generated the event.\n * Outputs will only be available at the *END* of the runnable.\n * For most runnables, this field can be inferred from the `chunk` field,\n * though there might be some exceptions for special cased runnables (e.g., like\n * chat models), which may return more information.\n */\n output?: unknown;\n /**\n * A streaming chunk from the output that generated the event.\n * chunks support addition in general, and adding them up should result\n * in the output of the runnable that generated the event.\n */\n chunk?: StreamChunk;\n /**\n * Runnable config for invoking other runnables within handlers.\n */\n config?: RunnableConfig;\n /**\n * Custom result from the runnable that generated the event.\n */\n result?: unknown;\n /**\n * Custom field to indicate the event was manually emitted, and may have been handled already\n */\n emitted?: boolean;\n};\n\n/**\n * A streaming event.\n *\n * Schema of a streaming event which is produced from the streamEvents method.\n */\nexport type StreamEvent = {\n /**\n * Event names are of the format: on_[runnable_type]_(start|stream|end).\n *\n * Runnable types are one of:\n * - llm - used by non chat models\n * - chat_model - used by chat models\n * - prompt -- e.g., ChatPromptTemplate\n * - tool -- LangChain tools\n * - chain - most Runnables are of this type\n *\n * Further, the events are categorized as one of:\n * - start - when the runnable starts\n * - stream - when the runnable is streaming\n * - end - when the runnable ends\n *\n * start, stream and end are associated with slightly different `data` payload.\n *\n * Please see the documentation for `EventData` for more details.\n */\n event: string;\n /** The name of the runnable that generated the event. */\n name: string;\n /**\n * An randomly generated ID to keep track of the execution of the given runnable.\n *\n * Each child runnable that gets invoked as part of the execution of a parent runnable\n * is assigned its own unique ID.\n */\n run_id: string;\n /**\n * Tags associated with the runnable that generated this event.\n * Tags are always inherited from parent runnables.\n */\n tags?: string[];\n /** Metadata associated with the runnable that generated this event. */\n metadata: Record<string, unknown>;\n /**\n * Event data.\n *\n * The contents of the event data depend on the event type.\n */\n data: StreamEventData;\n};\n\nexport type GraphConfig = {\n provider: string;\n thread_id?: string;\n run_id?: string;\n};\n\nexport type PartMetadata = {\n progress?: number;\n asset_pointer?: string;\n status?: string;\n action?: boolean;\n output?: string;\n};\n\nexport type ModelEndData =\n | (StreamEventData & { output: AIMessageChunk | undefined })\n | undefined;\nexport type GraphTools = GenericTool[] | BindToolsInput[] | GoogleAIToolType[];\nexport type StandardGraphInput = {\n runId?: string;\n signal?: AbortSignal;\n agents: AgentInputs[];\n tokenCounter?: TokenCounter;\n indexTokenCountMap?: Record<string, number>;\n};\n\nexport type GraphEdge = {\n /** Agent ID, use a list for multiple sources */\n from: string | string[];\n /** Agent ID, use a list for multiple destinations */\n to: string | string[];\n description?: string;\n /** Can return boolean or specific destination(s) */\n condition?: (state: BaseGraphState) => boolean | string | string[];\n /** EdgeType.HANDOFF creates tools for dynamic routing, EdgeType.DIRECT creates direct edges with parallel execution */\n edgeType?: import('@/common').EdgeType;\n /**\n * For direct edges: Optional prompt to add when transitioning through this edge.\n * String prompts can include variables like {results} which will be replaced with\n * messages from startIndex onwards. When {results} is used, excludeResults defaults to true.\n *\n * For handoff edges: Description for the input parameter that the handoff tool accepts,\n * allowing the supervisor to pass specific instructions/context to the transferred agent.\n */\n prompt?:\n | string\n | ((\n messages: BaseMessage[],\n runStartIndex: number\n ) => string | Promise<string> | undefined);\n /**\n * When true, excludes messages from startIndex when adding prompt.\n * Automatically set to true when {results} variable is used in prompt.\n */\n excludeResults?: boolean;\n /**\n * For handoff edges: Customizes the parameter name for the handoff input.\n * Defaults to \"instructions\" if not specified.\n * Only applies when prompt is provided for handoff edges.\n */\n promptKey?: string;\n /**\n * For delegate edges: Maximum characters for the result returned to the parent.\n * Uses head/tail truncation (60/40 split) to preserve key findings and conclusions.\n * Defaults to Constants.DEFAULT_DELEGATE_MAX_RESULT_CHARS (32768 chars, ~8192 tokens).\n */\n maxResultChars?: number;\n};\n\nexport type MultiAgentGraphInput = StandardGraphInput & {\n edges: GraphEdge[];\n};\n\n/**\n * Structured output mode determines how the agent returns structured data.\n * - 'tool': Uses tool calling to return structured output (works with all tool-calling models)\n * - 'provider': Uses provider-native structured output via LangChain's jsonMode (OpenAI, Anthropic, etc.)\n * - 'native': Uses provider's constrained decoding API directly for guaranteed schema compliance\n * (Anthropic output_config.format, OpenAI response_format.json_schema). Falls back to 'tool' for unsupported providers.\n * - 'auto': Automatically selects the best strategy — 'native' for supported providers, 'tool' for others\n */\nexport type StructuredOutputMode = 'tool' | 'provider' | 'native' | 'auto';\n\n/**\n * Resolved method used internally after mode resolution.\n * Maps to LangChain's withStructuredOutput method parameter plus our native path.\n */\nexport type ResolvedStructuredOutputMethod =\n | 'functionCalling'\n | 'jsonMode'\n | 'jsonSchema'\n | 'native'\n | undefined;\n\n/**\n * Error thrown when the model refuses to produce structured output due to safety policies.\n */\nexport class StructuredOutputRefusalError extends Error {\n constructor(public refusalText: string) {\n super(`Model refused to produce structured output: ${refusalText}`);\n this.name = 'StructuredOutputRefusalError';\n }\n}\n\n/**\n * Error thrown when the structured output response was truncated due to max_tokens.\n */\nexport class StructuredOutputTruncatedError extends Error {\n constructor(public stopReason: string) {\n super(\n `Structured output was truncated (stop_reason: ${stopReason}). ` +\n 'Increase max_tokens to allow the full JSON response to be generated.'\n );\n this.name = 'StructuredOutputTruncatedError';\n }\n}\n\n/**\n * Configuration for structured JSON output from agents.\n * When configured, the agent will return a validated JSON response\n * instead of streaming text.\n */\nexport interface StructuredOutputConfig {\n /**\n * JSON Schema defining the output structure.\n * The model will be forced to return data conforming to this schema.\n */\n schema: Record<string, unknown>;\n /**\n * Name for the structured output format (used in tool mode).\n * @default 'StructuredResponse'\n */\n name?: string;\n /**\n * Description of what the structured output represents.\n * Helps the model understand the expected format.\n */\n description?: string;\n /**\n * Output mode strategy.\n * @default 'auto'\n */\n mode?: StructuredOutputMode;\n /**\n * Enable strict schema validation.\n * When true, the response must exactly match the schema.\n * @default true\n */\n strict?: boolean;\n /**\n * Error handling configuration.\n * - true: Auto-retry on validation errors (default)\n * - false: Throw error on validation failure\n * - string: Custom error message for retry\n */\n handleErrors?: boolean | string;\n /**\n * Maximum number of retry attempts on validation failure.\n * @default 2\n */\n maxRetries?: number;\n /**\n * Include the raw AI message along with structured response.\n * Useful for debugging.\n * @default false\n */\n includeRaw?: boolean;\n}\n\n/**\n * Database/API structured output format (snake_case with enabled flag).\n * This matches the format stored in MongoDB and sent from frontends.\n */\nexport interface StructuredOutputInput {\n /** Whether structured output is enabled */\n enabled?: boolean;\n /** JSON Schema defining the expected response structure */\n schema?: Record<string, unknown>;\n /** Name identifier for the structured output */\n name?: string;\n /** Description of what the structured output represents */\n description?: string;\n /** Mode for structured output: 'tool' | 'provider' | 'native' | 'auto' */\n mode?: StructuredOutputMode;\n /** Whether to enforce strict schema validation */\n strict?: boolean;\n}\n\n/**\n * Trigger strategy for when summarization should activate.\n * - 'contextPercentage': Trigger when context utilization exceeds a threshold percentage\n * - 'messageCount': Trigger when pruned message count exceeds a threshold\n * - 'tokenThreshold': Trigger when total token count exceeds a raw threshold\n */\nexport type SummarizationTriggerType =\n | 'contextPercentage'\n | 'messageCount'\n | 'tokenThreshold';\n\n/**\n * Configuration for summarization behavior within the agent pipeline.\n * All fields are optional — sensible defaults are provided via constants.\n *\n * @see SUMMARIZATION_CONTEXT_THRESHOLD, SUMMARIZATION_RESERVE_RATIO, PRUNING_EMA_ALPHA\n */\nexport interface SummarizationConfig {\n /**\n * Strategy for when summarization triggers.\n * @default 'contextPercentage'\n */\n triggerType?: SummarizationTriggerType;\n\n /**\n * Threshold value interpreted based on triggerType:\n * - contextPercentage: 0-100 (percentage of context window)\n * - messageCount: absolute count of messages pruned\n * - tokenThreshold: absolute token count\n * @default 80 (for contextPercentage)\n */\n triggerThreshold?: number;\n\n /**\n * Fraction of context window (0-1) reserved for recent messages.\n * Prevents over-pruning by ensuring at least this fraction of the\n * context budget is preserved as recent conversation history.\n * @default 0.3\n */\n reserveRatio?: number;\n\n /**\n * Whether context pruning is enabled (can be disabled for debugging).\n * @default true\n */\n contextPruning?: boolean;\n\n /**\n * Initial summary text to seed across runs.\n * Different from persistedSummary: this is provided by the caller as a\n * cross-conversation seed (e.g., agent personality or recurring context),\n * while persistedSummary is loaded from the conversation's own history.\n */\n initialSummary?: string;\n}\n\n/**\n * Runtime state for EMA-based pruning calibration.\n * Maintained across iterations within a single run to smooth pruning decisions.\n */\nexport interface PruneCalibrationState {\n /** Current EMA calibration ratio */\n ratio: number;\n /** Number of calibration updates applied */\n iterations: number;\n}\n\n/**\n * Lightweight file metadata entry for conversation-level file awareness.\n * Contains only IDs and names — NOT full content — so the agent always knows\n * what files exist in the conversation even after compaction pushes old messages\n * behind the summary window. The agent can retrieve full content on-demand\n * via file_search (RAG) or content_tool read (by contentId).\n */\nexport interface FileManifestEntry {\n /** Unique file identifier (e.g., MongoDB ObjectId or UUID) */\n fileId: string;\n /** Original filename (e.g., \"quarterly-report.pdf\") */\n filename: string;\n /** Content identifier for on-demand retrieval via content_tool read */\n contentId?: string;\n /** File source (e.g., \"local\", \"sharepoint\", \"onedrive\") */\n source?: string;\n /** Index of the message that introduced this file (0-based in the original message array) */\n messageIndex?: number;\n}\n\nexport interface AgentInputs {\n agentId: string;\n /** Human-readable name for the agent (used in handoff context). Defaults to agentId if not provided. */\n name?: string;\n /** Description of what this agent does (used to enrich handoff tool descriptions). */\n description?: string;\n toolEnd?: boolean;\n toolMap?: ToolMap;\n tools?: GraphTools;\n provider: Providers;\n instructions?: string;\n streamBuffer?: number;\n maxContextTokens?: number;\n clientOptions?: ClientOptions;\n additional_instructions?: string;\n reasoningKey?: 'reasoning_content' | 'reasoning';\n /** Format content blocks as strings (for legacy compatibility i.e. Ollama/Azure Serverless) */\n useLegacyContent?: boolean;\n /**\n * Tool definitions for all tools, including deferred and programmatic.\n * Used for tool search and programmatic tool calling.\n * Maps tool name to LCTool definition.\n */\n toolRegistry?: Map<string, LCTool>;\n /**\n * Dynamic context that changes per-request (e.g., current time, user info).\n * This is injected as a user message rather than system prompt to preserve cache.\n * Keeping this separate from instructions ensures the system message stays static\n * and can be cached by Bedrock/Anthropic prompt caching.\n */\n dynamicContext?: string;\n /**\n * Structured output configuration (camelCase).\n * When set, disables streaming and returns a validated JSON response\n * conforming to the specified schema.\n */\n structuredOutput?: StructuredOutputConfig;\n /**\n * Structured output configuration (snake_case - database/API format).\n * Alternative to structuredOutput for compatibility with MongoDB/frontend.\n * Uses an `enabled` flag to control activation.\n * @deprecated Use structuredOutput instead when possible\n */\n structured_output?: StructuredOutputInput;\n /**\n * Serializable tool definitions for event-driven execution.\n * When provided, ToolNode operates in event-driven mode, dispatching\n * ON_TOOL_EXECUTE events instead of invoking tools directly.\n */\n toolDefinitions?: LCTool[];\n /**\n * Tool names discovered from previous conversation history.\n * These tools will be pre-marked as discovered so they're included\n * in tool binding without requiring tool_search.\n */\n discoveredTools?: string[];\n /**\n * Optional callback for summarizing messages that were pruned from context.\n * When provided, discarded messages are summarized by the caller (e.g., Ranger)\n * using a cheap LLM call, and the summary is prepended to the context.\n */\n summarizeCallback?: (\n messagesToRefine: import('@langchain/core/messages').BaseMessage[]\n ) => Promise<string | undefined>;\n /**\n * Pre-existing summary text loaded from persistent storage (MongoDB/Redis).\n * When provided, this summary is injected into the initial message context\n * so the agent has prior conversation history even on new turns.\n * Set by Ranger's SummaryStore when resuming a conversation.\n */\n persistedSummary?: string;\n /**\n * Summarization configuration controlling trigger strategy, reserve ratio,\n * and EMA calibration for pruning. When omitted, sensible defaults apply.\n * @see SummarizationConfig\n */\n summarizationConfig?: SummarizationConfig;\n /**\n * Lightweight file manifest for the conversation.\n * Contains file IDs, names, and metadata — NOT full content.\n *\n * Used by the compaction engine to inject a [Conversation Files] block\n * into the windowed view, ensuring the LLM always knows what files exist\n * even when old messages (with full file content) are behind the summary.\n *\n * The agent can retrieve full content on-demand via:\n * - file_search (RAG semantic search over embedded files)\n * - content_tool read (by contentId for exact file retrieval)\n *\n * Built by the orchestrator (e.g., Ranger) from message_file_map\n * and metadata.context_files across all conversation messages.\n */\n fileManifest?: FileManifestEntry[];\n}\n"],"names":[],"mappings":"AAkZA;;AAEG;AACG,MAAO,4BAA6B,SAAQ,KAAK,CAAA;AAClC,IAAA,WAAA;AAAnB,IAAA,WAAA,CAAmB,WAAmB,EAAA;AACpC,QAAA,KAAK,CAAC,CAAA,4CAAA,EAA+C,WAAW,CAAA,CAAE,CAAC;QADlD,IAAA,CAAA,WAAW,GAAX,WAAW;AAE5B,QAAA,IAAI,CAAC,IAAI,GAAG,8BAA8B;IAC5C;AACD;AAED;;AAEG;AACG,MAAO,8BAA+B,SAAQ,KAAK,CAAA;AACpC,IAAA,UAAA;AAAnB,IAAA,WAAA,CAAmB,UAAkB,EAAA;QACnC,KAAK,CACH,CAAA,8CAAA,EAAiD,UAAU,CAAA,GAAA,CAAK;AAC9D,YAAA,sEAAsE,CACzE;QAJgB,IAAA,CAAA,UAAU,GAAV,UAAU;AAK3B,QAAA,IAAI,CAAC,IAAI,GAAG,gCAAgC;IAC9C;AACD;;;;"}
1
+ {"version":3,"file":"graph.mjs","sources":["../../../src/types/graph.ts"],"sourcesContent":["// src/types/graph.ts\nimport type {\n START,\n StateType,\n UpdateType,\n StateGraph,\n StateGraphArgs,\n StateDefinition,\n CompiledStateGraph,\n BinaryOperatorAggregate,\n} from '@langchain/langgraph';\nimport type { BindToolsInput } from '@langchain/core/language_models/chat_models';\nimport type {\n BaseMessage,\n AIMessageChunk,\n SystemMessage,\n} from '@langchain/core/messages';\nimport type { RunnableConfig, Runnable } from '@langchain/core/runnables';\nimport type { ChatGenerationChunk } from '@langchain/core/outputs';\nimport type { GoogleAIToolType } from '@langchain/google-common';\nimport type {\n ToolMap,\n ToolEndEvent,\n GenericTool,\n LCTool,\n ToolApprovalConfig,\n} from '@/types/tools';\nimport type { Providers, Callback, GraphNodeKeys } from '@/common';\nimport type { StandardGraph, MultiAgentGraph } from '@/graphs';\nimport type { ClientOptions } from '@/types/llm';\nimport type {\n RunStep,\n RunStepDeltaEvent,\n MessageDeltaEvent,\n ReasoningDeltaEvent,\n} from '@/types/stream';\nimport type { TokenCounter } from '@/types/run';\n\n/** Interface for bound model with stream and invoke methods */\nexport interface ChatModel {\n stream?: (\n messages: BaseMessage[],\n config?: RunnableConfig\n ) => Promise<AsyncIterable<AIMessageChunk>>;\n invoke: (\n messages: BaseMessage[],\n config?: RunnableConfig\n ) => Promise<AIMessageChunk>;\n}\n\nexport type GraphNode = GraphNodeKeys | typeof START;\nexport type ClientCallback<T extends unknown[]> = (\n graph: StandardGraph,\n ...args: T\n) => void;\n\nexport type ClientCallbacks = {\n [Callback.TOOL_ERROR]?: ClientCallback<[Error, string]>;\n [Callback.TOOL_START]?: ClientCallback<unknown[]>;\n [Callback.TOOL_END]?: ClientCallback<unknown[]>;\n};\n\nexport type SystemCallbacks = {\n [K in keyof ClientCallbacks]: ClientCallbacks[K] extends ClientCallback<\n infer Args\n >\n ? (...args: Args) => void\n : never;\n};\n\nexport type BaseGraphState = {\n messages: BaseMessage[];\n /**\n * Structured response when using structured output mode.\n * Contains the validated JSON response conforming to the configured schema.\n */\n structuredResponse?: Record<string, unknown>;\n};\n\nexport type MultiAgentGraphState = BaseGraphState & {\n agentMessages?: BaseMessage[];\n};\n\nexport type IState = BaseGraphState;\n\nexport interface EventHandler {\n handle(\n event: string,\n data:\n | StreamEventData\n | ModelEndData\n | RunStep\n | RunStepDeltaEvent\n | MessageDeltaEvent\n | ReasoningDeltaEvent\n | { result: ToolEndEvent },\n metadata?: Record<string, unknown>,\n graph?: StandardGraph | MultiAgentGraph\n ): void | Promise<void>;\n}\n\nexport type GraphStateChannels<T extends BaseGraphState> =\n StateGraphArgs<T>['channels'];\n\nexport type Workflow<\n T extends BaseGraphState = BaseGraphState,\n U extends Partial<T> = Partial<T>,\n N extends string = string,\n> = StateGraph<T, U, N>;\n\nexport type CompiledWorkflow<\n T extends BaseGraphState = BaseGraphState,\n U extends Partial<T> = Partial<T>,\n N extends string = string,\n> = CompiledStateGraph<T, U, N>;\n\nexport type CompiledStateWorkflow = CompiledStateGraph<\n StateType<{\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n }>,\n UpdateType<{\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n }>,\n string,\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n StateDefinition\n>;\n\nexport type CompiledMultiAgentWorkflow = CompiledStateGraph<\n StateType<{\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n agentMessages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n }>,\n UpdateType<{\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n agentMessages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n }>,\n string,\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n agentMessages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n agentMessages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n StateDefinition\n>;\n\nexport type CompiledAgentWorfklow = CompiledStateGraph<\n {\n messages: BaseMessage[];\n },\n {\n messages?: BaseMessage[] | undefined;\n },\n '__start__' | `agent=${string}` | `tools=${string}`,\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n {\n messages: BinaryOperatorAggregate<BaseMessage[], BaseMessage[]>;\n },\n StateDefinition,\n {\n [x: `agent=${string}`]: Partial<BaseGraphState>;\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n [x: `tools=${string}`]: any;\n }\n>;\n\nexport type SystemRunnable =\n | Runnable<\n BaseMessage[],\n (BaseMessage | SystemMessage)[],\n RunnableConfig<Record<string, unknown>>\n >\n | undefined;\n\n/**\n * Optional compile options passed to workflow.compile().\n * These are intentionally untyped to avoid coupling to library internals.\n */\nexport type CompileOptions = {\n // A checkpointer instance (e.g., MemorySaver, SQL saver)\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n checkpointer?: any;\n interruptBefore?: string[];\n interruptAfter?: string[];\n /**\n * Human-in-the-loop tool approval configuration.\n * When set, tools matching the policy will trigger an interrupt()\n * before execution, pausing the graph for human approval.\n * Requires a checkpointer to be set for interrupt/resume to work.\n */\n toolApprovalConfig?: ToolApprovalConfig;\n};\n\nexport type EventStreamCallbackHandlerInput =\n Parameters<CompiledWorkflow['streamEvents']>[2] extends Omit<\n infer T,\n 'autoClose'\n >\n ? T\n : never;\n\nexport type StreamChunk =\n | (ChatGenerationChunk & {\n message: AIMessageChunk;\n })\n | AIMessageChunk;\n\n/**\n * Data associated with a StreamEvent.\n */\nexport type StreamEventData = {\n /**\n * The input passed to the runnable that generated the event.\n * Inputs will sometimes be available at the *START* of the runnable, and\n * sometimes at the *END* of the runnable.\n * If a runnable is able to stream its inputs, then its input by definition\n * won't be known until the *END* of the runnable when it has finished streaming\n * its inputs.\n */\n input?: unknown;\n /**\n * The output of the runnable that generated the event.\n * Outputs will only be available at the *END* of the runnable.\n * For most runnables, this field can be inferred from the `chunk` field,\n * though there might be some exceptions for special cased runnables (e.g., like\n * chat models), which may return more information.\n */\n output?: unknown;\n /**\n * A streaming chunk from the output that generated the event.\n * chunks support addition in general, and adding them up should result\n * in the output of the runnable that generated the event.\n */\n chunk?: StreamChunk;\n /**\n * Runnable config for invoking other runnables within handlers.\n */\n config?: RunnableConfig;\n /**\n * Custom result from the runnable that generated the event.\n */\n result?: unknown;\n /**\n * Custom field to indicate the event was manually emitted, and may have been handled already\n */\n emitted?: boolean;\n};\n\n/**\n * A streaming event.\n *\n * Schema of a streaming event which is produced from the streamEvents method.\n */\nexport type StreamEvent = {\n /**\n * Event names are of the format: on_[runnable_type]_(start|stream|end).\n *\n * Runnable types are one of:\n * - llm - used by non chat models\n * - chat_model - used by chat models\n * - prompt -- e.g., ChatPromptTemplate\n * - tool -- LangChain tools\n * - chain - most Runnables are of this type\n *\n * Further, the events are categorized as one of:\n * - start - when the runnable starts\n * - stream - when the runnable is streaming\n * - end - when the runnable ends\n *\n * start, stream and end are associated with slightly different `data` payload.\n *\n * Please see the documentation for `EventData` for more details.\n */\n event: string;\n /** The name of the runnable that generated the event. */\n name: string;\n /**\n * An randomly generated ID to keep track of the execution of the given runnable.\n *\n * Each child runnable that gets invoked as part of the execution of a parent runnable\n * is assigned its own unique ID.\n */\n run_id: string;\n /**\n * Tags associated with the runnable that generated this event.\n * Tags are always inherited from parent runnables.\n */\n tags?: string[];\n /** Metadata associated with the runnable that generated this event. */\n metadata: Record<string, unknown>;\n /**\n * Event data.\n *\n * The contents of the event data depend on the event type.\n */\n data: StreamEventData;\n};\n\nexport type GraphConfig = {\n provider: string;\n thread_id?: string;\n run_id?: string;\n};\n\nexport type PartMetadata = {\n progress?: number;\n asset_pointer?: string;\n status?: string;\n action?: boolean;\n output?: string;\n};\n\nexport type ModelEndData =\n | (StreamEventData & { output: AIMessageChunk | undefined })\n | undefined;\nexport type GraphTools = GenericTool[] | BindToolsInput[] | GoogleAIToolType[];\nexport type StandardGraphInput = {\n runId?: string;\n signal?: AbortSignal;\n agents: AgentInputs[];\n tokenCounter?: TokenCounter;\n indexTokenCountMap?: Record<string, number>;\n};\n\nexport type GraphEdge = {\n /** Agent ID, use a list for multiple sources */\n from: string | string[];\n /** Agent ID, use a list for multiple destinations */\n to: string | string[];\n description?: string;\n /** Can return boolean or specific destination(s) */\n condition?: (state: BaseGraphState) => boolean | string | string[];\n /**\n * EdgeType.HANDOFF — true agent handoff, parent calls child inline and gets result back.\n * EdgeType.TRANSFER — one-way transfer, parent exits and child takes over.\n * EdgeType.SEQUENCE — fixed graph edges for sequential/parallel transitions.\n */\n edgeType?: import('@/common').EdgeType;\n /**\n * For sequence edges: Optional prompt to add when transitioning through this edge.\n * String prompts can include variables like {results} which will be replaced with\n * messages from startIndex onwards. When {results} is used, excludeResults defaults to true.\n *\n * For transfer edges: Description for the input parameter that the transfer tool accepts,\n * allowing the supervisor to pass specific instructions/context to the transferred agent.\n */\n prompt?:\n | string\n | ((\n messages: BaseMessage[],\n runStartIndex: number\n ) => string | Promise<string> | undefined);\n /**\n * When true, excludes messages from startIndex when adding prompt.\n * Automatically set to true when {results} variable is used in prompt.\n */\n excludeResults?: boolean;\n /**\n * For transfer edges: Customizes the parameter name for the transfer input.\n * Defaults to \"instructions\" if not specified.\n * Only applies when prompt is provided for transfer edges.\n *\n * For handoff edges: Customizes the parameter name for the handoff instruction input.\n */\n promptKey?: string;\n /**\n * For handoff edges: Maximum characters for the result returned to the parent.\n * Uses head/tail truncation (60/40 split) to preserve key findings and conclusions.\n * Defaults to DEFAULT_HANDOFF_MAX_RESULT_CHARS (32768 chars, ~8192 tokens).\n */\n maxResultChars?: number;\n};\n\nexport type MultiAgentGraphInput = StandardGraphInput & {\n edges: GraphEdge[];\n};\n\n/**\n * Structured output mode determines how the agent returns structured data.\n * - 'tool': Uses tool calling to return structured output (works with all tool-calling models)\n * - 'provider': Uses provider-native structured output via LangChain's jsonMode (OpenAI, Anthropic, etc.)\n * - 'native': Uses provider's constrained decoding API directly for guaranteed schema compliance\n * (Anthropic output_config.format, OpenAI response_format.json_schema). Falls back to 'tool' for unsupported providers.\n * - 'auto': Automatically selects the best strategy — 'native' for supported providers, 'tool' for others\n */\nexport type StructuredOutputMode = 'tool' | 'provider' | 'native' | 'auto';\n\n/**\n * Resolved method used internally after mode resolution.\n * Maps to LangChain's withStructuredOutput method parameter plus our native path.\n */\nexport type ResolvedStructuredOutputMethod =\n | 'functionCalling'\n | 'jsonMode'\n | 'jsonSchema'\n | 'native'\n | undefined;\n\n/**\n * Error thrown when the model refuses to produce structured output due to safety policies.\n */\nexport class StructuredOutputRefusalError extends Error {\n constructor(public refusalText: string) {\n super(`Model refused to produce structured output: ${refusalText}`);\n this.name = 'StructuredOutputRefusalError';\n }\n}\n\n/**\n * Error thrown when the structured output response was truncated due to max_tokens.\n */\nexport class StructuredOutputTruncatedError extends Error {\n constructor(public stopReason: string) {\n super(\n `Structured output was truncated (stop_reason: ${stopReason}). ` +\n 'Increase max_tokens to allow the full JSON response to be generated.'\n );\n this.name = 'StructuredOutputTruncatedError';\n }\n}\n\n/**\n * Configuration for structured JSON output from agents.\n * When configured, the agent will return a validated JSON response\n * instead of streaming text.\n */\nexport interface StructuredOutputConfig {\n /**\n * JSON Schema defining the output structure.\n * The model will be forced to return data conforming to this schema.\n */\n schema: Record<string, unknown>;\n /**\n * Name for the structured output format (used in tool mode).\n * @default 'StructuredResponse'\n */\n name?: string;\n /**\n * Description of what the structured output represents.\n * Helps the model understand the expected format.\n */\n description?: string;\n /**\n * Output mode strategy.\n * @default 'auto'\n */\n mode?: StructuredOutputMode;\n /**\n * Enable strict schema validation.\n * When true, the response must exactly match the schema.\n * @default true\n */\n strict?: boolean;\n /**\n * Error handling configuration.\n * - true: Auto-retry on validation errors (default)\n * - false: Throw error on validation failure\n * - string: Custom error message for retry\n */\n handleErrors?: boolean | string;\n /**\n * Maximum number of retry attempts on validation failure.\n * @default 2\n */\n maxRetries?: number;\n /**\n * Include the raw AI message along with structured response.\n * Useful for debugging.\n * @default false\n */\n includeRaw?: boolean;\n}\n\n/**\n * Database/API structured output format (snake_case with enabled flag).\n * This matches the format stored in MongoDB and sent from frontends.\n */\nexport interface StructuredOutputInput {\n /** Whether structured output is enabled */\n enabled?: boolean;\n /** JSON Schema defining the expected response structure */\n schema?: Record<string, unknown>;\n /** Name identifier for the structured output */\n name?: string;\n /** Description of what the structured output represents */\n description?: string;\n /** Mode for structured output: 'tool' | 'provider' | 'native' | 'auto' */\n mode?: StructuredOutputMode;\n /** Whether to enforce strict schema validation */\n strict?: boolean;\n}\n\n/**\n * Trigger strategy for when summarization should activate.\n * - 'contextPercentage': Trigger when context utilization exceeds a threshold percentage\n * - 'messageCount': Trigger when pruned message count exceeds a threshold\n * - 'tokenThreshold': Trigger when total token count exceeds a raw threshold\n */\nexport type SummarizationTriggerType =\n | 'contextPercentage'\n | 'messageCount'\n | 'tokenThreshold';\n\n/**\n * Configuration for summarization behavior within the agent pipeline.\n * All fields are optional — sensible defaults are provided via constants.\n *\n * @see SUMMARIZATION_CONTEXT_THRESHOLD, SUMMARIZATION_RESERVE_RATIO, PRUNING_EMA_ALPHA\n */\nexport interface SummarizationConfig {\n /**\n * Strategy for when summarization triggers.\n * @default 'contextPercentage'\n */\n triggerType?: SummarizationTriggerType;\n\n /**\n * Threshold value interpreted based on triggerType:\n * - contextPercentage: 0-100 (percentage of context window)\n * - messageCount: absolute count of messages pruned\n * - tokenThreshold: absolute token count\n * @default 80 (for contextPercentage)\n */\n triggerThreshold?: number;\n\n /**\n * Fraction of context window (0-1) reserved for recent messages.\n * Prevents over-pruning by ensuring at least this fraction of the\n * context budget is preserved as recent conversation history.\n * @default 0.3\n */\n reserveRatio?: number;\n\n /**\n * Whether context pruning is enabled (can be disabled for debugging).\n * @default true\n */\n contextPruning?: boolean;\n\n /**\n * Initial summary text to seed across runs.\n * Different from persistedSummary: this is provided by the caller as a\n * cross-conversation seed (e.g., agent personality or recurring context),\n * while persistedSummary is loaded from the conversation's own history.\n */\n initialSummary?: string;\n}\n\n/**\n * Runtime state for EMA-based pruning calibration.\n * Maintained across iterations within a single run to smooth pruning decisions.\n */\nexport interface PruneCalibrationState {\n /** Current EMA calibration ratio */\n ratio: number;\n /** Number of calibration updates applied */\n iterations: number;\n}\n\n/**\n * Lightweight file metadata entry for conversation-level file awareness.\n * Contains only IDs and names — NOT full content — so the agent always knows\n * what files exist in the conversation even after compaction pushes old messages\n * behind the summary window. The agent can retrieve full content on-demand\n * via file_search (RAG) or content_tool read (by contentId).\n */\nexport interface FileManifestEntry {\n /** Unique file identifier (e.g., MongoDB ObjectId or UUID) */\n fileId: string;\n /** Original filename (e.g., \"quarterly-report.pdf\") */\n filename: string;\n /** Content identifier for on-demand retrieval via content_tool read */\n contentId?: string;\n /** File source (e.g., \"local\", \"sharepoint\", \"onedrive\") */\n source?: string;\n /** Index of the message that introduced this file (0-based in the original message array) */\n messageIndex?: number;\n}\n\nexport interface AgentInputs {\n agentId: string;\n /** Human-readable name for the agent (used in handoff context). Defaults to agentId if not provided. */\n name?: string;\n /** Description of what this agent does (used to enrich handoff tool descriptions). */\n description?: string;\n toolEnd?: boolean;\n toolMap?: ToolMap;\n tools?: GraphTools;\n provider: Providers;\n instructions?: string;\n streamBuffer?: number;\n maxContextTokens?: number;\n clientOptions?: ClientOptions;\n additional_instructions?: string;\n reasoningKey?: 'reasoning_content' | 'reasoning';\n /** Format content blocks as strings (for legacy compatibility i.e. Ollama/Azure Serverless) */\n useLegacyContent?: boolean;\n /**\n * Tool definitions for all tools, including deferred and programmatic.\n * Used for tool search and programmatic tool calling.\n * Maps tool name to LCTool definition.\n */\n toolRegistry?: Map<string, LCTool>;\n /**\n * Dynamic context that changes per-request (e.g., current time, user info).\n * This is injected as a user message rather than system prompt to preserve cache.\n * Keeping this separate from instructions ensures the system message stays static\n * and can be cached by Bedrock/Anthropic prompt caching.\n */\n dynamicContext?: string;\n /**\n * Structured output configuration (camelCase).\n * When set, disables streaming and returns a validated JSON response\n * conforming to the specified schema.\n */\n structuredOutput?: StructuredOutputConfig;\n /**\n * Structured output configuration (snake_case - database/API format).\n * Alternative to structuredOutput for compatibility with MongoDB/frontend.\n * Uses an `enabled` flag to control activation.\n * @deprecated Use structuredOutput instead when possible\n */\n structured_output?: StructuredOutputInput;\n /**\n * Serializable tool definitions for event-driven execution.\n * When provided, ToolNode operates in event-driven mode, dispatching\n * ON_TOOL_EXECUTE events instead of invoking tools directly.\n */\n toolDefinitions?: LCTool[];\n /**\n * Tool names discovered from previous conversation history.\n * These tools will be pre-marked as discovered so they're included\n * in tool binding without requiring tool_search.\n */\n discoveredTools?: string[];\n /**\n * Optional callback for summarizing messages that were pruned from context.\n * When provided, discarded messages are summarized by the caller (e.g., Ranger)\n * using a cheap LLM call, and the summary is prepended to the context.\n */\n summarizeCallback?: (\n messagesToRefine: import('@langchain/core/messages').BaseMessage[]\n ) => Promise<string | undefined>;\n /**\n * Pre-existing summary text loaded from persistent storage (MongoDB/Redis).\n * When provided, this summary is injected into the initial message context\n * so the agent has prior conversation history even on new turns.\n * Set by Ranger's SummaryStore when resuming a conversation.\n */\n persistedSummary?: string;\n /**\n * Summarization configuration controlling trigger strategy, reserve ratio,\n * and EMA calibration for pruning. When omitted, sensible defaults apply.\n * @see SummarizationConfig\n */\n summarizationConfig?: SummarizationConfig;\n /**\n * Lightweight file manifest for the conversation.\n * Contains file IDs, names, and metadata — NOT full content.\n *\n * Used by the compaction engine to inject a [Conversation Files] block\n * into the windowed view, ensuring the LLM always knows what files exist\n * even when old messages (with full file content) are behind the summary.\n *\n * The agent can retrieve full content on-demand via:\n * - file_search (RAG semantic search over embedded files)\n * - content_tool read (by contentId for exact file retrieval)\n *\n * Built by the orchestrator (e.g., Ranger) from message_file_map\n * and metadata.context_files across all conversation messages.\n */\n fileManifest?: FileManifestEntry[];\n}\n"],"names":[],"mappings":"AAwZA;;AAEG;AACG,MAAO,4BAA6B,SAAQ,KAAK,CAAA;AAClC,IAAA,WAAA;AAAnB,IAAA,WAAA,CAAmB,WAAmB,EAAA;AACpC,QAAA,KAAK,CAAC,CAAA,4CAAA,EAA+C,WAAW,CAAA,CAAE,CAAC;QADlD,IAAA,CAAA,WAAW,GAAX,WAAW;AAE5B,QAAA,IAAI,CAAC,IAAI,GAAG,8BAA8B;IAC5C;AACD;AAED;;AAEG;AACG,MAAO,8BAA+B,SAAQ,KAAK,CAAA;AACpC,IAAA,UAAA;AAAnB,IAAA,WAAA,CAAmB,UAAkB,EAAA;QACnC,KAAK,CACH,CAAA,8CAAA,EAAiD,UAAU,CAAA,GAAA,CAAK;AAC9D,YAAA,sEAAsE,CACzE;QAJgB,IAAA,CAAA,UAAU,GAAV,UAAU;AAK3B,QAAA,IAAI,CAAC,IAAI,GAAG,gCAAgC;IAC9C;AACD;;;;"}
@@ -75,12 +75,12 @@ export declare enum Providers {
75
75
  MOONSHOT = "moonshot"
76
76
  }
77
77
  export declare enum EdgeType {
78
- /** Creates handoff tools for dynamic agent routing (default for single-to-single edges) */
78
+ /** True agent handoff parent calls child agent inline, gets result back, continues orchestrating */
79
79
  HANDOFF = "handoff",
80
- /** Creates direct edges for automatic sequential/parallel transitions */
81
- DIRECT = "direct",
82
- /** Creates delegate tools that invoke child subgraph inline and return result to parent */
83
- DELEGATE = "delegate"
80
+ /** One-way transfer parent exits, child takes over and responds directly to user */
81
+ TRANSFER = "transfer",
82
+ /** Fixed graph edges for automatic sequential/parallel transitions */
83
+ SEQUENCE = "sequence"
84
84
  }
85
85
  export declare enum GraphNodeKeys {
86
86
  TOOLS = "tools=",
@@ -138,8 +138,8 @@ export declare enum Constants {
138
138
  WEB_SEARCH = "web_search",
139
139
  CONTENT_AND_ARTIFACT = "content_and_artifact",
140
140
  LC_TRANSFER_TO_ = "lc_transfer_to_",
141
- /** Prefix for delegate tool names: lc_delegate_to_{agentId} */
142
- LC_DELEGATE_TO_ = "lc_delegate_to_",
141
+ /** Prefix for handoff tool names: lc_handoff_to_{agentId} */
142
+ LC_HANDOFF_TO_ = "lc_handoff_to_",
143
143
  /** Tool name for the AskUser structured question tool */
144
144
  ASK_USER = "ask_user",
145
145
  /** Delimiter for MCP tools: toolName_mcp_serverName */
@@ -187,7 +187,7 @@ export declare enum MessageTypes {
187
187
  DEVELOPER = "developer",
188
188
  REMOVE = "remove"
189
189
  }
190
- /** Default max characters for delegate results returned to parent (~8192 tokens at ~4 chars/token) */
191
- export declare const DEFAULT_DELEGATE_MAX_RESULT_CHARS = 32768;
192
- /** Default timeout for delegate sub-agent execution in milliseconds (5 minutes) */
193
- export declare const DELEGATE_TIMEOUT_MS = 300000;
190
+ /** Default max characters for handoff results returned to parent (~8192 tokens at ~4 chars/token) */
191
+ export declare const DEFAULT_HANDOFF_MAX_RESULT_CHARS = 32768;
192
+ /** Default timeout for handoff sub-agent execution in milliseconds (5 minutes) */
193
+ export declare const HANDOFF_TIMEOUT_MS = 300000;
@@ -6,24 +6,24 @@ import { StandardGraph } from './Graph';
6
6
  * with handoffs, fan-in/fan-out, and other composable patterns.
7
7
  *
8
8
  * Key behavior:
9
- * - Agents with ONLY handoff edges: Can dynamically route to any handoff destination
10
- * - Agents with ONLY direct edges: Always follow their direct edges
11
- * - Agents with BOTH: Use Command for exclusive routing (handoff OR direct, not both)
12
- * - If handoff occurs: Only the handoff destination executes
13
- * - If no handoff: Direct edges execute (potentially in parallel)
9
+ * - Agents with ONLY transfer edges: Can dynamically route to any transfer destination
10
+ * - Agents with ONLY sequence edges: Always follow their sequence edges
11
+ * - Agents with BOTH: Use Command for exclusive routing (transfer OR sequence, not both)
12
+ * - If transfer occurs: Only the transfer destination executes
13
+ * - If no transfer: Sequence edges execute (potentially in parallel)
14
14
  *
15
- * This enables the common pattern where an agent either delegates (handoff)
16
- * OR continues its workflow (direct edges), but not both simultaneously.
15
+ * This enables the common pattern where an agent either transfers (one-way)
16
+ * OR continues its workflow (sequence edges), but not both simultaneously.
17
17
  */
18
18
  export declare class MultiAgentGraph extends StandardGraph {
19
19
  private edges;
20
20
  private startingNodes;
21
- private directEdges;
21
+ private sequenceEdges;
22
+ private transferEdges;
22
23
  private handoffEdges;
23
- private delegateEdges;
24
24
  /**
25
25
  * Lazily populated registry of compiled subgraphs, keyed by agentId.
26
- * Delegate tools are created in the constructor but reference subgraphs
26
+ * Handoff tools are created in the constructor but reference subgraphs
27
27
  * that are only created in createWorkflow(). This Map bridges that gap —
28
28
  * tools capture the Map reference in their closure, and createWorkflow()
29
29
  * populates it before any tool invocation occurs.
@@ -47,7 +47,7 @@ export declare class MultiAgentGraph extends StandardGraph {
47
47
  private lastActiveAgentId;
48
48
  constructor(input: t.MultiAgentGraphInput);
49
49
  /**
50
- * Categorize edges into handoff and direct types
50
+ * Categorize edges into handoff, transfer, and sequence types
51
51
  */
52
52
  private categorizeEdges;
53
53
  /**
@@ -91,44 +91,46 @@ export declare class MultiAgentGraph extends StandardGraph {
91
91
  */
92
92
  protected getParallelGroupIdForAgent(agentId: string): number | undefined;
93
93
  /**
94
- * Create handoff tools for agents based on handoff edges only
94
+ * Create transfer tools for agents based on transfer edges only.
95
+ * Transfer tools return Command for one-way routing — parent exits, child takes over.
95
96
  */
96
- private createHandoffTools;
97
+ private createTransferTools;
97
98
  /**
98
- * Create handoff tools for an edge (handles multiple destinations)
99
- * @param edge - The graph edge defining the handoff
100
- * @param sourceAgentId - The ID of the agent that will perform the handoff
99
+ * Create transfer tools for an edge (handles multiple destinations).
100
+ * Transfer tools return Command for one-way routing parent exits, child takes over.
101
+ * @param edge - The graph edge defining the transfer
102
+ * @param sourceAgentId - The ID of the agent that will perform the transfer
101
103
  * @param sourceAgentName - The human-readable name of the source agent
102
104
  */
103
- private createHandoffToolsForEdge;
105
+ private createTransferToolsForEdge;
104
106
  /**
105
- * Builds a meaningful default description for a handoff tool when no explicit
107
+ * Builds a meaningful default description for a transfer tool when no explicit
106
108
  * edge.description is provided. Uses the destination agent's name and description
107
109
  * so the LLM can make informed routing decisions.
108
110
  * @param destContext - AgentContext of the destination agent (may be undefined)
109
111
  * @param destinationId - Raw agent ID (fallback when context unavailable)
110
112
  */
111
- private buildDefaultHandoffDescription;
113
+ private buildDefaultTransferDescription;
112
114
  /**
113
- * Create delegate tools for agents based on delegate edges.
114
- * Delegate tools invoke child agent subgraphs inline and return the result
115
- * as a string to the parent agent's context. Unlike handoff tools (which
116
- * return Command for fire-and-forget routing), delegate tools execute the
117
- * child, extract the final text, and return it within the parent's agent loop.
115
+ * Create handoff tools for agents based on handoff edges.
116
+ * Handoff tools invoke child agent subgraphs inline and return the result
117
+ * as a string to the parent agent's context. Unlike transfer tools (which
118
+ * return Command for one-way routing), handoff tools execute the child,
119
+ * extract the final text, and return it within the parent's agent loop.
118
120
  *
119
121
  * This enables the supervisor pattern: parent calls child → gets result → thinks → calls another.
120
122
  */
121
- private createDelegateTools;
123
+ private createHandoffTools;
122
124
  /**
123
- * Create delegate tools for an edge (handles multiple destinations).
124
- * Each delegate tool invokes the child agent's compiled subgraph inline,
125
+ * Create handoff tools for an edge (handles multiple destinations).
126
+ * Each handoff tool invokes the child agent's compiled subgraph inline,
125
127
  * extracts the final AI message text, truncates it, and returns it as
126
128
  * a string (which becomes a ToolMessage in the parent's context).
127
129
  *
128
- * @param edge - The graph edge defining the delegation
130
+ * @param edge - The graph edge defining the handoff
129
131
  * @param sourceAgentId - The ID of the parent/supervisor agent
130
132
  */
131
- private createDelegateToolsForEdge;
133
+ private createHandoffToolsForEdge;
132
134
  /**
133
135
  * Extract the final text result from a child agent's output messages.
134
136
  * Walks backwards to find the last AIMessage with text content.
@@ -136,21 +138,21 @@ export declare class MultiAgentGraph extends StandardGraph {
136
138
  * @param messages - The child agent's output messages
137
139
  * @param agentId - The child agent ID (for fallback message)
138
140
  */
139
- static extractDelegateResult(messages: BaseMessage[], agentId: string): string;
141
+ static extractHandoffResult(messages: BaseMessage[], agentId: string): string;
140
142
  /**
141
- * Truncate delegate result using head/tail strategy (60/40 split).
143
+ * Truncate handoff result using head/tail strategy (60/40 split).
142
144
  * Preserves the beginning (key findings) and end (conclusions).
143
145
  * Matches the TaskTool.truncateResult pattern from Ranger.
144
146
  * @param result - The full result text
145
147
  * @param maxChars - Maximum allowed characters
146
148
  */
147
- static truncateDelegateResult(result: string, maxChars: number): string;
149
+ static truncateHandoffResult(result: string, maxChars: number): string;
148
150
  /**
149
- * Build a meaningful default description for a delegate tool.
151
+ * Build a meaningful default description for a handoff tool.
150
152
  * @param destContext - AgentContext of the destination agent
151
153
  * @param destinationId - Raw agent ID (fallback)
152
154
  */
153
- private buildDefaultDelegateDescription;
155
+ private buildDefaultHandoffDescription;
154
156
  /**
155
157
  * Create a complete agent subgraph (similar to createReactAgent)
156
158
  */
@@ -167,9 +169,9 @@ export declare class MultiAgentGraph extends StandardGraph {
167
169
  * @param agentId - The agent ID to check for handoff reception
168
170
  * @returns Object with filtered messages, extracted instructions, source agent, and parallel siblings
169
171
  */
170
- private processHandoffReception;
172
+ private processTransferReception;
171
173
  /**
172
- * Create the multi-agent workflow with dynamic handoffs
174
+ * Create the multi-agent workflow with handoffs, transfers, and sequences
173
175
  */
174
176
  createWorkflow(): t.CompiledMultiAgentWorkflow;
175
177
  }
@@ -220,14 +220,18 @@ export type GraphEdge = {
220
220
  description?: string;
221
221
  /** Can return boolean or specific destination(s) */
222
222
  condition?: (state: BaseGraphState) => boolean | string | string[];
223
- /** EdgeType.HANDOFF creates tools for dynamic routing, EdgeType.DIRECT creates direct edges with parallel execution */
223
+ /**
224
+ * EdgeType.HANDOFF — true agent handoff, parent calls child inline and gets result back.
225
+ * EdgeType.TRANSFER — one-way transfer, parent exits and child takes over.
226
+ * EdgeType.SEQUENCE — fixed graph edges for sequential/parallel transitions.
227
+ */
224
228
  edgeType?: import('@/common').EdgeType;
225
229
  /**
226
- * For direct edges: Optional prompt to add when transitioning through this edge.
230
+ * For sequence edges: Optional prompt to add when transitioning through this edge.
227
231
  * String prompts can include variables like {results} which will be replaced with
228
232
  * messages from startIndex onwards. When {results} is used, excludeResults defaults to true.
229
233
  *
230
- * For handoff edges: Description for the input parameter that the handoff tool accepts,
234
+ * For transfer edges: Description for the input parameter that the transfer tool accepts,
231
235
  * allowing the supervisor to pass specific instructions/context to the transferred agent.
232
236
  */
233
237
  prompt?: string | ((messages: BaseMessage[], runStartIndex: number) => string | Promise<string> | undefined);
@@ -237,15 +241,17 @@ export type GraphEdge = {
237
241
  */
238
242
  excludeResults?: boolean;
239
243
  /**
240
- * For handoff edges: Customizes the parameter name for the handoff input.
244
+ * For transfer edges: Customizes the parameter name for the transfer input.
241
245
  * Defaults to "instructions" if not specified.
242
- * Only applies when prompt is provided for handoff edges.
246
+ * Only applies when prompt is provided for transfer edges.
247
+ *
248
+ * For handoff edges: Customizes the parameter name for the handoff instruction input.
243
249
  */
244
250
  promptKey?: string;
245
251
  /**
246
- * For delegate edges: Maximum characters for the result returned to the parent.
252
+ * For handoff edges: Maximum characters for the result returned to the parent.
247
253
  * Uses head/tail truncation (60/40 split) to preserve key findings and conclusions.
248
- * Defaults to Constants.DEFAULT_DELEGATE_MAX_RESULT_CHARS (32768 chars, ~8192 tokens).
254
+ * Defaults to DEFAULT_HANDOFF_MAX_RESULT_CHARS (32768 chars, ~8192 tokens).
249
255
  */
250
256
  maxResultChars?: number;
251
257
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@illuma-ai/agents",
3
- "version": "1.1.15",
3
+ "version": "1.1.16",
4
4
  "main": "./dist/cjs/main.cjs",
5
5
  "module": "./dist/esm/main.mjs",
6
6
  "types": "./dist/types/index.d.ts",
@@ -18,18 +18,22 @@ import {
18
18
  } from '@/common';
19
19
 
20
20
  describe('EdgeType enum', () => {
21
- it('has correct HANDOFF value', () => {
21
+ it('has correct HANDOFF value (supervisor pattern)', () => {
22
22
  expect(EdgeType.HANDOFF).toBe('handoff');
23
23
  });
24
24
 
25
- it('has correct DIRECT value', () => {
26
- expect(EdgeType.DIRECT).toBe('direct');
25
+ it('has correct TRANSFER value (one-way fire-and-forget)', () => {
26
+ expect(EdgeType.TRANSFER).toBe('transfer');
27
27
  });
28
28
 
29
- it('has three members: handoff, direct, delegate', () => {
29
+ it('has correct SEQUENCE value (fixed graph edges)', () => {
30
+ expect(EdgeType.SEQUENCE).toBe('sequence');
31
+ });
32
+
33
+ it('has three members: handoff, transfer, sequence', () => {
30
34
  const values = Object.values(EdgeType);
31
35
  expect(values).toHaveLength(3);
32
- expect(values).toEqual(expect.arrayContaining(['handoff', 'direct', 'delegate']));
36
+ expect(values).toEqual(expect.arrayContaining(['handoff', 'transfer', 'sequence']));
33
37
  });
34
38
  });
35
39
 
@@ -42,10 +46,14 @@ describe('Constants enum', () => {
42
46
  expect(Constants.EXECUTE_CODE).toBe('execute_code');
43
47
  });
44
48
 
45
- it('has LC_TRANSFER_TO_ prefix for LangChain handoff tools', () => {
49
+ it('has LC_TRANSFER_TO_ prefix for LangChain transfer tools', () => {
46
50
  expect(Constants.LC_TRANSFER_TO_).toBe('lc_transfer_to_');
47
51
  });
48
52
 
53
+ it('has LC_HANDOFF_TO_ prefix for LangChain handoff tools', () => {
54
+ expect(Constants.LC_HANDOFF_TO_).toBe('lc_handoff_to_');
55
+ });
56
+
49
57
  it('has MCP_DELIMITER for MCP tool naming', () => {
50
58
  expect(Constants.MCP_DELIMITER).toBe('_mcp_');
51
59
  });
@@ -96,12 +96,12 @@ export enum Providers {
96
96
  }
97
97
 
98
98
  export enum EdgeType {
99
- /** Creates handoff tools for dynamic agent routing (default for single-to-single edges) */
99
+ /** True agent handoff parent calls child agent inline, gets result back, continues orchestrating */
100
100
  HANDOFF = 'handoff',
101
- /** Creates direct edges for automatic sequential/parallel transitions */
102
- DIRECT = 'direct',
103
- /** Creates delegate tools that invoke child subgraph inline and return result to parent */
104
- DELEGATE = 'delegate',
101
+ /** One-way transfer parent exits, child takes over and responds directly to user */
102
+ TRANSFER = 'transfer',
103
+ /** Fixed graph edges for automatic sequential/parallel transitions */
104
+ SEQUENCE = 'sequence',
105
105
  }
106
106
 
107
107
  export enum GraphNodeKeys {
@@ -184,8 +184,8 @@ export enum Constants {
184
184
  WEB_SEARCH = 'web_search',
185
185
  CONTENT_AND_ARTIFACT = 'content_and_artifact',
186
186
  LC_TRANSFER_TO_ = 'lc_transfer_to_',
187
- /** Prefix for delegate tool names: lc_delegate_to_{agentId} */
188
- LC_DELEGATE_TO_ = 'lc_delegate_to_',
187
+ /** Prefix for handoff tool names: lc_handoff_to_{agentId} */
188
+ LC_HANDOFF_TO_ = 'lc_handoff_to_',
189
189
  /** Tool name for the AskUser structured question tool */
190
190
  ASK_USER = 'ask_user',
191
191
  /** Delimiter for MCP tools: toolName_mcp_serverName */
@@ -238,8 +238,8 @@ export enum MessageTypes {
238
238
  REMOVE = 'remove',
239
239
  }
240
240
 
241
- /** Default max characters for delegate results returned to parent (~8192 tokens at ~4 chars/token) */
242
- export const DEFAULT_DELEGATE_MAX_RESULT_CHARS = 32768;
241
+ /** Default max characters for handoff results returned to parent (~8192 tokens at ~4 chars/token) */
242
+ export const DEFAULT_HANDOFF_MAX_RESULT_CHARS = 32768;
243
243
 
244
- /** Default timeout for delegate sub-agent execution in milliseconds (5 minutes) */
245
- export const DELEGATE_TIMEOUT_MS = 300_000;
244
+ /** Default timeout for handoff sub-agent execution in milliseconds (5 minutes) */
245
+ export const HANDOFF_TIMEOUT_MS = 300_000;