@truefoundry/trueforge-core 0.1.0-rc.0 → 0.1.0
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.
- package/dist/core/index.d.ts +9 -3
- package/dist/core/index.d.ts.map +1 -1
- package/dist/core/index.js +25 -0
- package/dist/core/index.js.map +1 -1
- package/dist/core/index.mjs +24 -2
- package/dist/core/index.mjs.map +1 -1
- package/dist/core/llm/VercelAILLM.d.ts +1 -0
- package/dist/core/llm/VercelAILLM.d.ts.map +1 -1
- package/dist/core/llm/VercelAILLM.js +9 -14
- package/dist/core/llm/VercelAILLM.js.map +1 -1
- package/dist/core/llm/VercelAILLM.mjs +9 -15
- package/dist/core/llm/VercelAILLM.mjs.map +1 -1
- package/dist/core/runtime/AgentThread.d.ts.map +1 -1
- package/dist/core/runtime/AgentThread.js +3 -1
- package/dist/core/runtime/AgentThread.js.map +1 -1
- package/dist/core/runtime/AgentThread.mjs +3 -1
- package/dist/core/runtime/AgentThread.mjs.map +1 -1
- package/dist/core/sandbox/Sandbox.d.ts +7 -9
- package/dist/core/sandbox/Sandbox.d.ts.map +1 -1
- package/dist/core/sandbox/Sandbox.js +45 -61
- package/dist/core/sandbox/Sandbox.js.map +1 -1
- package/dist/core/sandbox/Sandbox.mjs +46 -62
- package/dist/core/sandbox/Sandbox.mjs.map +1 -1
- package/dist/core/sandbox/codeMode/CodeModeDispatcher.d.ts +29 -0
- package/dist/core/sandbox/codeMode/CodeModeDispatcher.d.ts.map +1 -0
- package/dist/core/sandbox/codeMode/CodeModeDispatcher.js +128 -0
- package/dist/core/sandbox/codeMode/CodeModeDispatcher.js.map +1 -0
- package/dist/core/sandbox/codeMode/CodeModeDispatcher.mjs +107 -0
- package/dist/core/sandbox/codeMode/CodeModeDispatcher.mjs.map +1 -0
- package/dist/core/sandbox/codeMode/CodeModeTransport.d.ts +21 -0
- package/dist/core/sandbox/codeMode/CodeModeTransport.d.ts.map +1 -0
- package/dist/core/sandbox/codeMode/CodeModeTransport.js +19 -0
- package/dist/core/sandbox/codeMode/CodeModeTransport.js.map +1 -0
- package/dist/core/sandbox/codeMode/CodeModeTransport.mjs +1 -0
- package/dist/core/sandbox/codeMode/CodeModeTransport.mjs.map +1 -0
- package/dist/core/sandbox/codeMode/nats/CodeModeNatsTransport.d.ts +34 -0
- package/dist/core/sandbox/codeMode/nats/CodeModeNatsTransport.d.ts.map +1 -0
- package/dist/core/sandbox/codeMode/nats/CodeModeNatsTransport.js +187 -0
- package/dist/core/sandbox/codeMode/nats/CodeModeNatsTransport.js.map +1 -0
- package/dist/core/sandbox/codeMode/nats/CodeModeNatsTransport.mjs +162 -0
- package/dist/core/sandbox/codeMode/nats/CodeModeNatsTransport.mjs.map +1 -0
- package/dist/core/sandbox/codeMode/types.d.ts +34 -0
- package/dist/core/sandbox/codeMode/types.d.ts.map +1 -0
- package/dist/core/sandbox/codeMode/types.js +59 -0
- package/dist/core/sandbox/codeMode/types.js.map +1 -0
- package/dist/core/sandbox/codeMode/types.mjs +32 -0
- package/dist/core/sandbox/codeMode/types.mjs.map +1 -0
- package/dist/core/sandbox/provider/DaytonaProvider.d.ts +2 -1
- package/dist/core/sandbox/provider/DaytonaProvider.d.ts.map +1 -1
- package/dist/core/sandbox/provider/DaytonaProvider.js +13 -6
- package/dist/core/sandbox/provider/DaytonaProvider.js.map +1 -1
- package/dist/core/sandbox/provider/DaytonaProvider.mjs +13 -6
- package/dist/core/sandbox/provider/DaytonaProvider.mjs.map +1 -1
- package/dist/core/sandbox/provider/Provider.d.ts +4 -3
- package/dist/core/sandbox/provider/Provider.d.ts.map +1 -1
- package/dist/core/sandbox/provider/Provider.js.map +1 -1
- package/dist/core/sandbox/provider/Provider.mjs.map +1 -1
- package/dist/core/sandbox/provider/TFYSandboxProvider.d.ts +2 -1
- package/dist/core/sandbox/provider/TFYSandboxProvider.d.ts.map +1 -1
- package/dist/core/sandbox/provider/TFYSandboxProvider.js +8 -2
- package/dist/core/sandbox/provider/TFYSandboxProvider.js.map +1 -1
- package/dist/core/sandbox/provider/TFYSandboxProvider.mjs +8 -2
- package/dist/core/sandbox/provider/TFYSandboxProvider.mjs.map +1 -1
- package/dist/core/sandbox/sandboxImage.d.ts +1 -1
- package/dist/core/sandbox/sandboxImage.d.ts.map +1 -1
- package/dist/core/sandbox/sandboxImage.js +1 -1
- package/dist/core/sandbox/sandboxImage.js.map +1 -1
- package/dist/core/sandbox/sandboxImage.mjs +1 -1
- package/dist/core/sandbox/sandboxImage.mjs.map +1 -1
- package/dist/core/sandbox/sandboxScripts.gen.d.ts +1 -1
- package/dist/core/sandbox/sandboxScripts.gen.d.ts.map +1 -1
- package/dist/core/sandbox/sandboxScripts.gen.js +8 -8
- package/dist/core/sandbox/sandboxScripts.gen.js.map +1 -1
- package/dist/core/sandbox/sandboxScripts.gen.mjs +8 -8
- package/dist/core/sandbox/sandboxScripts.gen.mjs.map +1 -1
- package/dist/core/util/errorLogFields.d.ts +5 -0
- package/dist/core/util/errorLogFields.d.ts.map +1 -1
- package/dist/core/util/errorLogFields.js +38 -2
- package/dist/core/util/errorLogFields.js.map +1 -1
- package/dist/core/util/errorLogFields.mjs +37 -2
- package/dist/core/util/errorLogFields.mjs.map +1 -1
- package/package.json +1 -1
- package/dist/core/sandbox/SandboxNatsBridge.d.ts +0 -33
- package/dist/core/sandbox/SandboxNatsBridge.d.ts.map +0 -1
- package/dist/core/sandbox/SandboxNatsBridge.js +0 -222
- package/dist/core/sandbox/SandboxNatsBridge.js.map +0 -1
- package/dist/core/sandbox/SandboxNatsBridge.mjs +0 -201
- package/dist/core/sandbox/SandboxNatsBridge.mjs.map +0 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../../src/core/runtime/AgentThread.ts"],"sourcesContent":["import type { ChatCompletionMessageParam, ChatCompletionTool } from 'openai/resources/chat';\nimport type { Logger } from 'winston';\nimport type { AgentCapability, CapabilityState } from '../capabilities/AgentCapability';\nimport type {\n AgentContextProcessorOutput,\n AgentContextProcessorOverwriteContext,\n AgentThreadExecutionContext,\n PostToolCallAgentContextProcessor,\n PreLLMAgentContextProcessor,\n PreLLMEphemeralAgentContextProcessor,\n PreSendContextProcessor,\n} from '../capabilities/AgentContextProcessor';\nimport { SUB_AGENT_IDENTITY } from '../capabilities/builtins/DynamicSubAgents';\nimport type { ToolResponseProcessor } from '../capabilities/ToolResponseProcessor';\nimport { AgentHarnessError, InvalidAgentSendInputError } from '../errors';\nimport type { RegisteredPassthroughEvent } from '../events/PassthroughEvents';\nimport {\n EventType,\n newEventId,\n type AgentApprovalDecisionMessage,\n type AgentInfo,\n type AgentOutputEvent,\n type AgentParent,\n type MCPInitializeEvent,\n type MCPServerInitInfo,\n type ModelMessageDeltaEvent,\n type ModelMessageEvent,\n type ModelMessageUsage,\n type SandboxCreatedEvent,\n type ThreadOverwriteContextEvent,\n type ToolApprovalRequiredEvent,\n type ToolResponseEvent,\n type ToolResponseRequiredEvent,\n type UserToolApprovalMessage,\n type UserToolResponseMessage,\n} from '../events/schema';\nimport { InstructionBuilder, ROOT_AGENT_IDENTITY } from '../InstructionBuilder';\nimport type { LLMCreateParamsStreaming } from '../llm/ILLM';\nimport {\n type CompletionUsage,\n type ExtendedChatCompletionChunk,\n type FinishReason,\n type InternalEnrichedAssistantMessage,\n type InternalEnrichedToolCall,\n type LLMToolMessage,\n type LLMUserMessage,\n type RawAssistantMessage,\n} from '../llm/LLMTypes';\nimport { toOpenAIResponseFormat } from '../llm/responseFormat';\nimport { toOpenAIChatMessage } from '../llm/toOpenAIChatMessage';\nimport { estimateTokensForString } from '../llm/usage';\nimport { convertMCPServersToTools, type ConvertToolsResult, type MappedMCPTool } from '../mcp/convertMCPServers';\nimport { executeToolCalls } from '../mcp/executeToolCalls';\nimport type { IToolSet, MCPAuthRequired } from '../mcp/IMCPServer';\nimport type { Sandbox, SandboxInfo } from '../sandbox/Sandbox';\nimport type { AgentTracing } from '../tracing/AgentTracing';\nimport type { AgentDefinition } from './AgentDefinition';\nimport type {\n AgentThreadConstructorInput,\n AgentThreadRuntimeSendBatch,\n AgentThreadRuntimeSendInput,\n AgentThreadSnapshot,\n} from './AgentThread.types';\nimport {\n InternalEventType,\n type AgentThreadAppendContext,\n type AgentThreadEvent,\n type ContextMessage,\n type InternalCapabilityStateEvent,\n type InternalMCPAuthRequiredEvent,\n type InternalThreadDoneEvent,\n type SubAgentCompletionMarker,\n} from './AgentThread.types';\nimport {\n currentContextUsageFromCompletion,\n getEmptyCurrentContextUsage,\n mergeCurrentContextUsage,\n type CurrentContextUsage,\n} from './contextUsage';\nimport {\n assistantMessageContentToStringForSubAgent,\n estimateTokensForContextMessages,\n INTERNAL_SYSTEM_PROMPT,\n isApprovalDecisionMessage,\n isClientSideToolResponseMessage,\n isInputUserMessage,\n isLLMContextMessage,\n isLLMToolMessage,\n makeUnknownToolInfo,\n scanApprovalDecisions,\n toEnrichedToolCall,\n toToolCallInfo,\n} from './contextUtils';\nimport { DeferredTool } from './DeferredTool';\nimport { createEmptyAgentThreadMetrics, updateMetricsFromUsage, type AgentThreadMetrics } from './metrics';\nimport { getClosableOpenToolCallIds, OpenToolCallCloser } from './OpenToolCallCloser';\nimport { isEmptyMessageContent, processAgentUserInput, type AgentInputUserMessage } from './UserInputMessage';\n\nconst DEFAULT_ITERATION_LIMIT = 25;\n\ntype AgentThreadState = 'llm-call-required' | 'tool-response-required' | 'user-input-required';\n\ntype StepOutcome = 'exit' | 'continue';\n\nconst VALID_TRANSITIONS: Record<AgentThreadState, AgentThreadState[]> = {\n 'llm-call-required': ['tool-response-required', 'user-input-required'],\n 'tool-response-required': ['llm-call-required'],\n // user-input-required transitions to:\n // tool-response-required — after approval decisions are appended (approval flow)\n // llm-call-required — after client-side tool responses resolve tool calls directly\n 'user-input-required': ['tool-response-required', 'llm-call-required'],\n};\n\nfunction assertValidTransition(from: AgentThreadState, to: AgentThreadState): void {\n if (!VALID_TRANSITIONS[from].includes(to)) {\n throw new Error(`Invalid state transition: ${from} → ${to}`);\n }\n}\n\nfunction deriveAgentThreadState(context: ContextMessage[]): AgentThreadState {\n const openToolCallIds = getOpenToolCallIds(context);\n if (openToolCallIds.size === 0) return 'llm-call-required';\n\n const assistant = lastAssistantInContext(context);\n const decisions = scanApprovalDecisions(context);\n const hasPendingApproval = assistant?.tool_calls?.some(\n tc => openToolCallIds.has(tc.id) && tc.tool_info.is_approval_required === true && !decisions.has(tc.id),\n );\n const hasPendingClientSideTool = assistant?.tool_calls?.some(\n tc => openToolCallIds.has(tc.id) && tc.tool_info.is_client_side === true,\n );\n return hasPendingApproval || hasPendingClientSideTool ? 'user-input-required' : 'tool-response-required';\n}\n\nfunction hasToolCalls(message: InternalEnrichedAssistantMessage): boolean {\n return Boolean(message.tool_calls && message.tool_calls.length > 0);\n}\n\n// Tool call ids issued by the last assistant message that have no matching\n// tool response after it. Walks the context tail-first and stops at the last\n// assistant message — under the invariant that older assistant tool_calls are\n// already resolved, only the last assistant message can have open ids.\nfunction getOpenToolCallIds(context: ContextMessage[]): Set<string> {\n const resolvedToolCallIds = new Set<string>();\n const openToolCallIds = new Set<string>();\n for (let i = context.length - 1; i >= 0; i--) {\n const msg = context[i];\n if (msg === undefined) continue;\n if (!isLLMContextMessage(msg)) continue;\n if (msg.role === 'tool') {\n resolvedToolCallIds.add(msg.tool_call_id);\n continue;\n }\n if (msg.role === 'assistant') {\n for (const tc of msg.tool_calls ?? []) openToolCallIds.add(tc.id);\n for (const id of resolvedToolCallIds) openToolCallIds.delete(id);\n break;\n }\n }\n return openToolCallIds;\n}\n\nfunction lastAssistantInContext(context: ContextMessage[]): InternalEnrichedAssistantMessage | undefined {\n return context.findLast(\n (msg): msg is InternalEnrichedAssistantMessage => isLLMContextMessage(msg) && msg.role === 'assistant',\n );\n}\n\n// Open tool calls that block a new user message: the open set minus those OpenToolCallCloser will\n// auto-close during preSend. Lets a user message resume a thread whose only open calls are dangling\n// regular tool calls (which the closer repairs), while still blocking on approval/client-side/\n// sub-agent calls that genuinely need resolution. Takes the already-computed open set; copies it\n// since it mutates (deletes) the closable ids.\nfunction getUnclosableOpenToolCallIds(context: ContextMessage[], openToolCallIds: Set<string>): Set<string> {\n const blockingOpenToolCallIds = new Set(openToolCallIds);\n for (const id of getClosableOpenToolCallIds(context)) {\n blockingOpenToolCallIds.delete(id);\n }\n return blockingOpenToolCallIds;\n}\n\nfunction buildMCPInitializeEvent(initInfo: MCPServerInitInfo[], threadId: string): MCPInitializeEvent {\n return {\n type: EventType.MCP_INITIALIZE,\n id: newEventId(),\n created_at: new Date().toISOString(),\n thread_id: threadId,\n mcp_servers: initInfo,\n };\n}\n\nfunction buildMCPAuthRequiredEvent(\n authRequirementInfo: MCPAuthRequired[],\n threadId: string,\n): InternalMCPAuthRequiredEvent {\n return {\n type: InternalEventType.MCP_AUTH_REQUIRED,\n id: newEventId(),\n created_at: new Date().toISOString(),\n mcp_servers: authRequirementInfo.flatMap(or => or.servers.map(s => ({ ...s, thread_ids: [threadId] }))),\n // threadId identifies which thread triggered auth for each server so AgentThreadOrchestrator can merge\n // auth events across parallel sub-agents by server.\n thread_id: null,\n };\n}\n\nfunction buildSandboxCreatedEvent(info: SandboxInfo): SandboxCreatedEvent {\n return {\n type: EventType.SANDBOX_CREATED,\n id: newEventId(),\n created_at: new Date().toISOString(),\n ...info,\n thread_id: null,\n };\n}\n\nfunction buildModelMessageEvent({\n assistantMessage,\n threadId,\n finishReason,\n usage,\n id,\n}: {\n assistantMessage: InternalEnrichedAssistantMessage;\n threadId: string;\n finishReason: FinishReason | null;\n usage: ModelMessageUsage | undefined;\n id: string;\n}): ModelMessageEvent {\n // `thinking_blocks` / `source` stay on the context message for replay; strip them from the client event.\n const { role, tool_calls, thinking_blocks, source, ...rest } = assistantMessage;\n void role;\n void thinking_blocks;\n void source;\n const event: ModelMessageEvent = {\n ...rest,\n tool_calls: tool_calls?.map(toEnrichedToolCall),\n type: EventType.MODEL_MESSAGE,\n id,\n created_at: new Date().toISOString(),\n thread_id: threadId,\n finish_reason: finishReason,\n ...(usage && { usage }),\n };\n return event;\n}\n\nfunction validateUserMessage(\n message: { content: AgentInputUserMessage['content'] },\n blockingOpenToolCallIds: Set<string>,\n index: number,\n): void {\n if (isEmptyMessageContent(message.content)) {\n throw new InvalidAgentSendInputError(`messages[${String(index)}] user message has empty content`);\n }\n if (blockingOpenToolCallIds.size > 0) {\n throw new InvalidAgentSendInputError('user message cannot be sent while approvals or questions are pending');\n }\n}\n\nfunction validateToolMessage(\n message: LLMToolMessage | UserToolResponseMessage,\n openToolCallIds: Set<string>,\n index: number,\n): void {\n if (!openToolCallIds.has(message.tool_call_id)) {\n throw new InvalidAgentSendInputError(\n `messages[${String(index)}] no open tool call for tool_call_id '${message.tool_call_id}'`,\n );\n }\n}\n\nfunction validateApprovalMessage(\n message: UserToolApprovalMessage,\n pendingApprovalIds: Set<string>,\n index: number,\n): void {\n if (!pendingApprovalIds.has(message.tool_call_id)) {\n throw new InvalidAgentSendInputError(\n `messages[${String(index)}] no pending approval for tool_call_id '${message.tool_call_id}'`,\n );\n }\n}\n\nfunction getPendingApprovalToolCalls(context: ContextMessage[]): InternalEnrichedToolCall[] {\n const openToolCallIds = getOpenToolCallIds(context);\n const decisions = scanApprovalDecisions(context);\n const assistant = lastAssistantInContext(context);\n return (assistant?.tool_calls ?? []).filter(\n tc => openToolCallIds.has(tc.id) && tc.tool_info.is_approval_required === true && !decisions.has(tc.id),\n );\n}\n\nfunction getPendingClientSideToolCalls(context: ContextMessage[]): InternalEnrichedToolCall[] {\n const openToolCallIds = getOpenToolCallIds(context);\n const assistant = lastAssistantInContext(context);\n return (assistant?.tool_calls ?? []).filter(tc => openToolCallIds.has(tc.id) && tc.tool_info.is_client_side === true);\n}\n\nfunction validateInputMessageTypesGivenContext(\n context: ContextMessage[],\n messages: AgentThreadRuntimeSendInput[],\n): void {\n // Full open set: validates incoming tool responses and dedupes within the batch.\n const openToolCallIds = getOpenToolCallIds(context);\n // Subset that blocks a fresh user message: excludes calls OpenToolCallCloser will auto-close\n // during preSend, so a dangling regular tool call doesn't reject a user message it will repair.\n const blockingOpenToolCallIds = getUnclosableOpenToolCallIds(context, openToolCallIds);\n const pendingApprovalIds = new Set(getPendingApprovalToolCalls(context).map(tc => tc.id));\n const pendingClientSideIds = new Set(getPendingClientSideToolCalls(context).map(tc => tc.id));\n\n for (let i = 0; i < messages.length; i++) {\n const m = messages[i];\n if (m === undefined) continue;\n if (isApprovalDecisionMessage(m)) {\n validateApprovalMessage(m, pendingApprovalIds, i);\n pendingApprovalIds.delete(m.tool_call_id);\n } else if (isInputUserMessage(m)) {\n validateUserMessage(m, blockingOpenToolCallIds, i);\n } else if (isClientSideToolResponseMessage(m) || isLLMToolMessage(m)) {\n validateToolMessage(m, openToolCallIds, i);\n openToolCallIds.delete(m.tool_call_id);\n blockingOpenToolCallIds.delete(m.tool_call_id);\n pendingClientSideIds.delete(m.tool_call_id);\n } else {\n const _exhaustive: never = m;\n throw new InvalidAgentSendInputError(\n `messages[${String(i)}] has unsupported type: ${JSON.stringify(_exhaustive)}`,\n );\n }\n }\n\n // A send for a thread awaiting user input must resolve every pending approval and client-side\n // tool call in the same batch; any left unresolved (including an empty batch) is a blocker.\n if (pendingApprovalIds.size > 0 || pendingClientSideIds.size > 0) {\n const missing = [...pendingApprovalIds, ...pendingClientSideIds];\n throw new InvalidAgentSendInputError(\n `Send batch must resolve all pending tool calls awaiting user input. Missing: ${missing.join(', ')}`,\n );\n }\n}\n\nasync function buildModelMessageDeltaEvent({\n chunk,\n threadId,\n toolMapping,\n usage,\n id,\n logger,\n}: {\n chunk: ExtendedChatCompletionChunk;\n threadId: string;\n toolMapping: Map<string, MappedMCPTool>;\n usage: ModelMessageUsage | undefined;\n id: string;\n logger: Logger;\n}): Promise<ModelMessageDeltaEvent | undefined> {\n const choice = chunk.choices[0];\n const delta = choice?.delta;\n const finishReason = choice?.finish_reason;\n\n if (!delta || (Object.keys(delta).length === 0 && !finishReason && !usage)) {\n return;\n }\n\n // Drop empty deltas that carry no displayable or actionable data\n if (!delta.tool_calls?.length && !delta.content && !delta.reasoning_content && !finishReason && !usage) {\n return;\n }\n\n const toolCalls = delta.tool_calls ?? [];\n for (const toolCall of toolCalls) {\n if (toolCall.function?.name) {\n const toolInfo = toolMapping.get(toolCall.function.name);\n if (!toolInfo) {\n logger.warn(`LLM called unknown tool: Tool ${toolCall.function.name} not found in tool mapping.`);\n toolCall.tool_info = toToolCallInfo(makeUnknownToolInfo(toolCall.function.name));\n continue;\n }\n toolCall.tool_info = toToolCallInfo(\n await toolInfo.toolSet.toolCallInfo({ name: toolInfo.originalToolName }, false /* resolveUnderlyingTool */),\n );\n }\n }\n\n // Strip legacy `function_call` and replay-only `thinking_blocks` so neither reaches the client or delta stream.\n const { role, function_call, thinking_blocks, ...deltaWithoutRole } = delta;\n void role;\n void function_call;\n void thinking_blocks;\n return {\n ...deltaWithoutRole,\n type: EventType.MODEL_MESSAGE_DELTA,\n id,\n thread_id: threadId,\n ...(finishReason && { finish_reason: finishReason }),\n ...(usage && { usage }),\n };\n}\n\nasync function buildContextAssistantMessage(\n assistantMessage: RawAssistantMessage,\n toolMapping: Map<string, MappedMCPTool>,\n): Promise<InternalEnrichedAssistantMessage> {\n // Omit tool_calls when empty; OpenAI rejects `tool_calls: []` on replay.\n if (!assistantMessage.tool_calls?.length) {\n const { tool_calls, ...rest } = assistantMessage;\n void tool_calls;\n return rest;\n }\n\n // Sequential loop instead of Promise.all: the first call populates the MCP server's tool cache\n // (via listTools), making subsequent calls instant cache hits.\n // No race conditions either way but parallelism buys nothing here.\n const enrichedToolCalls = [];\n for (const toolCall of assistantMessage.tool_calls) {\n const toolInfo = toolMapping.get(toolCall.function.name);\n if (!toolInfo) {\n enrichedToolCalls.push({ ...toolCall, tool_info: makeUnknownToolInfo(toolCall.function.name) });\n continue;\n }\n const tool_info = await toolInfo.toolSet.toolCallInfo(\n {\n name: toolInfo.originalToolName,\n arguments: tryParseToolArgs(toolCall.function.arguments),\n },\n // During context persistence, we have the complete message and hence the tool arguments are available.\n // Hence, we resolve the underlying tool to get the tool information.\n true /* resolveUnderlyingTool */,\n );\n enrichedToolCalls.push({ ...toolCall, tool_info });\n }\n return { ...assistantMessage, tool_calls: enrichedToolCalls };\n}\n\nfunction isJsonObject(value: unknown): value is Record<string, unknown> {\n return typeof value === 'object' && value !== null && !Array.isArray(value);\n}\n\n// Args are only used by DeferredTool to delegate to the underlying server.\n// Defensive parse — hallucinated JSON shouldn't crash assistant-message construction.\nfunction tryParseToolArgs(args: string | undefined): Record<string, unknown> {\n if (!args) return {};\n try {\n const parsed: unknown = JSON.parse(args);\n return isJsonObject(parsed) ? parsed : {};\n } catch {\n return {};\n }\n}\n\n// State-sync contract: in-memory state must stay consistent with what the consumer\n// def foo():\n// for x in range(1, 10):\n// yield x\n// # This cannot raise exception\n// # This does not execute if update_redis fails.\n// update_local_context(x)\n// for x in foo():\n// # This can raise exception.\n// update_redis(x)\n\nexport class AgentThread {\n readonly threadId: string;\n readonly parent?: AgentParent | undefined;\n readonly definition: AgentDefinition;\n readonly title: string;\n readonly agentInfo?: AgentInfo | undefined;\n\n private context: ContextMessage[];\n private currentContextUsage: CurrentContextUsage;\n private preSendContextProcessors: PreSendContextProcessor[];\n private preLLMContextProcessors: PreLLMAgentContextProcessor[];\n private preEphemeralLLMContextProcessors: PreLLMEphemeralAgentContextProcessor[];\n private postToolCallContextProcessor: PostToolCallAgentContextProcessor[];\n\n private instruction: string | undefined;\n private toolResponseProcessors: ToolResponseProcessor[];\n private instructionBuilders: readonly ((builder: InstructionBuilder) => void)[];\n private systemToolSets: readonly IToolSet[];\n private deferredTool?: DeferredTool | undefined;\n private convertedTools: ConvertToolsResult | undefined;\n private pendingSandboxCreatedEvents: SandboxCreatedEvent[] = [];\n private sandbox?: Sandbox | undefined;\n private readonly tracing: AgentTracing;\n private readonly logger: Logger;\n\n private metrics: AgentThreadMetrics = createEmptyAgentThreadMetrics();\n private tfyManagedServerNames = new Set<string>();\n\n private contextBusy = false;\n private preSendRanThisTurn = false;\n private currentState: AgentThreadState | null = null;\n private readonly preComputedCompletion?: SubAgentCompletionMarker | undefined;\n /** Mirrored capability KV — source for toSnapshot().capability_state. */\n private capabilityState: CapabilityState = {};\n private readonly capabilityStateKeys: ReadonlySet<string>;\n\n constructor(input: AgentThreadConstructorInput) {\n this.tracing = input.tracing;\n this.logger = input.logger.child({ module: 'AgentThread' });\n this.threadId = input.threadId;\n this.definition = input.definition;\n this.context = input.context ? [...input.context] : [];\n this.title = input.title;\n this.parent = input.parent;\n this.currentContextUsage = input.currentContextUsage ?? getEmptyCurrentContextUsage();\n this.agentInfo = input.agentInfo;\n this.preComputedCompletion = input.preComputedCompletion;\n this.sandbox = input.sandbox;\n\n const capabilities = input.capabilities ?? [];\n this.systemToolSets = capabilities.flatMap(c => c.systemToolSets ?? []);\n this.preLLMContextProcessors = capabilities.flatMap(c => c.preLLMProcessors ?? []);\n this.preEphemeralLLMContextProcessors = capabilities.flatMap(c => c.preLLMEphemeralProcessors ?? []);\n this.postToolCallContextProcessor = capabilities.flatMap(c => c.postToolCallProcessors ?? []);\n this.toolResponseProcessors = capabilities.flatMap(c => c.toolResponseProcessors ?? []);\n this.instructionBuilders = capabilities.flatMap(c => c.instructionBuilders ?? []);\n const capabilityPreSend = capabilities.flatMap(c => c.preSendProcessors ?? []);\n // OpenToolCallCloser is fixed core before contributed preSend processors.\n this.preSendContextProcessors = [new OpenToolCallCloser(), ...capabilityPreSend];\n\n assertUniqueStateKeys(capabilities);\n const claimed = claimCapabilityState(capabilities, input.capabilityState, this.logger);\n this.capabilityState = claimed;\n this.capabilityStateKeys = new Set(\n capabilities.map(c => c.state?.key).filter((k): k is string => typeof k === 'string'),\n );\n for (const capability of capabilities) {\n if (!capability.state) continue;\n const value = claimed[capability.state.key];\n if (value !== undefined) {\n capability.state.load(value);\n }\n }\n\n if (this.definition.toolSets?.length) {\n this.deferredTool = new DeferredTool(this.definition.toolSets, {\n tracing: this.tracing,\n logger: input.logger,\n });\n }\n\n if (this.sandbox) {\n this.sandbox.configureCodeMode(this.definition.toolSets ?? []);\n }\n\n this.instruction = this.buildInstruction(this.definition.instruction);\n }\n\n private buildInstruction(userInstruction?: string): string {\n const identity = this.parent ? SUB_AGENT_IDENTITY : ROOT_AGENT_IDENTITY;\n const builder = InstructionBuilder.createSystemPrompt(identity);\n const capabilities = builder.beginSection('agent-capabilities');\n capabilities.addSection('internal-messages', INTERNAL_SYSTEM_PROMPT);\n\n if (this.sandbox) {\n this.sandbox.buildInstruction(capabilities);\n }\n if (this.deferredTool) {\n this.deferredTool.buildInstruction(capabilities);\n }\n for (const build of this.instructionBuilders) {\n build(capabilities);\n }\n if (!this.parent && userInstruction?.trim()) {\n builder.addSection('user-instructions', userInstruction.trim(), true);\n }\n return builder.build();\n }\n\n public async *send(messages: AgentThreadRuntimeSendBatch): AsyncGenerator<AgentThreadAppendContext, void, unknown> {\n // An empty batch is a no-op only when the thread is not awaiting user input.\n // While awaiting input, fall through so the validator rejects the empty/incomplete batch.\n if (messages.length === 0 && !this.isAwaitingUserInput()) {\n return;\n }\n this.throwIfContextBusy();\n\n this.contextBusy = true;\n try {\n for await (const event of this.executeContextProcessors('preSend')) {\n yield event;\n }\n this.preSendRanThisTurn = true;\n\n validateInputMessageTypesGivenContext(this.context, messages);\n\n const approvals: UserToolApprovalMessage[] = [];\n const clientSideToolResponses: UserToolResponseMessage[] = [];\n const contextMessages: (LLMUserMessage | LLMToolMessage)[] = [];\n\n for (const m of messages) {\n if (isApprovalDecisionMessage(m)) {\n approvals.push(m);\n } else if (isClientSideToolResponseMessage(m)) {\n clientSideToolResponses.push(m);\n } else if (isInputUserMessage(m)) {\n const result = await processAgentUserInput(m, this.sandbox);\n contextMessages.push(result.message);\n if (result.sandboxCreated) {\n this.pendingSandboxCreatedEvents.push(buildSandboxCreatedEvent(result.sandboxCreated));\n }\n } else if (isLLMToolMessage(m)) {\n contextMessages.push(m);\n } else {\n const _exhaustive: never = m;\n throw new InvalidAgentSendInputError(`Unsupported send input: ${JSON.stringify(_exhaustive)}`);\n }\n }\n\n if (approvals.length > 0 || clientSideToolResponses.length > 0) {\n const approvalContext: AgentApprovalDecisionMessage[] = approvals.map(a => ({\n type: EventType.USER_TOOL_APPROVAL,\n tool_call_id: a.tool_call_id,\n approval: a.approval,\n }));\n const toolResponseContext: LLMToolMessage[] = clientSideToolResponses.map(m => ({\n role: 'tool',\n tool_call_id: m.tool_call_id,\n content: m.content,\n }));\n yield* this.appendToContext({\n context: [...approvalContext, ...toolResponseContext],\n output: [],\n currentContextUsage: undefined,\n usage: undefined,\n });\n }\n if (contextMessages.length > 0) {\n yield* this.appendToContext({\n context: contextMessages,\n output: [],\n currentContextUsage: undefined,\n usage: undefined,\n });\n }\n } finally {\n this.contextBusy = false;\n }\n }\n\n private throwIfContextBusy(): void {\n if (this.contextBusy) {\n throw new Error(`context is busy for thread ${this.threadId}`);\n }\n }\n\n private deriveState(): AgentThreadState {\n const next = deriveAgentThreadState(this.context);\n if (this.currentState) {\n assertValidTransition(this.currentState, next);\n }\n this.currentState = next;\n return next;\n }\n\n private *appendToContext(opts: {\n context: ContextMessage[];\n output: AgentOutputEvent[];\n currentContextUsage: CurrentContextUsage | undefined;\n usage: CompletionUsage | undefined;\n completion?: SubAgentCompletionMarker | undefined;\n }): Generator<AgentThreadAppendContext, void, unknown> {\n const { context, output, currentContextUsage, usage, completion } = opts;\n\n const newCurrentContextUsage =\n currentContextUsage ??\n mergeCurrentContextUsage(this.currentContextUsage, estimateTokensForContextMessages(context));\n\n const event: AgentThreadAppendContext = {\n type: InternalEventType.AGENT_CONTEXT_APPEND,\n thread_id: this.threadId,\n context,\n output,\n current_context_usage: newCurrentContextUsage,\n ...(completion && { completion }),\n };\n\n // Update metrics before yield so we still count it if the stream stops here.\n if (usage) {\n updateMetricsFromUsage(this.metrics, usage);\n }\n\n yield event;\n\n this.context = this.context.concat(context);\n this.currentContextUsage = newCurrentContextUsage;\n }\n\n private *overwriteContext(\n payload: AgentContextProcessorOverwriteContext,\n ): Generator<ThreadOverwriteContextEvent, void, unknown> {\n const event: ThreadOverwriteContextEvent = {\n thread_id: this.threadId,\n ...payload,\n };\n // Update metrics before yield so we still count it if the stream stops here.\n updateMetricsFromUsage(this.metrics, payload.usage);\n\n yield event;\n this.context = payload.context;\n this.currentContextUsage = payload.current_context_usage;\n this.metrics.total_summarizations++;\n }\n\n private generateErrorEvent(message: string, output?: ModelMessageEvent): InternalThreadDoneEvent {\n return {\n type: InternalEventType.AGENT_DONE,\n status: 'error',\n thread_id: this.threadId,\n title: this.title,\n error: message,\n parent: this.parent,\n send_to_parent: this.parent\n ? {\n role: 'tool',\n content: message,\n tool_call_id: this.parent.tool_call_id,\n }\n : undefined,\n ...(output && { output }),\n };\n }\n\n public hasOpenToolCallId(toolCallId: string): boolean {\n return getOpenToolCallIds(this.context).has(toolCallId);\n }\n\n // True when this thread is paused waiting on the user to resolve a pending tool\n // approval or a client-side tool response.\n public isAwaitingUserInput(): boolean {\n return (\n getPendingApprovalToolCalls(this.context).length > 0 || getPendingClientSideToolCalls(this.context).length > 0\n );\n }\n\n // Pure validation of an input batch against this thread's current context; throws\n // on an invalid/incomplete batch without mutating the context.\n public validateSendInput(messages: AgentThreadRuntimeSendBatch): void {\n validateInputMessageTypesGivenContext(this.context, messages);\n }\n\n public toSnapshot(): AgentThreadSnapshot {\n const capability_state = Object.keys(this.capabilityState).length > 0 ? { ...this.capabilityState } : null;\n return {\n thread_id: this.threadId,\n context: this.context,\n current_context_usage: this.currentContextUsage,\n parent: this.parent ?? null,\n agent_info: this.agentInfo ?? null,\n completion: this.preComputedCompletion ?? null,\n capability_state,\n };\n }\n\n public getAgentThreadMetrics(): AgentThreadMetrics {\n return { ...this.metrics };\n }\n\n private transformToLLMRequest(tools: ChatCompletionTool[]): LLMCreateParamsStreaming {\n let messages: ChatCompletionMessageParam[] = [];\n\n if (this.instruction) {\n messages.push({\n role: 'system',\n content: this.instruction,\n });\n }\n\n if (this.definition.messages) {\n for (const msg of this.definition.messages) {\n if (isLLMContextMessage(msg)) {\n messages.push(toOpenAIChatMessage(msg));\n }\n }\n }\n\n // NOTE: all this code-golf is to remove `tool_info` before sending the message to Gateway\n // ApprovalDecisionMessage rows are persisted in context but must not be sent to the LLM.\n const contextMessages = this.context.filter(isLLMContextMessage).map(msg => toOpenAIChatMessage(msg));\n\n messages.push(...contextMessages);\n\n for (const processor of this.preEphemeralLLMContextProcessors) {\n messages = processor.processPreLLMEphemeral(messages) ?? messages;\n }\n\n // modelParams may include provider extensions (e.g. reasoning_effort) beyond the SDK's\n // ChatCompletionCreateParamsStreaming field set; assign after constructing the typed body.\n // Model identity is owned by modelClient — do not set `model` on the request.\n const requestBody: LLMCreateParamsStreaming = {\n messages,\n stream: true,\n ...(this.definition.responseFormat !== undefined\n ? { response_format: toOpenAIResponseFormat(this.definition.responseFormat) }\n : {}),\n };\n if (this.definition.modelParams) {\n Object.assign(requestBody, this.definition.modelParams);\n }\n\n if (tools.length > 0) {\n requestBody.tools = tools;\n }\n\n return requestBody;\n }\n\n private computeAssistantMessageUsage(params: {\n requestBody: LLMCreateParamsStreaming;\n usage: CompletionUsage;\n toolMapping: Map<string, MappedMCPTool>;\n }): ModelMessageUsage {\n const { requestBody, usage, toolMapping } = params;\n // Sub-agents have no <user-instructions> section — their agent.instruction is\n // SUB_AGENT_IDENTITY which is harness content, not user-defined instructions.\n const trimmedInstruction = this.definition.instruction?.trim() ?? '';\n const instructionsEstimate = this.parent ? 0 : Math.round(estimateTokensForString(trimmedInstruction));\n\n const skillsEstimate = this.sandbox?.estimateSkillsTokens() ?? 0;\n\n let tfyManagedToolTokens = 0;\n let userToolTokens = 0;\n if (requestBody.tools) {\n for (const tool of requestBody.tools) {\n const toolTokens = Math.round(estimateTokensForString(JSON.stringify(tool)));\n const info = 'function' in tool ? toolMapping.get(tool.function.name) : undefined;\n if (info && this.tfyManagedServerNames.has(info.toolSet.name)) {\n tfyManagedToolTokens += toolTokens;\n } else {\n userToolTokens += toolTokens;\n }\n }\n }\n\n const totalInstructionTokens = Math.round(estimateTokensForString(this.instruction ?? ''));\n const harnessInstructionTokens = Math.max(0, totalInstructionTokens - instructionsEstimate - skillsEstimate);\n const harnessEstimate = harnessInstructionTokens + tfyManagedToolTokens;\n\n const estimatedComponentsTotal = harnessEstimate + skillsEstimate + instructionsEstimate + userToolTokens;\n const messagesEstimate = Math.max(0, usage.input_tokens - estimatedComponentsTotal);\n\n return {\n input_tokens: usage.input_tokens,\n output_tokens: usage.output_tokens,\n cache_read_tokens: usage.cache_read_tokens,\n cache_write_tokens: usage.cache_write_tokens,\n input_tokens_breakdown: {\n harness: harnessEstimate,\n skills: skillsEstimate,\n instructions: instructionsEstimate,\n tool_definitions: userToolTokens,\n messages: messagesEstimate,\n },\n };\n }\n\n private executeContextProcessors(hook: 'preSend'): AsyncGenerator<AgentThreadAppendContext, void, unknown>;\n private executeContextProcessors(\n hook: 'preLLM' | 'postToolCall',\n ): AsyncGenerator<\n | ThreadOverwriteContextEvent\n | AgentThreadAppendContext\n | { type: typeof InternalEventType.PASSTHROUGH; event: RegisteredPassthroughEvent }\n | InternalCapabilityStateEvent,\n void,\n unknown\n >;\n private async *executeContextProcessors(\n hook: 'preSend' | 'preLLM' | 'postToolCall',\n ): AsyncGenerator<\n | ThreadOverwriteContextEvent\n | AgentThreadAppendContext\n | { type: typeof InternalEventType.PASSTHROUGH; event: RegisteredPassthroughEvent }\n | InternalCapabilityStateEvent,\n void,\n unknown\n > {\n let processors: ((\n execution: Readonly<AgentThreadExecutionContext>,\n ) => AsyncIterable<AgentContextProcessorOutput>)[];\n switch (hook) {\n case 'preSend':\n processors = this.preSendContextProcessors.map(p => p.processPreSend.bind(p));\n break;\n case 'preLLM':\n processors = this.preLLMContextProcessors.map(p => p.processPreLLM.bind(p));\n break;\n case 'postToolCall':\n processors = this.postToolCallContextProcessor.map(p => p.processPostToolCall.bind(p));\n break;\n default:\n throw new Error(`Unknown hook: ${String(hook)}`);\n }\n\n const execution: Readonly<AgentThreadExecutionContext> = {\n threadId: this.threadId,\n sandbox: this.sandbox,\n currentContextUsage: this.currentContextUsage,\n context: this.context,\n };\n\n for (const processor of processors) {\n for await (const response of processor(execution)) {\n switch (response.type) {\n case InternalEventType.AGENT_CONTEXT_APPEND:\n yield* this.appendToContext({\n context: response.context,\n output: response.output,\n currentContextUsage: response.current_context_usage ?? this.currentContextUsage,\n usage: undefined,\n });\n break;\n case EventType.AGENT_CONTEXT_OVERWRITE:\n yield* this.overwriteContext(response);\n break;\n case InternalEventType.PASSTHROUGH:\n yield response;\n break;\n case InternalEventType.CAPABILITY_STATE:\n if (!this.capabilityStateKeys.has(response.key)) {\n throw new AgentHarnessError(\n 'capability_state_error',\n `CAPABILITY_STATE key '${response.key}' is not declared by any capability on thread '${this.threadId}'`,\n );\n }\n yield {\n type: InternalEventType.CAPABILITY_STATE,\n thread_id: this.threadId,\n key: response.key,\n state: response.state,\n };\n this.capabilityState[response.key] = response.state;\n break;\n default: {\n const _exhaustive: never = response;\n return _exhaustive;\n }\n }\n }\n }\n }\n\n private async init(): Promise<{\n initializationInfo: MCPServerInitInfo[];\n authRequirementInfo: MCPAuthRequired[];\n }> {\n if (this.convertedTools) {\n return { initializationInfo: [], authRequirementInfo: [] };\n }\n return this.initTools();\n }\n\n private async initTools(): Promise<{\n initializationInfo: MCPServerInitInfo[];\n authRequirementInfo: MCPAuthRequired[];\n }> {\n const tfyManagedServers: IToolSet[] = [...this.systemToolSets];\n if (this.sandbox) {\n tfyManagedServers.push(this.sandbox);\n }\n if (this.deferredTool) {\n tfyManagedServers.push(this.deferredTool);\n }\n const userServers = [...(this.definition.toolSets ?? [])];\n\n const { convertedTools, initializationInfo, authRequirementInfo } = await convertMCPServersToTools({\n tfyManagedServers,\n userServers,\n });\n this.convertedTools = convertedTools;\n this.tfyManagedServerNames = new Set(tfyManagedServers.map(s => s.name));\n return { initializationInfo, authRequirementInfo };\n }\n\n private getConvertedTools(): ConvertToolsResult {\n if (!this.convertedTools) {\n throw new Error('unreachable');\n }\n return this.convertedTools;\n }\n\n private async *stepLLMCall(\n tools: ChatCompletionTool[],\n toolMapping: Map<string, MappedMCPTool>,\n signal?: AbortSignal,\n ): AsyncGenerator<AgentThreadEvent, { outcome: StepOutcome; modelMessageEventId: string }, unknown> {\n const modelMessageEventId = newEventId();\n if (signal?.aborted) {\n return { outcome: 'exit', modelMessageEventId };\n }\n\n for await (const event of this.executeContextProcessors('preLLM')) {\n yield event;\n }\n\n const requestBody = this.transformToLLMRequest(tools);\n const llmStream = this.definition.modelClient.create(requestBody);\n\n // We start the delta stream with a model message event.\n yield {\n type: EventType.MODEL_MESSAGE,\n thread_id: this.threadId,\n created_at: new Date().toISOString(),\n id: modelMessageEventId,\n } satisfies ModelMessageEvent;\n\n let firstDeltaTimestamped = false;\n let result = await llmStream.next();\n let modelMessageUsage: ModelMessageUsage | undefined = undefined;\n while (!result.done) {\n const chunk = result.value;\n if (chunk.usage) {\n modelMessageUsage = this.computeAssistantMessageUsage({\n requestBody,\n usage: chunk.usage,\n toolMapping,\n });\n }\n const event = await buildModelMessageDeltaEvent({\n chunk,\n threadId: this.threadId,\n toolMapping,\n usage: modelMessageUsage,\n id: modelMessageEventId,\n logger: this.logger,\n });\n if (event) {\n if (!firstDeltaTimestamped) {\n firstDeltaTimestamped = true;\n yield { ...event, created_at: new Date().toISOString() };\n } else {\n yield event;\n }\n }\n result = await llmStream.next();\n }\n\n // If the stream was aborted mid-way, result.value.output is only a partial\n // accumulation of the deltas — not the true complete response. Skip the\n // final model.message event to avoid emitting an inconsistent assembled message.\n if (signal?.aborted) {\n return { outcome: 'exit', modelMessageEventId };\n }\n\n // should be computed by this point but in case provider never gives out any delta with usage, compute it now.\n modelMessageUsage ??= this.computeAssistantMessageUsage({\n requestBody,\n usage: result.value.usage,\n toolMapping,\n });\n const assistantMessage: InternalEnrichedAssistantMessage = await buildContextAssistantMessage(\n result.value.output,\n toolMapping,\n );\n const finishReason = result.value.finish_reason;\n const agentAssistantMessage = buildModelMessageEvent({\n assistantMessage,\n threadId: this.threadId,\n finishReason,\n usage: modelMessageUsage,\n id: modelMessageEventId,\n });\n\n let completion: SubAgentCompletionMarker | undefined;\n if (this.parent) {\n if (finishReason === 'length') {\n const errorMessage = assistantMessageContentToStringForSubAgent(\n assistantMessage.content,\n 'max_tokens breached',\n );\n completion = {\n type: 'error',\n output: agentAssistantMessage,\n error_message: errorMessage,\n send_to_parent: { role: 'tool', tool_call_id: this.parent.tool_call_id, content: errorMessage },\n };\n } else if (!hasToolCalls(assistantMessage)) {\n const content = assistantMessageContentToStringForSubAgent(assistantMessage.content);\n completion = {\n type: 'done',\n output: agentAssistantMessage,\n send_to_parent: { role: 'tool', tool_call_id: this.parent.tool_call_id, content },\n };\n }\n }\n\n yield* this.appendToContext({\n context: [assistantMessage],\n output: [agentAssistantMessage],\n currentContextUsage: currentContextUsageFromCompletion(result.value.usage),\n usage: result.value.usage,\n completion,\n });\n\n if (finishReason === 'length') {\n const errorContent = completion?.error_message ?? 'max_tokens breached';\n yield this.generateErrorEvent(errorContent, agentAssistantMessage);\n return { outcome: 'exit', modelMessageEventId };\n }\n\n if (!hasToolCalls(assistantMessage)) {\n yield {\n type: InternalEventType.AGENT_DONE,\n status: 'done',\n thread_id: this.threadId,\n title: this.title,\n output: agentAssistantMessage,\n parent: this.parent,\n send_to_parent: completion?.send_to_parent,\n };\n return { outcome: 'exit', modelMessageEventId };\n }\n\n return { outcome: 'continue', modelMessageEventId };\n }\n\n private async *stepToolResponse(\n toolMapping: Map<string, MappedMCPTool>,\n ): AsyncGenerator<AgentThreadEvent, StepOutcome, unknown> {\n const assistantMessage = lastAssistantInContext(this.context);\n if (!assistantMessage) {\n throw new Error('unreachable');\n }\n\n const openIds = getOpenToolCallIds(this.context);\n const openCalls = assistantMessage.tool_calls?.filter(tc => openIds.has(tc.id)) ?? [];\n const decisions = scanApprovalDecisions(this.context);\n\n const assistantForExecution: InternalEnrichedAssistantMessage = {\n ...assistantMessage,\n tool_calls: openCalls,\n };\n const {\n toolCallResults,\n initializationInfo,\n createThreadEvents,\n sandboxCreated,\n authRequirementInfo,\n approvalRequiredToolCalls,\n clientSideToolCalls,\n events: passthroughEvents,\n } = await executeToolCalls({\n assistantMessage: assistantForExecution,\n toolMapping,\n threadId: this.threadId,\n approvalDecisions: decisions,\n });\n void clientSideToolCalls;\n if (approvalRequiredToolCalls.length > 0) {\n throw new Error('Unreachable');\n }\n this.metrics.total_tool_calls += toolCallResults.length;\n this.metrics.total_sub_agents += createThreadEvents.length;\n\n if (initializationInfo.length > 0) {\n yield buildMCPInitializeEvent(initializationInfo, this.threadId);\n }\n\n if (sandboxCreated) {\n yield buildSandboxCreatedEvent(sandboxCreated);\n }\n\n for (const event of passthroughEvents) {\n yield { type: InternalEventType.PASSTHROUGH, event };\n }\n\n const toolIdsBeforeProcessing = toolCallResults.map(t => t.message.tool_call_id);\n const toolResponseExecution: Readonly<AgentThreadExecutionContext> = {\n threadId: this.threadId,\n sandbox: this.sandbox,\n currentContextUsage: this.currentContextUsage,\n context: this.context,\n };\n for (const processor of this.toolResponseProcessors) {\n const processorResult = await processor.process(toolCallResults, toolResponseExecution);\n if (processorResult.sandboxCreated) {\n yield buildSandboxCreatedEvent(processorResult.sandboxCreated);\n }\n for (const event of processorResult.events ?? []) {\n yield { type: InternalEventType.PASSTHROUGH, event };\n }\n }\n if (toolIdsBeforeProcessing.length !== toolCallResults.length) {\n throw Error('Some tool call processor has removed tool call.');\n }\n const toolIdsAfterProcessing = new Set(toolCallResults.map(t => t.message.tool_call_id));\n\n if (!toolIdsBeforeProcessing.every(id => toolIdsAfterProcessing.has(id))) {\n throw Error('Tool call IDs do not match after processing.');\n }\n\n const agentToolMessages: ToolResponseEvent[] = toolCallResults.map(t => {\n const { role, ...toolMessage } = t.message;\n void role;\n return {\n ...toolMessage,\n type: EventType.TOOL_RESPONSE,\n id: newEventId(),\n created_at: t.completedAt,\n thread_id: this.threadId,\n };\n });\n for (const msg of agentToolMessages) {\n yield msg;\n }\n // tool.response is persisted by the session/response layer when yielded; only mutate context here.\n yield* this.appendToContext({\n context: toolCallResults.map(t => t.message),\n output: [],\n currentContextUsage: undefined,\n usage: undefined,\n });\n\n if (authRequirementInfo.length > 0) {\n yield buildMCPAuthRequiredEvent(authRequirementInfo, this.threadId);\n return 'exit';\n }\n\n for await (const event of this.executeContextProcessors('postToolCall')) {\n yield event;\n }\n for (const event of createThreadEvents) {\n yield event;\n }\n if (createThreadEvents.length > 0) {\n return 'exit';\n }\n\n return 'continue';\n }\n\n private *stepUserInputRequired(modelMessageEventId: string): Generator<AgentThreadEvent, StepOutcome, unknown> {\n const pendingClientSideToolCalls = getPendingClientSideToolCalls(this.context);\n if (pendingClientSideToolCalls.length > 0) {\n const responseRequiredEvent: ToolResponseRequiredEvent = {\n type: EventType.TOOL_RESPONSE_REQUIRED,\n id: newEventId(),\n created_at: new Date().toISOString(),\n thread_id: this.threadId,\n tool_calls: pendingClientSideToolCalls.map(tc => ({ id: tc.id, source_event_id: modelMessageEventId })),\n };\n yield responseRequiredEvent;\n }\n\n const pendingApprovalToolCalls = getPendingApprovalToolCalls(this.context);\n if (pendingApprovalToolCalls.length > 0) {\n const event: ToolApprovalRequiredEvent = {\n type: EventType.TOOL_APPROVAL_REQUIRED,\n id: newEventId(),\n created_at: new Date().toISOString(),\n thread_id: this.threadId,\n tool_calls: pendingApprovalToolCalls.map(({ id }) => ({ id, source_event_id: modelMessageEventId })),\n };\n yield event;\n }\n return 'exit';\n }\n\n private buildReplayEvent(c: SubAgentCompletionMarker): InternalThreadDoneEvent {\n const base = {\n type: InternalEventType.AGENT_DONE,\n thread_id: this.threadId,\n title: this.title,\n parent: this.parent,\n send_to_parent: c.send_to_parent,\n };\n return c.type === 'done'\n ? { ...base, status: 'done', output: c.output }\n : { ...base, status: 'error', error: c.error_message ?? 'Sub-agent errored', output: c.output };\n }\n\n public async *execute(options?: {\n signal?: AbortSignal | undefined;\n }): AsyncGenerator<AgentThreadEvent, void, unknown> {\n const signal = options?.signal;\n\n this.throwIfContextBusy();\n this.contextBusy = true;\n this.currentState = null;\n\n // there should always be this top level try-catch block because agent execution cant raise an error. it should yield an error event.\n try {\n if (this.preComputedCompletion) {\n yield this.buildReplayEvent(this.preComputedCompletion);\n return;\n }\n\n if (!this.preSendRanThisTurn) {\n for await (const event of this.executeContextProcessors('preSend')) {\n yield event;\n }\n }\n this.preSendRanThisTurn = false;\n const { initializationInfo, authRequirementInfo } = await this.tracing.withInitSpan(() => this.init());\n\n if (initializationInfo.length > 0) {\n yield buildMCPInitializeEvent(initializationInfo, this.threadId);\n }\n\n if (authRequirementInfo.length > 0) {\n yield buildMCPAuthRequiredEvent(authRequirementInfo, this.threadId);\n return;\n }\n\n const { tools, toolMapping } = this.getConvertedTools();\n\n const iterationLimit = this.definition.iterationLimit ?? DEFAULT_ITERATION_LIMIT;\n // Starts empty; set only after stepLLMCall in this execute(). That is intentional:\n // user-input-required is only reachable here right after an LLM step that produced\n // pending approval/client-side tools (which sets currentModelMessageEventId first).\n // A resumed turn that is still awaiting user input never reaches this loop — orchestrator\n // send() / validateSendInput rejects empty or incomplete batches before execute runs.\n let currentModelMessageEventId = '';\n\n for (;;) {\n for (;;) {\n const sandboxCreatedEvent = this.pendingSandboxCreatedEvents.shift();\n if (sandboxCreatedEvent === undefined) break;\n yield sandboxCreatedEvent;\n }\n\n const state = this.deriveState();\n let outcome: StepOutcome;\n switch (state) {\n case 'llm-call-required': {\n // Cancel only before network/side-effecting steps (LLM call, tool execution), never before 'user-input-required', so the required event is always emitted once the assistant message is committed.\n if (signal?.aborted) return;\n if (this.metrics.iterations >= iterationLimit) {\n yield this.generateErrorEvent(\n `You have reached iteration limit of ${String(iterationLimit)}, please request again`,\n );\n return;\n }\n this.metrics.iterations++;\n\n const llmResult = yield* this.stepLLMCall(tools, toolMapping, signal);\n outcome = llmResult.outcome;\n currentModelMessageEventId = llmResult.modelMessageEventId;\n break;\n }\n case 'tool-response-required': {\n if (signal?.aborted) return;\n outcome = yield* this.stepToolResponse(toolMapping);\n break;\n }\n case 'user-input-required': {\n // Intentionally no cancellation check here — see comment in 'llm-call-required'.\n // source_event_id comes from currentModelMessageEventId; see comment where it is declared.\n outcome = yield* this.stepUserInputRequired(currentModelMessageEventId);\n break;\n }\n default: {\n throw new Error('unreachable');\n }\n }\n if (outcome === 'exit') return;\n }\n } catch (error) {\n yield this.generateErrorEvent(error instanceof Error ? error.message : 'Unknown error occurred');\n } finally {\n this.contextBusy = false;\n }\n }\n}\n\nfunction assertUniqueStateKeys(capabilities: readonly AgentCapability[]): void {\n const seen = new Set<string>();\n for (const capability of capabilities) {\n const key = capability.state?.key;\n if (!key) continue;\n if (seen.has(key)) {\n throw new AgentHarnessError(\n 'capability_state_error',\n `Duplicate capability state key '${key}' — each key may be claimed by at most one capability`,\n );\n }\n seen.add(key);\n }\n}\n\nfunction claimCapabilityState(\n capabilities: readonly AgentCapability[],\n input: CapabilityState | undefined,\n logger: Logger,\n): CapabilityState {\n if (!input) return {};\n const claimedKeys = new Set(capabilities.map(c => c.state?.key).filter((k): k is string => typeof k === 'string'));\n const claimed: CapabilityState = {};\n for (const [key, value] of Object.entries(input)) {\n if (!claimedKeys.has(key)) {\n logger.warn(`Dropping unclaimed capability_state key '${key}' — no capability declares it`);\n continue;\n }\n claimed[key] = value;\n }\n return claimed;\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../../../src/core/runtime/AgentThread.ts"],"sourcesContent":["import type { ChatCompletionMessageParam, ChatCompletionTool } from 'openai/resources/chat';\nimport type { Logger } from 'winston';\nimport type { AgentCapability, CapabilityState } from '../capabilities/AgentCapability';\nimport type {\n AgentContextProcessorOutput,\n AgentContextProcessorOverwriteContext,\n AgentThreadExecutionContext,\n PostToolCallAgentContextProcessor,\n PreLLMAgentContextProcessor,\n PreLLMEphemeralAgentContextProcessor,\n PreSendContextProcessor,\n} from '../capabilities/AgentContextProcessor';\nimport { SUB_AGENT_IDENTITY } from '../capabilities/builtins/DynamicSubAgents';\nimport type { ToolResponseProcessor } from '../capabilities/ToolResponseProcessor';\nimport { AgentHarnessError, InvalidAgentSendInputError } from '../errors';\nimport type { RegisteredPassthroughEvent } from '../events/PassthroughEvents';\nimport {\n EventType,\n newEventId,\n type AgentApprovalDecisionMessage,\n type AgentInfo,\n type AgentOutputEvent,\n type AgentParent,\n type MCPInitializeEvent,\n type MCPServerInitInfo,\n type ModelMessageDeltaEvent,\n type ModelMessageEvent,\n type ModelMessageUsage,\n type SandboxCreatedEvent,\n type ThreadOverwriteContextEvent,\n type ToolApprovalRequiredEvent,\n type ToolResponseEvent,\n type ToolResponseRequiredEvent,\n type UserToolApprovalMessage,\n type UserToolResponseMessage,\n} from '../events/schema';\nimport { InstructionBuilder, ROOT_AGENT_IDENTITY } from '../InstructionBuilder';\nimport type { LLMCreateParamsStreaming } from '../llm/ILLM';\nimport {\n type CompletionUsage,\n type ExtendedChatCompletionChunk,\n type FinishReason,\n type InternalEnrichedAssistantMessage,\n type InternalEnrichedToolCall,\n type LLMToolMessage,\n type LLMUserMessage,\n type RawAssistantMessage,\n} from '../llm/LLMTypes';\nimport { toOpenAIResponseFormat } from '../llm/responseFormat';\nimport { toOpenAIChatMessage } from '../llm/toOpenAIChatMessage';\nimport { estimateTokensForString } from '../llm/usage';\nimport { convertMCPServersToTools, type ConvertToolsResult, type MappedMCPTool } from '../mcp/convertMCPServers';\nimport { executeToolCalls } from '../mcp/executeToolCalls';\nimport type { IToolSet, MCPAuthRequired } from '../mcp/IMCPServer';\nimport type { Sandbox, SandboxInfo } from '../sandbox/Sandbox';\nimport type { AgentTracing } from '../tracing/AgentTracing';\nimport { describeUnknownError, extractErrorLogFields } from '../util/errorLogFields';\nimport type { AgentDefinition } from './AgentDefinition';\nimport type {\n AgentThreadConstructorInput,\n AgentThreadRuntimeSendBatch,\n AgentThreadRuntimeSendInput,\n AgentThreadSnapshot,\n} from './AgentThread.types';\nimport {\n InternalEventType,\n type AgentThreadAppendContext,\n type AgentThreadEvent,\n type ContextMessage,\n type InternalCapabilityStateEvent,\n type InternalMCPAuthRequiredEvent,\n type InternalThreadDoneEvent,\n type SubAgentCompletionMarker,\n} from './AgentThread.types';\nimport {\n currentContextUsageFromCompletion,\n getEmptyCurrentContextUsage,\n mergeCurrentContextUsage,\n type CurrentContextUsage,\n} from './contextUsage';\nimport {\n assistantMessageContentToStringForSubAgent,\n estimateTokensForContextMessages,\n INTERNAL_SYSTEM_PROMPT,\n isApprovalDecisionMessage,\n isClientSideToolResponseMessage,\n isInputUserMessage,\n isLLMContextMessage,\n isLLMToolMessage,\n makeUnknownToolInfo,\n scanApprovalDecisions,\n toEnrichedToolCall,\n toToolCallInfo,\n} from './contextUtils';\nimport { DeferredTool } from './DeferredTool';\nimport { createEmptyAgentThreadMetrics, updateMetricsFromUsage, type AgentThreadMetrics } from './metrics';\nimport { getClosableOpenToolCallIds, OpenToolCallCloser } from './OpenToolCallCloser';\nimport { isEmptyMessageContent, processAgentUserInput, type AgentInputUserMessage } from './UserInputMessage';\n\nconst DEFAULT_ITERATION_LIMIT = 25;\n\ntype AgentThreadState = 'llm-call-required' | 'tool-response-required' | 'user-input-required';\n\ntype StepOutcome = 'exit' | 'continue';\n\nconst VALID_TRANSITIONS: Record<AgentThreadState, AgentThreadState[]> = {\n 'llm-call-required': ['tool-response-required', 'user-input-required'],\n 'tool-response-required': ['llm-call-required'],\n // user-input-required transitions to:\n // tool-response-required — after approval decisions are appended (approval flow)\n // llm-call-required — after client-side tool responses resolve tool calls directly\n 'user-input-required': ['tool-response-required', 'llm-call-required'],\n};\n\nfunction assertValidTransition(from: AgentThreadState, to: AgentThreadState): void {\n if (!VALID_TRANSITIONS[from].includes(to)) {\n throw new Error(`Invalid state transition: ${from} → ${to}`);\n }\n}\n\nfunction deriveAgentThreadState(context: ContextMessage[]): AgentThreadState {\n const openToolCallIds = getOpenToolCallIds(context);\n if (openToolCallIds.size === 0) return 'llm-call-required';\n\n const assistant = lastAssistantInContext(context);\n const decisions = scanApprovalDecisions(context);\n const hasPendingApproval = assistant?.tool_calls?.some(\n tc => openToolCallIds.has(tc.id) && tc.tool_info.is_approval_required === true && !decisions.has(tc.id),\n );\n const hasPendingClientSideTool = assistant?.tool_calls?.some(\n tc => openToolCallIds.has(tc.id) && tc.tool_info.is_client_side === true,\n );\n return hasPendingApproval || hasPendingClientSideTool ? 'user-input-required' : 'tool-response-required';\n}\n\nfunction hasToolCalls(message: InternalEnrichedAssistantMessage): boolean {\n return Boolean(message.tool_calls && message.tool_calls.length > 0);\n}\n\n// Tool call ids issued by the last assistant message that have no matching\n// tool response after it. Walks the context tail-first and stops at the last\n// assistant message — under the invariant that older assistant tool_calls are\n// already resolved, only the last assistant message can have open ids.\nfunction getOpenToolCallIds(context: ContextMessage[]): Set<string> {\n const resolvedToolCallIds = new Set<string>();\n const openToolCallIds = new Set<string>();\n for (let i = context.length - 1; i >= 0; i--) {\n const msg = context[i];\n if (msg === undefined) continue;\n if (!isLLMContextMessage(msg)) continue;\n if (msg.role === 'tool') {\n resolvedToolCallIds.add(msg.tool_call_id);\n continue;\n }\n if (msg.role === 'assistant') {\n for (const tc of msg.tool_calls ?? []) openToolCallIds.add(tc.id);\n for (const id of resolvedToolCallIds) openToolCallIds.delete(id);\n break;\n }\n }\n return openToolCallIds;\n}\n\nfunction lastAssistantInContext(context: ContextMessage[]): InternalEnrichedAssistantMessage | undefined {\n return context.findLast(\n (msg): msg is InternalEnrichedAssistantMessage => isLLMContextMessage(msg) && msg.role === 'assistant',\n );\n}\n\n// Open tool calls that block a new user message: the open set minus those OpenToolCallCloser will\n// auto-close during preSend. Lets a user message resume a thread whose only open calls are dangling\n// regular tool calls (which the closer repairs), while still blocking on approval/client-side/\n// sub-agent calls that genuinely need resolution. Takes the already-computed open set; copies it\n// since it mutates (deletes) the closable ids.\nfunction getUnclosableOpenToolCallIds(context: ContextMessage[], openToolCallIds: Set<string>): Set<string> {\n const blockingOpenToolCallIds = new Set(openToolCallIds);\n for (const id of getClosableOpenToolCallIds(context)) {\n blockingOpenToolCallIds.delete(id);\n }\n return blockingOpenToolCallIds;\n}\n\nfunction buildMCPInitializeEvent(initInfo: MCPServerInitInfo[], threadId: string): MCPInitializeEvent {\n return {\n type: EventType.MCP_INITIALIZE,\n id: newEventId(),\n created_at: new Date().toISOString(),\n thread_id: threadId,\n mcp_servers: initInfo,\n };\n}\n\nfunction buildMCPAuthRequiredEvent(\n authRequirementInfo: MCPAuthRequired[],\n threadId: string,\n): InternalMCPAuthRequiredEvent {\n return {\n type: InternalEventType.MCP_AUTH_REQUIRED,\n id: newEventId(),\n created_at: new Date().toISOString(),\n mcp_servers: authRequirementInfo.flatMap(or => or.servers.map(s => ({ ...s, thread_ids: [threadId] }))),\n // threadId identifies which thread triggered auth for each server so AgentThreadOrchestrator can merge\n // auth events across parallel sub-agents by server.\n thread_id: null,\n };\n}\n\nfunction buildSandboxCreatedEvent(info: SandboxInfo): SandboxCreatedEvent {\n return {\n type: EventType.SANDBOX_CREATED,\n id: newEventId(),\n created_at: new Date().toISOString(),\n ...info,\n thread_id: null,\n };\n}\n\nfunction buildModelMessageEvent({\n assistantMessage,\n threadId,\n finishReason,\n usage,\n id,\n}: {\n assistantMessage: InternalEnrichedAssistantMessage;\n threadId: string;\n finishReason: FinishReason | null;\n usage: ModelMessageUsage | undefined;\n id: string;\n}): ModelMessageEvent {\n // `thinking_blocks` / `source` stay on the context message for replay; strip them from the client event.\n const { role, tool_calls, thinking_blocks, source, ...rest } = assistantMessage;\n void role;\n void thinking_blocks;\n void source;\n const event: ModelMessageEvent = {\n ...rest,\n tool_calls: tool_calls?.map(toEnrichedToolCall),\n type: EventType.MODEL_MESSAGE,\n id,\n created_at: new Date().toISOString(),\n thread_id: threadId,\n finish_reason: finishReason,\n ...(usage && { usage }),\n };\n return event;\n}\n\nfunction validateUserMessage(\n message: { content: AgentInputUserMessage['content'] },\n blockingOpenToolCallIds: Set<string>,\n index: number,\n): void {\n if (isEmptyMessageContent(message.content)) {\n throw new InvalidAgentSendInputError(`messages[${String(index)}] user message has empty content`);\n }\n if (blockingOpenToolCallIds.size > 0) {\n throw new InvalidAgentSendInputError('user message cannot be sent while approvals or questions are pending');\n }\n}\n\nfunction validateToolMessage(\n message: LLMToolMessage | UserToolResponseMessage,\n openToolCallIds: Set<string>,\n index: number,\n): void {\n if (!openToolCallIds.has(message.tool_call_id)) {\n throw new InvalidAgentSendInputError(\n `messages[${String(index)}] no open tool call for tool_call_id '${message.tool_call_id}'`,\n );\n }\n}\n\nfunction validateApprovalMessage(\n message: UserToolApprovalMessage,\n pendingApprovalIds: Set<string>,\n index: number,\n): void {\n if (!pendingApprovalIds.has(message.tool_call_id)) {\n throw new InvalidAgentSendInputError(\n `messages[${String(index)}] no pending approval for tool_call_id '${message.tool_call_id}'`,\n );\n }\n}\n\nfunction getPendingApprovalToolCalls(context: ContextMessage[]): InternalEnrichedToolCall[] {\n const openToolCallIds = getOpenToolCallIds(context);\n const decisions = scanApprovalDecisions(context);\n const assistant = lastAssistantInContext(context);\n return (assistant?.tool_calls ?? []).filter(\n tc => openToolCallIds.has(tc.id) && tc.tool_info.is_approval_required === true && !decisions.has(tc.id),\n );\n}\n\nfunction getPendingClientSideToolCalls(context: ContextMessage[]): InternalEnrichedToolCall[] {\n const openToolCallIds = getOpenToolCallIds(context);\n const assistant = lastAssistantInContext(context);\n return (assistant?.tool_calls ?? []).filter(tc => openToolCallIds.has(tc.id) && tc.tool_info.is_client_side === true);\n}\n\nfunction validateInputMessageTypesGivenContext(\n context: ContextMessage[],\n messages: AgentThreadRuntimeSendInput[],\n): void {\n // Full open set: validates incoming tool responses and dedupes within the batch.\n const openToolCallIds = getOpenToolCallIds(context);\n // Subset that blocks a fresh user message: excludes calls OpenToolCallCloser will auto-close\n // during preSend, so a dangling regular tool call doesn't reject a user message it will repair.\n const blockingOpenToolCallIds = getUnclosableOpenToolCallIds(context, openToolCallIds);\n const pendingApprovalIds = new Set(getPendingApprovalToolCalls(context).map(tc => tc.id));\n const pendingClientSideIds = new Set(getPendingClientSideToolCalls(context).map(tc => tc.id));\n\n for (let i = 0; i < messages.length; i++) {\n const m = messages[i];\n if (m === undefined) continue;\n if (isApprovalDecisionMessage(m)) {\n validateApprovalMessage(m, pendingApprovalIds, i);\n pendingApprovalIds.delete(m.tool_call_id);\n } else if (isInputUserMessage(m)) {\n validateUserMessage(m, blockingOpenToolCallIds, i);\n } else if (isClientSideToolResponseMessage(m) || isLLMToolMessage(m)) {\n validateToolMessage(m, openToolCallIds, i);\n openToolCallIds.delete(m.tool_call_id);\n blockingOpenToolCallIds.delete(m.tool_call_id);\n pendingClientSideIds.delete(m.tool_call_id);\n } else {\n const _exhaustive: never = m;\n throw new InvalidAgentSendInputError(\n `messages[${String(i)}] has unsupported type: ${JSON.stringify(_exhaustive)}`,\n );\n }\n }\n\n // A send for a thread awaiting user input must resolve every pending approval and client-side\n // tool call in the same batch; any left unresolved (including an empty batch) is a blocker.\n if (pendingApprovalIds.size > 0 || pendingClientSideIds.size > 0) {\n const missing = [...pendingApprovalIds, ...pendingClientSideIds];\n throw new InvalidAgentSendInputError(\n `Send batch must resolve all pending tool calls awaiting user input. Missing: ${missing.join(', ')}`,\n );\n }\n}\n\nasync function buildModelMessageDeltaEvent({\n chunk,\n threadId,\n toolMapping,\n usage,\n id,\n logger,\n}: {\n chunk: ExtendedChatCompletionChunk;\n threadId: string;\n toolMapping: Map<string, MappedMCPTool>;\n usage: ModelMessageUsage | undefined;\n id: string;\n logger: Logger;\n}): Promise<ModelMessageDeltaEvent | undefined> {\n const choice = chunk.choices[0];\n const delta = choice?.delta;\n const finishReason = choice?.finish_reason;\n\n if (!delta || (Object.keys(delta).length === 0 && !finishReason && !usage)) {\n return;\n }\n\n // Drop empty deltas that carry no displayable or actionable data\n if (!delta.tool_calls?.length && !delta.content && !delta.reasoning_content && !finishReason && !usage) {\n return;\n }\n\n const toolCalls = delta.tool_calls ?? [];\n for (const toolCall of toolCalls) {\n if (toolCall.function?.name) {\n const toolInfo = toolMapping.get(toolCall.function.name);\n if (!toolInfo) {\n logger.warn(`LLM called unknown tool: Tool ${toolCall.function.name} not found in tool mapping.`);\n toolCall.tool_info = toToolCallInfo(makeUnknownToolInfo(toolCall.function.name));\n continue;\n }\n toolCall.tool_info = toToolCallInfo(\n await toolInfo.toolSet.toolCallInfo({ name: toolInfo.originalToolName }, false /* resolveUnderlyingTool */),\n );\n }\n }\n\n // Strip legacy `function_call` and replay-only `thinking_blocks` so neither reaches the client or delta stream.\n const { role, function_call, thinking_blocks, ...deltaWithoutRole } = delta;\n void role;\n void function_call;\n void thinking_blocks;\n return {\n ...deltaWithoutRole,\n type: EventType.MODEL_MESSAGE_DELTA,\n id,\n thread_id: threadId,\n ...(finishReason && { finish_reason: finishReason }),\n ...(usage && { usage }),\n };\n}\n\nasync function buildContextAssistantMessage(\n assistantMessage: RawAssistantMessage,\n toolMapping: Map<string, MappedMCPTool>,\n): Promise<InternalEnrichedAssistantMessage> {\n // Omit tool_calls when empty; OpenAI rejects `tool_calls: []` on replay.\n if (!assistantMessage.tool_calls?.length) {\n const { tool_calls, ...rest } = assistantMessage;\n void tool_calls;\n return rest;\n }\n\n // Sequential loop instead of Promise.all: the first call populates the MCP server's tool cache\n // (via listTools), making subsequent calls instant cache hits.\n // No race conditions either way but parallelism buys nothing here.\n const enrichedToolCalls = [];\n for (const toolCall of assistantMessage.tool_calls) {\n const toolInfo = toolMapping.get(toolCall.function.name);\n if (!toolInfo) {\n enrichedToolCalls.push({ ...toolCall, tool_info: makeUnknownToolInfo(toolCall.function.name) });\n continue;\n }\n const tool_info = await toolInfo.toolSet.toolCallInfo(\n {\n name: toolInfo.originalToolName,\n arguments: tryParseToolArgs(toolCall.function.arguments),\n },\n // During context persistence, we have the complete message and hence the tool arguments are available.\n // Hence, we resolve the underlying tool to get the tool information.\n true /* resolveUnderlyingTool */,\n );\n enrichedToolCalls.push({ ...toolCall, tool_info });\n }\n return { ...assistantMessage, tool_calls: enrichedToolCalls };\n}\n\nfunction isJsonObject(value: unknown): value is Record<string, unknown> {\n return typeof value === 'object' && value !== null && !Array.isArray(value);\n}\n\n// Args are only used by DeferredTool to delegate to the underlying server.\n// Defensive parse — hallucinated JSON shouldn't crash assistant-message construction.\nfunction tryParseToolArgs(args: string | undefined): Record<string, unknown> {\n if (!args) return {};\n try {\n const parsed: unknown = JSON.parse(args);\n return isJsonObject(parsed) ? parsed : {};\n } catch {\n return {};\n }\n}\n\n// State-sync contract: in-memory state must stay consistent with what the consumer\n// def foo():\n// for x in range(1, 10):\n// yield x\n// # This cannot raise exception\n// # This does not execute if update_redis fails.\n// update_local_context(x)\n// for x in foo():\n// # This can raise exception.\n// update_redis(x)\n\nexport class AgentThread {\n readonly threadId: string;\n readonly parent?: AgentParent | undefined;\n readonly definition: AgentDefinition;\n readonly title: string;\n readonly agentInfo?: AgentInfo | undefined;\n\n private context: ContextMessage[];\n private currentContextUsage: CurrentContextUsage;\n private preSendContextProcessors: PreSendContextProcessor[];\n private preLLMContextProcessors: PreLLMAgentContextProcessor[];\n private preEphemeralLLMContextProcessors: PreLLMEphemeralAgentContextProcessor[];\n private postToolCallContextProcessor: PostToolCallAgentContextProcessor[];\n\n private instruction: string | undefined;\n private toolResponseProcessors: ToolResponseProcessor[];\n private instructionBuilders: readonly ((builder: InstructionBuilder) => void)[];\n private systemToolSets: readonly IToolSet[];\n private deferredTool?: DeferredTool | undefined;\n private convertedTools: ConvertToolsResult | undefined;\n private pendingSandboxCreatedEvents: SandboxCreatedEvent[] = [];\n private sandbox?: Sandbox | undefined;\n private readonly tracing: AgentTracing;\n private readonly logger: Logger;\n\n private metrics: AgentThreadMetrics = createEmptyAgentThreadMetrics();\n private tfyManagedServerNames = new Set<string>();\n\n private contextBusy = false;\n private preSendRanThisTurn = false;\n private currentState: AgentThreadState | null = null;\n private readonly preComputedCompletion?: SubAgentCompletionMarker | undefined;\n /** Mirrored capability KV — source for toSnapshot().capability_state. */\n private capabilityState: CapabilityState = {};\n private readonly capabilityStateKeys: ReadonlySet<string>;\n\n constructor(input: AgentThreadConstructorInput) {\n this.tracing = input.tracing;\n this.logger = input.logger.child({ module: 'AgentThread' });\n this.threadId = input.threadId;\n this.definition = input.definition;\n this.context = input.context ? [...input.context] : [];\n this.title = input.title;\n this.parent = input.parent;\n this.currentContextUsage = input.currentContextUsage ?? getEmptyCurrentContextUsage();\n this.agentInfo = input.agentInfo;\n this.preComputedCompletion = input.preComputedCompletion;\n this.sandbox = input.sandbox;\n\n const capabilities = input.capabilities ?? [];\n this.systemToolSets = capabilities.flatMap(c => c.systemToolSets ?? []);\n this.preLLMContextProcessors = capabilities.flatMap(c => c.preLLMProcessors ?? []);\n this.preEphemeralLLMContextProcessors = capabilities.flatMap(c => c.preLLMEphemeralProcessors ?? []);\n this.postToolCallContextProcessor = capabilities.flatMap(c => c.postToolCallProcessors ?? []);\n this.toolResponseProcessors = capabilities.flatMap(c => c.toolResponseProcessors ?? []);\n this.instructionBuilders = capabilities.flatMap(c => c.instructionBuilders ?? []);\n const capabilityPreSend = capabilities.flatMap(c => c.preSendProcessors ?? []);\n // OpenToolCallCloser is fixed core before contributed preSend processors.\n this.preSendContextProcessors = [new OpenToolCallCloser(), ...capabilityPreSend];\n\n assertUniqueStateKeys(capabilities);\n const claimed = claimCapabilityState(capabilities, input.capabilityState, this.logger);\n this.capabilityState = claimed;\n this.capabilityStateKeys = new Set(\n capabilities.map(c => c.state?.key).filter((k): k is string => typeof k === 'string'),\n );\n for (const capability of capabilities) {\n if (!capability.state) continue;\n const value = claimed[capability.state.key];\n if (value !== undefined) {\n capability.state.load(value);\n }\n }\n\n if (this.definition.toolSets?.length) {\n this.deferredTool = new DeferredTool(this.definition.toolSets, {\n tracing: this.tracing,\n logger: input.logger,\n });\n }\n\n if (this.sandbox) {\n this.sandbox.configureCodeMode(this.definition.toolSets ?? []);\n }\n\n this.instruction = this.buildInstruction(this.definition.instruction);\n }\n\n private buildInstruction(userInstruction?: string): string {\n const identity = this.parent ? SUB_AGENT_IDENTITY : ROOT_AGENT_IDENTITY;\n const builder = InstructionBuilder.createSystemPrompt(identity);\n const capabilities = builder.beginSection('agent-capabilities');\n capabilities.addSection('internal-messages', INTERNAL_SYSTEM_PROMPT);\n\n if (this.sandbox) {\n this.sandbox.buildInstruction(capabilities);\n }\n if (this.deferredTool) {\n this.deferredTool.buildInstruction(capabilities);\n }\n for (const build of this.instructionBuilders) {\n build(capabilities);\n }\n if (!this.parent && userInstruction?.trim()) {\n builder.addSection('user-instructions', userInstruction.trim(), true);\n }\n return builder.build();\n }\n\n public async *send(messages: AgentThreadRuntimeSendBatch): AsyncGenerator<AgentThreadAppendContext, void, unknown> {\n // An empty batch is a no-op only when the thread is not awaiting user input.\n // While awaiting input, fall through so the validator rejects the empty/incomplete batch.\n if (messages.length === 0 && !this.isAwaitingUserInput()) {\n return;\n }\n this.throwIfContextBusy();\n\n this.contextBusy = true;\n try {\n for await (const event of this.executeContextProcessors('preSend')) {\n yield event;\n }\n this.preSendRanThisTurn = true;\n\n validateInputMessageTypesGivenContext(this.context, messages);\n\n const approvals: UserToolApprovalMessage[] = [];\n const clientSideToolResponses: UserToolResponseMessage[] = [];\n const contextMessages: (LLMUserMessage | LLMToolMessage)[] = [];\n\n for (const m of messages) {\n if (isApprovalDecisionMessage(m)) {\n approvals.push(m);\n } else if (isClientSideToolResponseMessage(m)) {\n clientSideToolResponses.push(m);\n } else if (isInputUserMessage(m)) {\n const result = await processAgentUserInput(m, this.sandbox);\n contextMessages.push(result.message);\n if (result.sandboxCreated) {\n this.pendingSandboxCreatedEvents.push(buildSandboxCreatedEvent(result.sandboxCreated));\n }\n } else if (isLLMToolMessage(m)) {\n contextMessages.push(m);\n } else {\n const _exhaustive: never = m;\n throw new InvalidAgentSendInputError(`Unsupported send input: ${JSON.stringify(_exhaustive)}`);\n }\n }\n\n if (approvals.length > 0 || clientSideToolResponses.length > 0) {\n const approvalContext: AgentApprovalDecisionMessage[] = approvals.map(a => ({\n type: EventType.USER_TOOL_APPROVAL,\n tool_call_id: a.tool_call_id,\n approval: a.approval,\n }));\n const toolResponseContext: LLMToolMessage[] = clientSideToolResponses.map(m => ({\n role: 'tool',\n tool_call_id: m.tool_call_id,\n content: m.content,\n }));\n yield* this.appendToContext({\n context: [...approvalContext, ...toolResponseContext],\n output: [],\n currentContextUsage: undefined,\n usage: undefined,\n });\n }\n if (contextMessages.length > 0) {\n yield* this.appendToContext({\n context: contextMessages,\n output: [],\n currentContextUsage: undefined,\n usage: undefined,\n });\n }\n } finally {\n this.contextBusy = false;\n }\n }\n\n private throwIfContextBusy(): void {\n if (this.contextBusy) {\n throw new Error(`context is busy for thread ${this.threadId}`);\n }\n }\n\n private deriveState(): AgentThreadState {\n const next = deriveAgentThreadState(this.context);\n if (this.currentState) {\n assertValidTransition(this.currentState, next);\n }\n this.currentState = next;\n return next;\n }\n\n private *appendToContext(opts: {\n context: ContextMessage[];\n output: AgentOutputEvent[];\n currentContextUsage: CurrentContextUsage | undefined;\n usage: CompletionUsage | undefined;\n completion?: SubAgentCompletionMarker | undefined;\n }): Generator<AgentThreadAppendContext, void, unknown> {\n const { context, output, currentContextUsage, usage, completion } = opts;\n\n const newCurrentContextUsage =\n currentContextUsage ??\n mergeCurrentContextUsage(this.currentContextUsage, estimateTokensForContextMessages(context));\n\n const event: AgentThreadAppendContext = {\n type: InternalEventType.AGENT_CONTEXT_APPEND,\n thread_id: this.threadId,\n context,\n output,\n current_context_usage: newCurrentContextUsage,\n ...(completion && { completion }),\n };\n\n // Update metrics before yield so we still count it if the stream stops here.\n if (usage) {\n updateMetricsFromUsage(this.metrics, usage);\n }\n\n yield event;\n\n this.context = this.context.concat(context);\n this.currentContextUsage = newCurrentContextUsage;\n }\n\n private *overwriteContext(\n payload: AgentContextProcessorOverwriteContext,\n ): Generator<ThreadOverwriteContextEvent, void, unknown> {\n const event: ThreadOverwriteContextEvent = {\n thread_id: this.threadId,\n ...payload,\n };\n // Update metrics before yield so we still count it if the stream stops here.\n updateMetricsFromUsage(this.metrics, payload.usage);\n\n yield event;\n this.context = payload.context;\n this.currentContextUsage = payload.current_context_usage;\n this.metrics.total_summarizations++;\n }\n\n private generateErrorEvent(message: string, output?: ModelMessageEvent): InternalThreadDoneEvent {\n return {\n type: InternalEventType.AGENT_DONE,\n status: 'error',\n thread_id: this.threadId,\n title: this.title,\n error: message,\n parent: this.parent,\n send_to_parent: this.parent\n ? {\n role: 'tool',\n content: message,\n tool_call_id: this.parent.tool_call_id,\n }\n : undefined,\n ...(output && { output }),\n };\n }\n\n public hasOpenToolCallId(toolCallId: string): boolean {\n return getOpenToolCallIds(this.context).has(toolCallId);\n }\n\n // True when this thread is paused waiting on the user to resolve a pending tool\n // approval or a client-side tool response.\n public isAwaitingUserInput(): boolean {\n return (\n getPendingApprovalToolCalls(this.context).length > 0 || getPendingClientSideToolCalls(this.context).length > 0\n );\n }\n\n // Pure validation of an input batch against this thread's current context; throws\n // on an invalid/incomplete batch without mutating the context.\n public validateSendInput(messages: AgentThreadRuntimeSendBatch): void {\n validateInputMessageTypesGivenContext(this.context, messages);\n }\n\n public toSnapshot(): AgentThreadSnapshot {\n const capability_state = Object.keys(this.capabilityState).length > 0 ? { ...this.capabilityState } : null;\n return {\n thread_id: this.threadId,\n context: this.context,\n current_context_usage: this.currentContextUsage,\n parent: this.parent ?? null,\n agent_info: this.agentInfo ?? null,\n completion: this.preComputedCompletion ?? null,\n capability_state,\n };\n }\n\n public getAgentThreadMetrics(): AgentThreadMetrics {\n return { ...this.metrics };\n }\n\n private transformToLLMRequest(tools: ChatCompletionTool[]): LLMCreateParamsStreaming {\n let messages: ChatCompletionMessageParam[] = [];\n\n if (this.instruction) {\n messages.push({\n role: 'system',\n content: this.instruction,\n });\n }\n\n if (this.definition.messages) {\n for (const msg of this.definition.messages) {\n if (isLLMContextMessage(msg)) {\n messages.push(toOpenAIChatMessage(msg));\n }\n }\n }\n\n // NOTE: all this code-golf is to remove `tool_info` before sending the message to Gateway\n // ApprovalDecisionMessage rows are persisted in context but must not be sent to the LLM.\n const contextMessages = this.context.filter(isLLMContextMessage).map(msg => toOpenAIChatMessage(msg));\n\n messages.push(...contextMessages);\n\n for (const processor of this.preEphemeralLLMContextProcessors) {\n messages = processor.processPreLLMEphemeral(messages) ?? messages;\n }\n\n // modelParams may include provider extensions (e.g. reasoning_effort) beyond the SDK's\n // ChatCompletionCreateParamsStreaming field set; assign after constructing the typed body.\n // Model identity is owned by modelClient — do not set `model` on the request.\n const requestBody: LLMCreateParamsStreaming = {\n messages,\n stream: true,\n ...(this.definition.responseFormat !== undefined\n ? { response_format: toOpenAIResponseFormat(this.definition.responseFormat) }\n : {}),\n };\n if (this.definition.modelParams) {\n Object.assign(requestBody, this.definition.modelParams);\n }\n\n if (tools.length > 0) {\n requestBody.tools = tools;\n }\n\n return requestBody;\n }\n\n private computeAssistantMessageUsage(params: {\n requestBody: LLMCreateParamsStreaming;\n usage: CompletionUsage;\n toolMapping: Map<string, MappedMCPTool>;\n }): ModelMessageUsage {\n const { requestBody, usage, toolMapping } = params;\n // Sub-agents have no <user-instructions> section — their agent.instruction is\n // SUB_AGENT_IDENTITY which is harness content, not user-defined instructions.\n const trimmedInstruction = this.definition.instruction?.trim() ?? '';\n const instructionsEstimate = this.parent ? 0 : Math.round(estimateTokensForString(trimmedInstruction));\n\n const skillsEstimate = this.sandbox?.estimateSkillsTokens() ?? 0;\n\n let tfyManagedToolTokens = 0;\n let userToolTokens = 0;\n if (requestBody.tools) {\n for (const tool of requestBody.tools) {\n const toolTokens = Math.round(estimateTokensForString(JSON.stringify(tool)));\n const info = 'function' in tool ? toolMapping.get(tool.function.name) : undefined;\n if (info && this.tfyManagedServerNames.has(info.toolSet.name)) {\n tfyManagedToolTokens += toolTokens;\n } else {\n userToolTokens += toolTokens;\n }\n }\n }\n\n const totalInstructionTokens = Math.round(estimateTokensForString(this.instruction ?? ''));\n const harnessInstructionTokens = Math.max(0, totalInstructionTokens - instructionsEstimate - skillsEstimate);\n const harnessEstimate = harnessInstructionTokens + tfyManagedToolTokens;\n\n const estimatedComponentsTotal = harnessEstimate + skillsEstimate + instructionsEstimate + userToolTokens;\n const messagesEstimate = Math.max(0, usage.input_tokens - estimatedComponentsTotal);\n\n return {\n input_tokens: usage.input_tokens,\n output_tokens: usage.output_tokens,\n cache_read_tokens: usage.cache_read_tokens,\n cache_write_tokens: usage.cache_write_tokens,\n input_tokens_breakdown: {\n harness: harnessEstimate,\n skills: skillsEstimate,\n instructions: instructionsEstimate,\n tool_definitions: userToolTokens,\n messages: messagesEstimate,\n },\n };\n }\n\n private executeContextProcessors(hook: 'preSend'): AsyncGenerator<AgentThreadAppendContext, void, unknown>;\n private executeContextProcessors(\n hook: 'preLLM' | 'postToolCall',\n ): AsyncGenerator<\n | ThreadOverwriteContextEvent\n | AgentThreadAppendContext\n | { type: typeof InternalEventType.PASSTHROUGH; event: RegisteredPassthroughEvent }\n | InternalCapabilityStateEvent,\n void,\n unknown\n >;\n private async *executeContextProcessors(\n hook: 'preSend' | 'preLLM' | 'postToolCall',\n ): AsyncGenerator<\n | ThreadOverwriteContextEvent\n | AgentThreadAppendContext\n | { type: typeof InternalEventType.PASSTHROUGH; event: RegisteredPassthroughEvent }\n | InternalCapabilityStateEvent,\n void,\n unknown\n > {\n let processors: ((\n execution: Readonly<AgentThreadExecutionContext>,\n ) => AsyncIterable<AgentContextProcessorOutput>)[];\n switch (hook) {\n case 'preSend':\n processors = this.preSendContextProcessors.map(p => p.processPreSend.bind(p));\n break;\n case 'preLLM':\n processors = this.preLLMContextProcessors.map(p => p.processPreLLM.bind(p));\n break;\n case 'postToolCall':\n processors = this.postToolCallContextProcessor.map(p => p.processPostToolCall.bind(p));\n break;\n default:\n throw new Error(`Unknown hook: ${String(hook)}`);\n }\n\n const execution: Readonly<AgentThreadExecutionContext> = {\n threadId: this.threadId,\n sandbox: this.sandbox,\n currentContextUsage: this.currentContextUsage,\n context: this.context,\n };\n\n for (const processor of processors) {\n for await (const response of processor(execution)) {\n switch (response.type) {\n case InternalEventType.AGENT_CONTEXT_APPEND:\n yield* this.appendToContext({\n context: response.context,\n output: response.output,\n currentContextUsage: response.current_context_usage ?? this.currentContextUsage,\n usage: undefined,\n });\n break;\n case EventType.AGENT_CONTEXT_OVERWRITE:\n yield* this.overwriteContext(response);\n break;\n case InternalEventType.PASSTHROUGH:\n yield response;\n break;\n case InternalEventType.CAPABILITY_STATE:\n if (!this.capabilityStateKeys.has(response.key)) {\n throw new AgentHarnessError(\n 'capability_state_error',\n `CAPABILITY_STATE key '${response.key}' is not declared by any capability on thread '${this.threadId}'`,\n );\n }\n yield {\n type: InternalEventType.CAPABILITY_STATE,\n thread_id: this.threadId,\n key: response.key,\n state: response.state,\n };\n this.capabilityState[response.key] = response.state;\n break;\n default: {\n const _exhaustive: never = response;\n return _exhaustive;\n }\n }\n }\n }\n }\n\n private async init(): Promise<{\n initializationInfo: MCPServerInitInfo[];\n authRequirementInfo: MCPAuthRequired[];\n }> {\n if (this.convertedTools) {\n return { initializationInfo: [], authRequirementInfo: [] };\n }\n return this.initTools();\n }\n\n private async initTools(): Promise<{\n initializationInfo: MCPServerInitInfo[];\n authRequirementInfo: MCPAuthRequired[];\n }> {\n const tfyManagedServers: IToolSet[] = [...this.systemToolSets];\n if (this.sandbox) {\n tfyManagedServers.push(this.sandbox);\n }\n if (this.deferredTool) {\n tfyManagedServers.push(this.deferredTool);\n }\n const userServers = [...(this.definition.toolSets ?? [])];\n\n const { convertedTools, initializationInfo, authRequirementInfo } = await convertMCPServersToTools({\n tfyManagedServers,\n userServers,\n });\n this.convertedTools = convertedTools;\n this.tfyManagedServerNames = new Set(tfyManagedServers.map(s => s.name));\n return { initializationInfo, authRequirementInfo };\n }\n\n private getConvertedTools(): ConvertToolsResult {\n if (!this.convertedTools) {\n throw new Error('unreachable');\n }\n return this.convertedTools;\n }\n\n private async *stepLLMCall(\n tools: ChatCompletionTool[],\n toolMapping: Map<string, MappedMCPTool>,\n signal?: AbortSignal,\n ): AsyncGenerator<AgentThreadEvent, { outcome: StepOutcome; modelMessageEventId: string }, unknown> {\n const modelMessageEventId = newEventId();\n if (signal?.aborted) {\n return { outcome: 'exit', modelMessageEventId };\n }\n\n for await (const event of this.executeContextProcessors('preLLM')) {\n yield event;\n }\n\n const requestBody = this.transformToLLMRequest(tools);\n const llmStream = this.definition.modelClient.create(requestBody);\n\n // We start the delta stream with a model message event.\n yield {\n type: EventType.MODEL_MESSAGE,\n thread_id: this.threadId,\n created_at: new Date().toISOString(),\n id: modelMessageEventId,\n } satisfies ModelMessageEvent;\n\n let firstDeltaTimestamped = false;\n let result = await llmStream.next();\n let modelMessageUsage: ModelMessageUsage | undefined = undefined;\n while (!result.done) {\n const chunk = result.value;\n if (chunk.usage) {\n modelMessageUsage = this.computeAssistantMessageUsage({\n requestBody,\n usage: chunk.usage,\n toolMapping,\n });\n }\n const event = await buildModelMessageDeltaEvent({\n chunk,\n threadId: this.threadId,\n toolMapping,\n usage: modelMessageUsage,\n id: modelMessageEventId,\n logger: this.logger,\n });\n if (event) {\n if (!firstDeltaTimestamped) {\n firstDeltaTimestamped = true;\n yield { ...event, created_at: new Date().toISOString() };\n } else {\n yield event;\n }\n }\n result = await llmStream.next();\n }\n\n // If the stream was aborted mid-way, result.value.output is only a partial\n // accumulation of the deltas — not the true complete response. Skip the\n // final model.message event to avoid emitting an inconsistent assembled message.\n if (signal?.aborted) {\n return { outcome: 'exit', modelMessageEventId };\n }\n\n // should be computed by this point but in case provider never gives out any delta with usage, compute it now.\n modelMessageUsage ??= this.computeAssistantMessageUsage({\n requestBody,\n usage: result.value.usage,\n toolMapping,\n });\n const assistantMessage: InternalEnrichedAssistantMessage = await buildContextAssistantMessage(\n result.value.output,\n toolMapping,\n );\n const finishReason = result.value.finish_reason;\n const agentAssistantMessage = buildModelMessageEvent({\n assistantMessage,\n threadId: this.threadId,\n finishReason,\n usage: modelMessageUsage,\n id: modelMessageEventId,\n });\n\n let completion: SubAgentCompletionMarker | undefined;\n if (this.parent) {\n if (finishReason === 'length') {\n const errorMessage = assistantMessageContentToStringForSubAgent(\n assistantMessage.content,\n 'max_tokens breached',\n );\n completion = {\n type: 'error',\n output: agentAssistantMessage,\n error_message: errorMessage,\n send_to_parent: { role: 'tool', tool_call_id: this.parent.tool_call_id, content: errorMessage },\n };\n } else if (!hasToolCalls(assistantMessage)) {\n const content = assistantMessageContentToStringForSubAgent(assistantMessage.content);\n completion = {\n type: 'done',\n output: agentAssistantMessage,\n send_to_parent: { role: 'tool', tool_call_id: this.parent.tool_call_id, content },\n };\n }\n }\n\n yield* this.appendToContext({\n context: [assistantMessage],\n output: [agentAssistantMessage],\n currentContextUsage: currentContextUsageFromCompletion(result.value.usage),\n usage: result.value.usage,\n completion,\n });\n\n if (finishReason === 'length') {\n const errorContent = completion?.error_message ?? 'max_tokens breached';\n yield this.generateErrorEvent(errorContent, agentAssistantMessage);\n return { outcome: 'exit', modelMessageEventId };\n }\n\n if (!hasToolCalls(assistantMessage)) {\n yield {\n type: InternalEventType.AGENT_DONE,\n status: 'done',\n thread_id: this.threadId,\n title: this.title,\n output: agentAssistantMessage,\n parent: this.parent,\n send_to_parent: completion?.send_to_parent,\n };\n return { outcome: 'exit', modelMessageEventId };\n }\n\n return { outcome: 'continue', modelMessageEventId };\n }\n\n private async *stepToolResponse(\n toolMapping: Map<string, MappedMCPTool>,\n ): AsyncGenerator<AgentThreadEvent, StepOutcome, unknown> {\n const assistantMessage = lastAssistantInContext(this.context);\n if (!assistantMessage) {\n throw new Error('unreachable');\n }\n\n const openIds = getOpenToolCallIds(this.context);\n const openCalls = assistantMessage.tool_calls?.filter(tc => openIds.has(tc.id)) ?? [];\n const decisions = scanApprovalDecisions(this.context);\n\n const assistantForExecution: InternalEnrichedAssistantMessage = {\n ...assistantMessage,\n tool_calls: openCalls,\n };\n const {\n toolCallResults,\n initializationInfo,\n createThreadEvents,\n sandboxCreated,\n authRequirementInfo,\n approvalRequiredToolCalls,\n clientSideToolCalls,\n events: passthroughEvents,\n } = await executeToolCalls({\n assistantMessage: assistantForExecution,\n toolMapping,\n threadId: this.threadId,\n approvalDecisions: decisions,\n });\n void clientSideToolCalls;\n if (approvalRequiredToolCalls.length > 0) {\n throw new Error('Unreachable');\n }\n this.metrics.total_tool_calls += toolCallResults.length;\n this.metrics.total_sub_agents += createThreadEvents.length;\n\n if (initializationInfo.length > 0) {\n yield buildMCPInitializeEvent(initializationInfo, this.threadId);\n }\n\n if (sandboxCreated) {\n yield buildSandboxCreatedEvent(sandboxCreated);\n }\n\n for (const event of passthroughEvents) {\n yield { type: InternalEventType.PASSTHROUGH, event };\n }\n\n const toolIdsBeforeProcessing = toolCallResults.map(t => t.message.tool_call_id);\n const toolResponseExecution: Readonly<AgentThreadExecutionContext> = {\n threadId: this.threadId,\n sandbox: this.sandbox,\n currentContextUsage: this.currentContextUsage,\n context: this.context,\n };\n for (const processor of this.toolResponseProcessors) {\n const processorResult = await processor.process(toolCallResults, toolResponseExecution);\n if (processorResult.sandboxCreated) {\n yield buildSandboxCreatedEvent(processorResult.sandboxCreated);\n }\n for (const event of processorResult.events ?? []) {\n yield { type: InternalEventType.PASSTHROUGH, event };\n }\n }\n if (toolIdsBeforeProcessing.length !== toolCallResults.length) {\n throw Error('Some tool call processor has removed tool call.');\n }\n const toolIdsAfterProcessing = new Set(toolCallResults.map(t => t.message.tool_call_id));\n\n if (!toolIdsBeforeProcessing.every(id => toolIdsAfterProcessing.has(id))) {\n throw Error('Tool call IDs do not match after processing.');\n }\n\n const agentToolMessages: ToolResponseEvent[] = toolCallResults.map(t => {\n const { role, ...toolMessage } = t.message;\n void role;\n return {\n ...toolMessage,\n type: EventType.TOOL_RESPONSE,\n id: newEventId(),\n created_at: t.completedAt,\n thread_id: this.threadId,\n };\n });\n for (const msg of agentToolMessages) {\n yield msg;\n }\n // tool.response is persisted by the session/response layer when yielded; only mutate context here.\n yield* this.appendToContext({\n context: toolCallResults.map(t => t.message),\n output: [],\n currentContextUsage: undefined,\n usage: undefined,\n });\n\n if (authRequirementInfo.length > 0) {\n yield buildMCPAuthRequiredEvent(authRequirementInfo, this.threadId);\n return 'exit';\n }\n\n for await (const event of this.executeContextProcessors('postToolCall')) {\n yield event;\n }\n for (const event of createThreadEvents) {\n yield event;\n }\n if (createThreadEvents.length > 0) {\n return 'exit';\n }\n\n return 'continue';\n }\n\n private *stepUserInputRequired(modelMessageEventId: string): Generator<AgentThreadEvent, StepOutcome, unknown> {\n const pendingClientSideToolCalls = getPendingClientSideToolCalls(this.context);\n if (pendingClientSideToolCalls.length > 0) {\n const responseRequiredEvent: ToolResponseRequiredEvent = {\n type: EventType.TOOL_RESPONSE_REQUIRED,\n id: newEventId(),\n created_at: new Date().toISOString(),\n thread_id: this.threadId,\n tool_calls: pendingClientSideToolCalls.map(tc => ({ id: tc.id, source_event_id: modelMessageEventId })),\n };\n yield responseRequiredEvent;\n }\n\n const pendingApprovalToolCalls = getPendingApprovalToolCalls(this.context);\n if (pendingApprovalToolCalls.length > 0) {\n const event: ToolApprovalRequiredEvent = {\n type: EventType.TOOL_APPROVAL_REQUIRED,\n id: newEventId(),\n created_at: new Date().toISOString(),\n thread_id: this.threadId,\n tool_calls: pendingApprovalToolCalls.map(({ id }) => ({ id, source_event_id: modelMessageEventId })),\n };\n yield event;\n }\n return 'exit';\n }\n\n private buildReplayEvent(c: SubAgentCompletionMarker): InternalThreadDoneEvent {\n const base = {\n type: InternalEventType.AGENT_DONE,\n thread_id: this.threadId,\n title: this.title,\n parent: this.parent,\n send_to_parent: c.send_to_parent,\n };\n return c.type === 'done'\n ? { ...base, status: 'done', output: c.output }\n : { ...base, status: 'error', error: c.error_message ?? 'Sub-agent errored', output: c.output };\n }\n\n public async *execute(options?: {\n signal?: AbortSignal | undefined;\n }): AsyncGenerator<AgentThreadEvent, void, unknown> {\n const signal = options?.signal;\n\n this.throwIfContextBusy();\n this.contextBusy = true;\n this.currentState = null;\n\n // there should always be this top level try-catch block because agent execution cant raise an error. it should yield an error event.\n try {\n if (this.preComputedCompletion) {\n yield this.buildReplayEvent(this.preComputedCompletion);\n return;\n }\n\n if (!this.preSendRanThisTurn) {\n for await (const event of this.executeContextProcessors('preSend')) {\n yield event;\n }\n }\n this.preSendRanThisTurn = false;\n const { initializationInfo, authRequirementInfo } = await this.tracing.withInitSpan(() => this.init());\n\n if (initializationInfo.length > 0) {\n yield buildMCPInitializeEvent(initializationInfo, this.threadId);\n }\n\n if (authRequirementInfo.length > 0) {\n yield buildMCPAuthRequiredEvent(authRequirementInfo, this.threadId);\n return;\n }\n\n const { tools, toolMapping } = this.getConvertedTools();\n\n const iterationLimit = this.definition.iterationLimit ?? DEFAULT_ITERATION_LIMIT;\n // Starts empty; set only after stepLLMCall in this execute(). That is intentional:\n // user-input-required is only reachable here right after an LLM step that produced\n // pending approval/client-side tools (which sets currentModelMessageEventId first).\n // A resumed turn that is still awaiting user input never reaches this loop — orchestrator\n // send() / validateSendInput rejects empty or incomplete batches before execute runs.\n let currentModelMessageEventId = '';\n\n for (;;) {\n for (;;) {\n const sandboxCreatedEvent = this.pendingSandboxCreatedEvents.shift();\n if (sandboxCreatedEvent === undefined) break;\n yield sandboxCreatedEvent;\n }\n\n const state = this.deriveState();\n let outcome: StepOutcome;\n switch (state) {\n case 'llm-call-required': {\n // Cancel only before network/side-effecting steps (LLM call, tool execution), never before 'user-input-required', so the required event is always emitted once the assistant message is committed.\n if (signal?.aborted) return;\n if (this.metrics.iterations >= iterationLimit) {\n yield this.generateErrorEvent(\n `You have reached iteration limit of ${String(iterationLimit)}, please request again`,\n );\n return;\n }\n this.metrics.iterations++;\n\n const llmResult = yield* this.stepLLMCall(tools, toolMapping, signal);\n outcome = llmResult.outcome;\n currentModelMessageEventId = llmResult.modelMessageEventId;\n break;\n }\n case 'tool-response-required': {\n if (signal?.aborted) return;\n outcome = yield* this.stepToolResponse(toolMapping);\n break;\n }\n case 'user-input-required': {\n // Intentionally no cancellation check here — see comment in 'llm-call-required'.\n // source_event_id comes from currentModelMessageEventId; see comment where it is declared.\n outcome = yield* this.stepUserInputRequired(currentModelMessageEventId);\n break;\n }\n default: {\n throw new Error('unreachable');\n }\n }\n if (outcome === 'exit') return;\n }\n } catch (error) {\n // Providers / transports often reject with plain objects; instanceof Error would\n // otherwise collapse those into an opaque \"Unknown error occurred\" in Agent Steps.\n this.logger.error('Agent thread execution failed', extractErrorLogFields(error));\n yield this.generateErrorEvent(describeUnknownError(error));\n } finally {\n this.contextBusy = false;\n }\n }\n}\n\nfunction assertUniqueStateKeys(capabilities: readonly AgentCapability[]): void {\n const seen = new Set<string>();\n for (const capability of capabilities) {\n const key = capability.state?.key;\n if (!key) continue;\n if (seen.has(key)) {\n throw new AgentHarnessError(\n 'capability_state_error',\n `Duplicate capability state key '${key}' — each key may be claimed by at most one capability`,\n );\n }\n seen.add(key);\n }\n}\n\nfunction claimCapabilityState(\n capabilities: readonly AgentCapability[],\n input: CapabilityState | undefined,\n logger: Logger,\n): CapabilityState {\n if (!input) return {};\n const claimedKeys = new Set(capabilities.map(c => c.state?.key).filter((k): k is string => typeof k === 'string'));\n const claimed: CapabilityState = {};\n for (const [key, value] of Object.entries(input)) {\n if (!claimedKeys.has(key)) {\n logger.warn(`Dropping unclaimed capability_state key '${key}' — no capability declares it`);\n continue;\n }\n claimed[key] = value;\n }\n return claimed;\n}\n"],"mappings":"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","names":[]}
|
|
@@ -54,14 +54,15 @@ export declare class Sandbox extends LocalToolMCP {
|
|
|
54
54
|
private sandboxInitPromise?;
|
|
55
55
|
private codeExecToolSets;
|
|
56
56
|
private readonly fileDownloadEnabled;
|
|
57
|
-
private readonly
|
|
57
|
+
private readonly requestTimeoutSeconds;
|
|
58
58
|
private readonly execExtraEnv?;
|
|
59
59
|
private readonly skillMounter?;
|
|
60
60
|
private cachedSkillsSection?;
|
|
61
61
|
private readonly mcpClientScriptBase64;
|
|
62
62
|
private readonly logger;
|
|
63
63
|
private readonly resolvedGitCredentialsContent;
|
|
64
|
-
private
|
|
64
|
+
private codeModeDispatcher;
|
|
65
|
+
private codeModeTransport;
|
|
65
66
|
private tools;
|
|
66
67
|
constructor(options: SandboxOptions);
|
|
67
68
|
private buildMcpServersEnvelope;
|
|
@@ -108,14 +109,11 @@ export declare class Sandbox extends LocalToolMCP {
|
|
|
108
109
|
private writeGitCredentials;
|
|
109
110
|
private initSandboxEnvironment;
|
|
110
111
|
/**
|
|
111
|
-
* Lazily
|
|
112
|
-
* Skipped when
|
|
113
|
-
*
|
|
114
|
-
* time — there is no HTTPS fallback.
|
|
112
|
+
* Lazily start Code Mode transport. Single-flight and idempotent inside the transport.
|
|
113
|
+
* Skipped when code mode was never configured. Connect failures resolve to `undefined`
|
|
114
|
+
* (no Code Mode env for that exec); mcp_client then errors at call time — no HTTPS fallback.
|
|
115
115
|
*/
|
|
116
|
-
private
|
|
117
|
-
private connectNatsBridge;
|
|
118
|
-
private attachBridgeInvalidationOnClose;
|
|
116
|
+
private ensureCodeModeStarted;
|
|
119
117
|
close(): Promise<void>;
|
|
120
118
|
}
|
|
121
119
|
//# sourceMappingURL=Sandbox.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Sandbox.d.ts","sourceRoot":"","sources":["../../../src/core/sandbox/Sandbox.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,SAAS,CAAC;AAEtC,OAAO,EAAE,kBAAkB,EAAE,MAAM,uBAAuB,CAAC;AAE3D,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAC;AAC9D,OAAO,EAA6C,KAAK,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAC7F,OAAO,EAAc,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAO/D,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAC;
|
|
1
|
+
{"version":3,"file":"Sandbox.d.ts","sourceRoot":"","sources":["../../../src/core/sandbox/Sandbox.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,SAAS,CAAC;AAEtC,OAAO,EAAE,kBAAkB,EAAE,MAAM,uBAAuB,CAAC;AAE3D,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAC;AAC9D,OAAO,EAA6C,KAAK,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAC7F,OAAO,EAAc,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAO/D,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAC;AAK5D,OAAO,EAAkC,KAAK,eAAe,EAAE,MAAM,qBAAqB,CAAC;AAK3F,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AAE5D,MAAM,WAAW,WAAW;IAC1B,UAAU,EAAE,MAAM,CAAC;CACpB;AAGD,eAAO,MAAM,8BAA8B,MAAM,CAAC;AAOlD,wBAAgB,6BAA6B,CAAC,MAAM,EAAE;IAAE,UAAU,EAAE,MAAM,CAAC;IAAC,aAAa,EAAE,MAAM,CAAA;CAAE,GAAG,MAAM,CAS3G;AA4BD,MAAM,WAAW,iBAAiB;IAChC,QAAQ,EAAE,MAAM,CAAC;IACjB,cAAc,CAAC,EAAE,WAAW,GAAG,SAAS,CAAC;CAC1C;AAED,MAAM,WAAW,cAAc;IAC7B,QAAQ,EAAE,eAAe,CAAC;IAC1B,iBAAiB,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACvC,YAAY,CAAC,EAAE,aAAa,GAAG,SAAS,CAAC;IACzC,mBAAmB,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC;IAC1C,+EAA+E;IAC/E,6BAA6B,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC;IAC1D;;;OAGG;IACH,+BAA+B,EAAE,IAAI,CAAC;IACtC,mEAAmE;IACnE,mBAAmB,EAAE,MAAM,CAAC;IAC5B,mBAAmB,EAAE,MAAM,CAAC;IAC5B,YAAY,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,GAAG,SAAS,CAAC;IAC5D,OAAO,EAAE,YAAY,CAAC;IACtB,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,eAAO,MAAM,sBAAsB,SAAS,CAAC;AAG7C,eAAO,MAAM,wBAAwB,yBAAyB,CAAC;AA8E/D,wBAAgB,sCAAsC,IAAI,MAAM,CAE/D;AAED,eAAO,MAAM,qBAAqB,YAAY,CAAC;AAG/C,qBAAa,OAAQ,SAAQ,YAAY;IACvC,QAAQ,CAAC,IAAI,aAAyB;IACtC,QAAQ,CAAC,WAAW,aAAa;IACjC,SAAkB,WAAW,uDAAuD;IACpF,MAAM,CAAC,QAAQ,CAAC,gBAAgB,kBAA4B;IAE5D,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAkB;IAC3C,OAAO,CAAC,QAAQ,CAAC,iBAAiB,CAAC,CAAqB;IACxD,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAS;IACpC,OAAO,CAAC,mBAAmB,CAA0B;IAErD,OAAO,CAAC,sBAAsB,CAAC,CAAmC;IAClE,OAAO,CAAC,kBAAkB,CAAC,CAA4B;IACvD,OAAO,CAAC,gBAAgB,CAA2B;IACnD,OAAO,CAAC,QAAQ,CAAC,mBAAmB,CAAU;IAC9C,OAAO,CAAC,QAAQ,CAAC,qBAAqB,CAAS;IAC/C,OAAO,CAAC,QAAQ,CAAC,YAAY,CAAC,CAA+C;IAC7E,OAAO,CAAC,QAAQ,CAAC,YAAY,CAAC,CAA4B;IAC1D,OAAO,CAAC,mBAAmB,CAAC,CAAqB;IACjD,OAAO,CAAC,QAAQ,CAAC,qBAAqB,CAAS;IAC/C,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;IAEhC,OAAO,CAAC,QAAQ,CAAC,6BAA6B,CAAgB;IAC9D,OAAO,CAAC,kBAAkB,CAAiC;IAC3D,OAAO,CAAC,iBAAiB,CAAgC;IAEzD,OAAO,CAAC,KAAK,CAOX;IAEF,YAAY,OAAO,EAAE,cAAc,EAqBlC;IAED,OAAO,CAAC,uBAAuB;IAS/B,SAAS,CAAC,QAAQ,kCAEjB;IAED,iBAAiB,CAAC,OAAO,EAAE,SAAS,QAAQ,EAAE,GAAG,IAAI,CAUpD;IAED,oBAAoB,IAAI,MAAM,CAE7B;IAGD,OAAO,CAAC,mBAAmB;IAS3B,gBAAgB,CAAC,OAAO,EAAE,kBAAkB,GAAG,IAAI,CAmBlD;IAED,OAAO,CAAC,uBAAuB;IAO/B,OAAO,CAAC,kBAAkB;IAc1B,OAAO,CAAC,sBAAsB;IAsB9B,OAAO,CAAC,kBAAkB;IAI1B,OAAO,CAAC,eAAe;IA4EvB,OAAO,KAAK,mBAAmB,GAK9B;YAEa,oBAAoB;YA+BpB,UAAU;IA6ClB,oBAAoB,IAAI,OAAO,CAAC;QAAE,GAAG,EAAE,MAAM,CAAC;QAAC,cAAc,EAAE,WAAW,GAAG,SAAS,CAAA;KAAE,CAAC,CAI9F;IAEK,UAAU,CAAC,MAAM,EAAE;QACvB,SAAS,EAAE,MAAM,CAAC;QAClB,QAAQ,EAAE,MAAM,CAAC;QACjB,OAAO,EAAE,MAAM,CAAC;KACjB,GAAG,OAAO,CAAC;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,cAAc,EAAE,WAAW,GAAG,SAAS,CAAA;KAAE,CAAC,CASzE;IAEK,cAAc,CAAC,KAAK,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,OAAO,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAW3G;IAEK,aAAa,CAAC,KAAK,EAAE;QACzB,QAAQ,EAAE,MAAM,CAAC;QACjB,OAAO,EAAE,MAAM,CAAC;QAChB,UAAU,CAAC,EAAE,aAAa,GAAG,SAAS,CAAC;KACxC,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAa7B;IAED;;;OAGG;YACW,wBAAwB;YAQxB,mBAAmB;YAUnB,sBAAsB;IAoCpC;;;;OAIG;YACW,qBAAqB;IAyB7B,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC,CAW3B;CACF"}
|
|
@@ -48,10 +48,10 @@ var import_IMCPServer = require("../mcp/IMCPServer.js");
|
|
|
48
48
|
var import_LocalToolMCP = require("../mcp/LocalToolMCP.js");
|
|
49
49
|
var import_DeferredTool = require("../runtime/DeferredTool.js");
|
|
50
50
|
var import_errorLogFields = require("../util/errorLogFields.js");
|
|
51
|
+
var import_CodeModeDispatcher = require("./codeMode/CodeModeDispatcher.js");
|
|
51
52
|
var import_constants = require("./constants.js");
|
|
52
53
|
var import_Provider = require("./provider/Provider.js");
|
|
53
54
|
var import_SandboxErrors = require("./SandboxErrors.js");
|
|
54
|
-
var import_SandboxNatsBridge = require("./SandboxNatsBridge.js");
|
|
55
55
|
var import_sandboxScripts = require("./sandboxScripts.gen.js");
|
|
56
56
|
var import_constants2 = require("./skills/constants.js");
|
|
57
57
|
var SKILL_DOWNLOAD_TIMEOUT_SECONDS = 180;
|
|
@@ -97,6 +97,8 @@ function injectTraceContextEnv() {
|
|
|
97
97
|
return env;
|
|
98
98
|
}
|
|
99
99
|
function injectMCPClientEnv(params) {
|
|
100
|
+
const codeModeEnv = params.codeModeEnv ?? {};
|
|
101
|
+
const hasCodeModeTransport = Object.keys(codeModeEnv).length > 0;
|
|
100
102
|
return {
|
|
101
103
|
...params.execExtraEnv ?? {},
|
|
102
104
|
...params.env ?? {},
|
|
@@ -104,13 +106,10 @@ function injectMCPClientEnv(params) {
|
|
|
104
106
|
...Object.keys(params.mcpServers).length > 0 && {
|
|
105
107
|
TFY_MCP_SERVERS: Buffer.from(JSON.stringify(params.mcpServers)).toString("base64")
|
|
106
108
|
},
|
|
107
|
-
...
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
// W3C trace context captured per-exec so each NATS request carries the originating
|
|
112
|
-
// Sandbox: exec span as parent. Without this, MCP spans dispatched via the bridge
|
|
113
|
-
// inherit whatever ALS context the NATS callback runs under (stale, shared across execs).
|
|
109
|
+
...codeModeEnv,
|
|
110
|
+
...hasCodeModeTransport && {
|
|
111
|
+
// W3C trace context captured per-exec so each Code Mode request carries the originating
|
|
112
|
+
// Sandbox: exec span as parent.
|
|
114
113
|
...injectTraceContextEnv()
|
|
115
114
|
},
|
|
116
115
|
// Approvals are always enabled: destructive tools cannot run in code mode.
|
|
@@ -149,7 +148,7 @@ var Sandbox = class _Sandbox extends import_LocalToolMCP.LocalToolMCP {
|
|
|
149
148
|
sandboxInitPromise;
|
|
150
149
|
codeExecToolSets = [];
|
|
151
150
|
fileDownloadEnabled;
|
|
152
|
-
|
|
151
|
+
requestTimeoutSeconds;
|
|
153
152
|
execExtraEnv;
|
|
154
153
|
skillMounter;
|
|
155
154
|
cachedSkillsSection;
|
|
@@ -157,7 +156,8 @@ var Sandbox = class _Sandbox extends import_LocalToolMCP.LocalToolMCP {
|
|
|
157
156
|
logger;
|
|
158
157
|
// Pre-resolved credential-store file content (null = clear / no git auth).
|
|
159
158
|
resolvedGitCredentialsContent;
|
|
160
|
-
|
|
159
|
+
codeModeDispatcher;
|
|
160
|
+
codeModeTransport;
|
|
161
161
|
tools = [
|
|
162
162
|
(0, import_LocalToolMCP.defineTool)({
|
|
163
163
|
name: SANDBOX_EXEC_TOOL_NAME,
|
|
@@ -174,7 +174,7 @@ var Sandbox = class _Sandbox extends import_LocalToolMCP.LocalToolMCP {
|
|
|
174
174
|
this.skillMounter = options.skillMounter;
|
|
175
175
|
this.fileDownloadEnabled = options.fileDownloadEnabled ?? false;
|
|
176
176
|
const mcpBoundTimeoutMs = options.mcpRequestTimeoutMs + options.mcpConnectTimeoutMs;
|
|
177
|
-
this.
|
|
177
|
+
this.requestTimeoutSeconds = Math.ceil(mcpBoundTimeoutMs / 1e3) + NATS_REQUEST_TIMEOUT_BUFFER_SECONDS;
|
|
178
178
|
this.execExtraEnv = options.execExtraEnv;
|
|
179
179
|
this.mcpClientScriptBase64 = Buffer.from(import_sandboxScripts.sandboxScripts.mcpClient, "utf-8").toString("base64");
|
|
180
180
|
this.logger = options.logger.child({ module: "Sandbox" });
|
|
@@ -199,7 +199,12 @@ var Sandbox = class _Sandbox extends import_LocalToolMCP.LocalToolMCP {
|
|
|
199
199
|
if (!servers.length) {
|
|
200
200
|
return;
|
|
201
201
|
}
|
|
202
|
+
if (this.codeModeDispatcher !== void 0 || this.codeModeTransport !== void 0) {
|
|
203
|
+
throw new Error("Code Mode is already configured for this Sandbox");
|
|
204
|
+
}
|
|
202
205
|
this.codeExecToolSets = servers;
|
|
206
|
+
this.codeModeDispatcher = new import_CodeModeDispatcher.CodeModeDispatcher({ toolSets: servers, logger: this.logger });
|
|
207
|
+
this.codeModeTransport = this.provider.createCodeModeTransport();
|
|
203
208
|
}
|
|
204
209
|
estimateSkillsTokens() {
|
|
205
210
|
return Math.round((0, import_usage.estimateTokensForString)(this.renderSkillsSection()));
|
|
@@ -383,13 +388,12 @@ var Sandbox = class _Sandbox extends import_LocalToolMCP.LocalToolMCP {
|
|
|
383
388
|
overrides: { sandboxCreated: sandboxCreatedFlag, sandboxInfo }
|
|
384
389
|
});
|
|
385
390
|
}
|
|
386
|
-
const
|
|
391
|
+
const codeModeEnv = await this.ensureCodeModeStarted(sandboxInfo.sandbox_id);
|
|
387
392
|
const mcpClientEnv = injectMCPClientEnv({
|
|
388
393
|
env: input.env,
|
|
389
394
|
mcpServers: this.buildMcpServersEnvelope(),
|
|
390
395
|
execExtraEnv: this.execExtraEnv,
|
|
391
|
-
|
|
392
|
-
natsRequestTimeoutSeconds: this.natsRequestTimeoutSeconds
|
|
396
|
+
codeModeEnv
|
|
393
397
|
});
|
|
394
398
|
const gitAuthEnv = this.resolvedGitCredentialsContent !== null ? buildGitCredentialHelperEnv(this.provider.getGitCredentialsPath(sandboxInfo.sandbox_id)) : {};
|
|
395
399
|
const env = { ...mcpClientEnv, ...gitAuthEnv };
|
|
@@ -499,63 +503,43 @@ var Sandbox = class _Sandbox extends import_LocalToolMCP.LocalToolMCP {
|
|
|
499
503
|
await this.writeGitCredentials();
|
|
500
504
|
}
|
|
501
505
|
/**
|
|
502
|
-
* Lazily
|
|
503
|
-
* Skipped when
|
|
504
|
-
*
|
|
505
|
-
* time — there is no HTTPS fallback.
|
|
506
|
+
* Lazily start Code Mode transport. Single-flight and idempotent inside the transport.
|
|
507
|
+
* Skipped when code mode was never configured. Connect failures resolve to `undefined`
|
|
508
|
+
* (no Code Mode env for that exec); mcp_client then errors at call time — no HTTPS fallback.
|
|
506
509
|
*/
|
|
507
|
-
async
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
510
|
+
async ensureCodeModeStarted(sandboxId) {
|
|
511
|
+
const dispatcher = this.codeModeDispatcher;
|
|
512
|
+
const transport = this.codeModeTransport;
|
|
513
|
+
if (dispatcher === void 0 || transport === void 0) {
|
|
514
|
+
return void 0;
|
|
515
|
+
}
|
|
516
|
+
try {
|
|
517
|
+
const { env } = await transport.start({
|
|
518
|
+
codeModeDispatcher: dispatcher,
|
|
519
|
+
sandboxId,
|
|
520
|
+
requestTimeoutSeconds: this.requestTimeoutSeconds
|
|
521
|
+
});
|
|
522
|
+
return env;
|
|
523
|
+
} catch (e) {
|
|
524
|
+
this.logger.error("Code Mode transport start failed", {
|
|
511
525
|
...(0, import_errorLogFields.extractErrorLogFields)(e),
|
|
512
526
|
sandboxId
|
|
513
527
|
});
|
|
514
|
-
this.natsBridgePromise = void 0;
|
|
515
528
|
return void 0;
|
|
516
|
-
});
|
|
517
|
-
return this.natsBridgePromise;
|
|
518
|
-
}
|
|
519
|
-
async connectNatsBridge(sandboxId) {
|
|
520
|
-
const wsUrl = await this.provider.getNatsBridgeUrl(sandboxId);
|
|
521
|
-
const toolSets = /* @__PURE__ */ new Map();
|
|
522
|
-
for (const server of this.codeExecToolSets) {
|
|
523
|
-
toolSets.set(server.name, server);
|
|
524
529
|
}
|
|
525
|
-
const bridge = await import_SandboxNatsBridge.SandboxNatsBridge.connect({ url: wsUrl, toolSets, logger: this.logger });
|
|
526
|
-
this.logger.info("Sandbox NATS bridge connected", {
|
|
527
|
-
sandboxId,
|
|
528
|
-
toolSetCount: toolSets.size
|
|
529
|
-
});
|
|
530
|
-
this.attachBridgeInvalidationOnClose(bridge, sandboxId);
|
|
531
|
-
return bridge;
|
|
532
530
|
}
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
void bridge.whenClosed().then(() => {
|
|
536
|
-
if (this.natsBridgePromise === cachedPromise) {
|
|
537
|
-
this.natsBridgePromise = void 0;
|
|
538
|
-
this.logger.info("Sandbox NATS bridge closed; cache invalidated, next exec will reconnect", { sandboxId });
|
|
539
|
-
}
|
|
540
|
-
});
|
|
541
|
-
}
|
|
542
|
-
// Tears down per-Sandbox resources. Awaits the in-flight connect (if any) and explicitly
|
|
543
|
-
// closes the bridge — dropping the field alone would leak the WS socket and live
|
|
544
|
-
// subscriptions, and orphan a bridge that finishes connecting after close() returned.
|
|
531
|
+
// Tears down per-Sandbox Code Mode resources. Dispatcher close first (in-flight requests get
|
|
532
|
+
// source: transport), then transport.stop() — always safe whether start succeeded, failed, or never ran.
|
|
545
533
|
async close() {
|
|
546
|
-
|
|
547
|
-
this.
|
|
548
|
-
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
bridge = await pendingPromise;
|
|
552
|
-
} catch {
|
|
553
|
-
}
|
|
554
|
-
if (!bridge) return;
|
|
534
|
+
this.codeModeDispatcher?.close();
|
|
535
|
+
this.codeModeDispatcher = void 0;
|
|
536
|
+
const transport = this.codeModeTransport;
|
|
537
|
+
this.codeModeTransport = void 0;
|
|
538
|
+
if (transport === void 0) return;
|
|
555
539
|
try {
|
|
556
|
-
await
|
|
540
|
+
await transport.stop();
|
|
557
541
|
} catch (e) {
|
|
558
|
-
this.logger.warn("Error
|
|
542
|
+
this.logger.warn("Error stopping Code Mode transport", (0, import_errorLogFields.extractErrorLogFields)(e));
|
|
559
543
|
}
|
|
560
544
|
}
|
|
561
545
|
};
|