@aipack-ai/multi-agent 1.1.5 → 1.1.7
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/index.d.ts +87 -5
- package/dist/index.js +828 -356
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../core/context.ts","../../agent/core/types.ts","../../agent/core/tapable.ts","../../agent/core/request.ts","../../agent/core/context-resource.ts","../../agent/core/task-graph.ts","../../agent/core/extension.ts","../../agent/core/result.ts","../../agent/core/session.ts","../../agent/request/index.ts","../../agent/context-resource/index.ts","../../agent/ai/index.ts","../../agent/ai/errors.ts","../../agent/ai/overflow.ts","../../agent/transformer/index.ts","../../agent/runtime/index.ts","../core/executor.ts","../core/graph.ts","../patterns/pipeline.ts","../patterns/router.ts","../core/supervisor-executor.ts","../patterns/supervisor.ts","../core/debate-executor.ts","../patterns/debate.ts","../core/map-reduce-executor.ts","../patterns/map-reduce.ts","../../mcp/src/client/jsonrpc.ts","../../mcp/src/client/protocol.ts","../../mcp/src/server/host.ts","../extensions/mcp-bridge.ts","../extensions/debug.ts"],"sourcesContent":["/**\n * core/context.ts - SharedContext 实现\n *\n * 提供 EventBus、ToolRegistry 和 SharedContext 的默认实现。\n */\n\nimport type { Tool } from '@aipack-ai/agent';\nimport type { EventBus, ToolRegistry, SharedContext, EventListener } from './types';\n\n// ─── SimpleEventBus ──────────────────────────────────────────────\n\n/** 简单同步事件总线实现 */\nexport class SimpleEventBus implements EventBus {\n private listeners = new Map<string, Set<EventListener>>();\n\n on(event: string, listener: EventListener): this {\n let set = this.listeners.get(event);\n if (!set) {\n set = new Set();\n this.listeners.set(event, set);\n }\n set.add(listener);\n return this;\n }\n\n off(event: string, listener: EventListener): this {\n this.listeners.get(event)?.delete(listener);\n return this;\n }\n\n emit(event: string, data?: unknown): this {\n const set = this.listeners.get(event);\n if (set) {\n for (const listener of set) {\n try {\n listener(data);\n } catch {\n // 防止监听器异常中断事件传播\n }\n }\n }\n return this;\n }\n}\n\n// ─── SimpleToolRegistry ─────────────────────────────────────────\n\n/** 简单工具注册表实现 */\nexport class SimpleToolRegistry implements ToolRegistry {\n private tools = new Map<string, Tool>();\n\n register(tool: Tool): this {\n this.tools.set(tool.name, tool);\n return this;\n }\n\n registerAll(tools: Tool[]): this {\n for (const tool of tools) {\n this.tools.set(tool.name, tool);\n }\n return this;\n }\n\n get(name: string): Tool | undefined {\n return this.tools.get(name);\n }\n\n getAll(): Tool[] {\n return Array.from(this.tools.values());\n }\n\n has(name: string): boolean {\n return this.tools.has(name);\n }\n}\n\n// ─── createSharedContext ────────────────────────────────────────\n\n/** 创建默认 SharedContext */\nexport function createSharedContext(init?: Partial<SharedContext>): SharedContext {\n return {\n blackboard: init?.blackboard ?? new Map(),\n bus: init?.bus ?? new SimpleEventBus(),\n toolRegistry: init?.toolRegistry ?? new SimpleToolRegistry(),\n meta: init?.meta ?? {},\n };\n}\n","/**\n * packages/core/types.ts - 核心类型定义\n *\n * 这是整个框架的类型基础,不依赖任何外部实现。\n * 所有消息、内容块、模型、工具等类型都在此定义。\n */\n\n// ─── 内容块类型 ───────────────────────────────────────────────────\n\nexport interface TextContent {\n type: 'text';\n text: string;\n}\n\nexport interface ImageContent {\n type: 'image';\n data: string; // base64 或 URL\n mimeType: string;\n}\n\nexport interface ToolCallContent {\n type: 'toolCall';\n id: string;\n name: string;\n arguments: unknown;\n}\n\nexport interface ThinkingContent {\n type: 'thinking';\n text: string;\n}\n\nexport type ContentBlock =\n | TextContent\n | ImageContent\n | ToolCallContent\n | ThinkingContent;\n\n// ─── 消息类型 ─────────────────────────────────────────────────────\n\nexport interface BaseMessage {\n role: string;\n content: string | ContentBlock[];\n timestamp: number;\n [key: string]: unknown;\n}\n\nexport interface UserMessage extends BaseMessage {\n role: 'user';\n}\n\nexport interface AssistantMessage extends BaseMessage {\n role: 'assistant';\n model?: string;\n provider?: string;\n stopReason?: string;\n usage?: Usage;\n errorMessage?: string;\n responseId?: string;\n}\n\nexport interface ToolResultMessage extends BaseMessage {\n role: 'toolResult';\n toolCallId: string;\n toolName: string;\n isError: boolean;\n}\n\nexport interface SystemMessage extends BaseMessage {\n role: 'system';\n}\n\nexport type Message = UserMessage | AssistantMessage | ToolResultMessage | SystemMessage;\n\n// ─── Token 用量 ───────────────────────────────────────────────────\n\n/**\n * 用量与费用。与 aipack/ai 的 Usage 结构对齐:\n * cacheRead/cacheWrite/reasoning 为可选字段,旧消费者无需感知。\n */\nexport interface Usage {\n input: number;\n output: number;\n total: number;\n /** 命中缓存读取的 token 数(不计入 input) */\n cacheRead?: number;\n /** 写入缓存的 token 数 */\n cacheWrite?: number;\n /** 推理 token 数(completion 的子集) */\n reasoning?: number;\n /** 还原后的原始 token 总数(input + output + cacheRead + cacheWrite) */\n totalTokens?: number;\n}\n\n// ─── 模型定义 ─────────────────────────────────────────────────────\n\nexport interface Model {\n id: string;\n name: string;\n provider: string;\n contextWindow: number;\n maxTokens: number;\n reasoning: boolean;\n [key: string]: unknown;\n}\n\n// ─── 工具定义 ─────────────────────────────────────────────────────\n\nexport interface ToolResult {\n content: ContentBlock[];\n details: unknown;\n usage?: Usage;\n}\n\nexport interface Tool {\n name: string;\n description: string;\n parameters: unknown; // JSON Schema 或 TypeBox schema\n /**\n * 所需权限能力声明(如 'shell:exec' / 'fs:write' / 'memory:write' / 'network:fetch')。\n * 供框架级 PermissionPolicy 裁决使用;未声明视为安全工具。\n */\n permissions?: string[];\n execute: (\n toolCallId: string,\n args: unknown,\n signal?: AbortSignal,\n ) => Promise<ToolResult>;\n prepareArguments?: (args: unknown) => unknown;\n}\n\n// ─── 上下文 ───────────────────────────────────────────────────────\n\nexport interface Context {\n systemPrompt: string;\n messages: Message[];\n tools?: Tool[];\n}\n\n// ─── 流式事件 ─────────────────────────────────────────────────────\n\nexport interface StreamOptions {\n signal?: AbortSignal;\n reasoning?: string;\n sessionId?: string;\n /** 重试回调:provider 内 retry() 真正退避重试时调用(可观测/埋点用) */\n onRetryAttempt?: (info: { attempt: number; error: unknown; delayMs: number }) => void;\n}\n\nexport type StreamEvent =\n | { type: 'start'; partial: { content: ContentBlock[] } }\n | { type: 'text_delta'; delta: string }\n | { type: 'thinking_delta'; delta: string }\n | { type: 'tool_call_start'; id: string; name: string }\n | { type: 'tool_call_delta'; id: string; delta: string }\n | { type: 'tool_call_end'; id: string }\n | { type: 'done'; message: AssistantMessage }\n | { type: 'error'; message: AssistantMessage };\n\nexport type StreamResult = AsyncIterable<StreamEvent>;\n\n/**\n * 流式函数类型 - 模型提供者需实现此接口\n *\n * 是一个可替换的核心能力。\n * 用户通过提供不同的 streamFn 来接入不同的 LLM 提供商。\n */\nexport type StreamFn = (\n model: Model,\n context: Context,\n options?: StreamOptions,\n) => StreamResult;\n\n// ─── Agent 状态 ───────────────────────────────────────────────────\n\nexport type ThinkingLevel = 'off' | 'minimal' | 'low' | 'medium' | 'high' | 'max';\n\nexport interface AgentState {\n systemPrompt: string;\n model: Model;\n thinkingLevel: ThinkingLevel;\n tools: Tool[];\n messages: Message[];\n isStreaming: boolean;\n streamingMessage?: Message;\n pendingToolCalls: Set<string>;\n errorMessage?: string;\n}\n\n// ─── 工具函数 ─────────────────────────────────────────────────────\n\nexport function extractText(content: string | ContentBlock[]): string {\n if (typeof content === 'string') return content;\n return content\n .filter((c): c is TextContent => c.type === 'text')\n .map(c => c.text)\n .join('');\n}\n\nexport function extractToolCalls(content: string | ContentBlock[]): ToolCallContent[] {\n if (typeof content === 'string') return [];\n return content.filter((c): c is ToolCallContent => c.type === 'toolCall');\n}\n\nexport function createTextContent(text: string): TextContent {\n return { type: 'text', text };\n}\n\nexport function createEmptyUsage(): Usage {\n return { input: 0, output: 0, total: 0 };\n}\n","/**\n * Tapable - 事件钩子系统\n *\n * 提供同步与异步钩子,允许 Extension 在 Runtime 生命周期的关键节点注入逻辑。\n */\n\n// ─── 钩子类型 ─────────────────────────────────────────────────────\n\nexport type TapType = 'sync' | 'async' | 'promise';\n\nexport interface Tap {\n /** 钩子名称(用于调试与去重) */\n name: string;\n /** 钩子类型 */\n type: TapType;\n /** 回调函数 */\n fn: (...args: any[]) => any;\n /** 执行阶段:before / during / after */\n stage?: number;\n}\n\n// ─── SyncHook ─────────────────────────────────────────────────────\n\nexport class SyncHook<TArgs extends any[] = any[]> {\n private taps: Tap[] = [];\n\n constructor(private readonly name: string) {}\n\n tap(name: string, fn: (...args: TArgs) => void, stage?: number): void {\n this.taps.push({ name, type: 'sync', fn, stage: stage ?? 0 });\n this.taps.sort((a, b) => (a.stage ?? 0) - (b.stage ?? 0));\n }\n\n call(...args: TArgs): void {\n for (const tap of this.taps) {\n try {\n tap.fn(...args);\n } catch (err) {\n // 单个 tap 失败不影响其他 tap\n }\n }\n }\n\n isUsed(): boolean {\n return this.taps.length > 0;\n }\n\n clear(): void {\n this.taps = [];\n }\n}\n\n// ─── AsyncSeriesHook ──────────────────────────────────────────────\n\nexport class AsyncSeriesHook<TArgs extends any[] = any[]> {\n private taps: Tap[] = [];\n\n constructor(private readonly name: string) {}\n\n tapPromise(name: string, fn: (...args: TArgs) => Promise<void>, stage?: number): void {\n this.taps.push({ name, type: 'promise', fn, stage: stage ?? 0 });\n this.taps.sort((a, b) => (a.stage ?? 0) - (b.stage ?? 0));\n }\n\n async promise(...args: TArgs): Promise<void> {\n for (const tap of this.taps) {\n try {\n await tap.fn(...args);\n } catch (err) {\n // 单个 tap 失败不影响其他 tap\n }\n }\n }\n\n isUsed(): boolean {\n return this.taps.length > 0;\n }\n\n clear(): void {\n this.taps = [];\n }\n}\n\n// ─── AsyncSeriesWaterfallHook ─────────────────────────────────────\n\nexport class AsyncSeriesWaterfallHook<T = any> {\n private taps: Tap[] = [];\n\n constructor(private readonly name: string) {}\n\n tapPromise(name: string, fn: (value: T, ...rest: any[]) => Promise<T>, stage?: number): void {\n this.taps.push({ name, type: 'promise', fn, stage: stage ?? 0 });\n this.taps.sort((a, b) => (a.stage ?? 0) - (b.stage ?? 0));\n }\n\n async promise(value: T, ...rest: any[]): Promise<T> {\n let current = value;\n for (const tap of this.taps) {\n try {\n current = await tap.fn(current, ...rest);\n } catch (err) {\n // 失败时保持当前值不变\n }\n }\n return current;\n }\n\n isUsed(): boolean {\n return this.taps.length > 0;\n }\n\n clear(): void {\n this.taps = [];\n }\n}\n\n// ─── HookMap ──────────────────────────────────────────────────────\n\nexport class HookMap<THook> {\n private map = new Map<string, THook>();\n\n constructor(private readonly factory: () => THook) {}\n\n for(key: string): THook {\n let hook = this.map.get(key);\n if (!hook) {\n hook = this.factory();\n this.map.set(key, hook);\n }\n return hook;\n }\n\n has(key: string): boolean {\n return this.map.has(key);\n }\n\n get(key: string): THook | undefined {\n return this.map.get(key);\n }\n\n keys(): string[] {\n return Array.from(this.map.keys());\n }\n}\n","/**\n * Request - 请求入口\n *\n * 代表一次 Agent 运行的入口请求,包含用户输入、会话标识与运行选项。\n */\n\n// ─── 请求类型 ─────────────────────────────────────────────────────\n\nexport type RequestType = 'message' | 'stream' | 'continue' | 'replay';\n\n// ─── 请求接口 ─────────────────────────────────────────────────────\n\nexport interface Request {\n /** 用户输入消息 */\n readonly message: string;\n /** 请求类型 */\n readonly type: RequestType;\n /** 通道标识 */\n readonly channel?: string;\n /** 聊天 ID */\n readonly chatId?: string;\n /** 发送者 ID */\n readonly senderId?: string;\n /**\n * 会话标识。同一 Runtime 可服务多个会话(SessionManager / 多租户):\n * 未指定时回退到 Runtime 的默认会话 key(createRuntime 的 sessionKey)。\n * 不同 sessionKey 的请求消息历史相互隔离、串行队列独立。\n */\n readonly sessionKey?: string;\n /** 媒体附件 */\n readonly media?: string[];\n /** 是否临时会话(不持久化) */\n readonly ephemeral?: boolean;\n /** 指定模型 */\n readonly model?: string;\n /** 指定模型预设 */\n readonly modelPreset?: string;\n /** 额外元数据 */\n readonly metadata?: Record<string, unknown>;\n}\n\n// ─── 请求构建器 ───────────────────────────────────────────────────\n\nexport class RequestBuilder {\n private _message: string = '';\n private _type: RequestType = 'message';\n private _channel?: string;\n private _chatId?: string;\n private _senderId?: string;\n private _media?: string[];\n private _ephemeral?: boolean;\n private _model?: string;\n private _modelPreset?: string;\n private _sessionKey?: string;\n private _metadata: Record<string, unknown> = {};\n\n message(msg: string): this {\n this._message = msg;\n return this;\n }\n\n type(t: RequestType): this {\n this._type = t;\n return this;\n }\n\n channel(ch: string): this {\n this._channel = ch;\n return this;\n }\n\n chatId(id: string): this {\n this._chatId = id;\n return this;\n }\n\n senderId(id: string): this {\n this._senderId = id;\n return this;\n }\n\n media(m: string[]): this {\n this._media = m;\n return this;\n }\n\n ephemeral(e: boolean): this {\n this._ephemeral = e;\n return this;\n }\n\n model(m: string): this {\n this._model = m;\n return this;\n }\n\n modelPreset(p: string): this {\n this._modelPreset = p;\n return this;\n }\n\n metadata(key: string, value: unknown): this {\n this._metadata[key] = value;\n return this;\n }\n\n /** 指定会话 key(多会话运行时按此路由到对应会话) */\n sessionKey(key: string): this {\n this._sessionKey = key;\n return this;\n }\n\n build(): Request {\n return {\n message: this._message,\n type: this._type,\n channel: this._channel,\n chatId: this._chatId,\n senderId: this._senderId,\n sessionKey: this._sessionKey,\n media: this._media,\n ephemeral: this._ephemeral,\n model: this._model,\n modelPreset: this._modelPreset,\n metadata: this._metadata,\n };\n }\n}\n\nexport function createRequest(message: string, options?: Partial<Request>): Request {\n return {\n message,\n type: 'message',\n ...options,\n };\n}\n","/**\n * ContextResource - 上下文资源\n *\n * 代表上下文中的单个资源单元(消息、工具调用、工具结果、状态快照等)。\n * 每个 Resource 拥有唯一标识,并可声明对其他 Resource 的依赖。\n */\n\n// ─── 资源类型 ─────────────────────────────────────────────────────\n\nexport type ResourceType =\n | 'user_message'\n | 'assistant_message'\n | 'tool_call'\n | 'tool_result'\n | 'system_message'\n | 'state_snapshot'\n | 'compaction_summary'\n | 'custom';\n\nexport type ResourceRole = 'user' | 'assistant' | 'toolResult' | 'system' | string;\n\n// ─── 资源接口 ─────────────────────────────────────────────────────\n\nexport interface ContextResource {\n /** 唯一标识 */\n readonly id: string;\n /** 资源类型 */\n readonly type: ResourceType;\n /** 消息角色 */\n readonly role: ResourceRole;\n /** 资源内容(消息体或工具数据) */\n readonly content: unknown;\n /** 时间戳 */\n readonly timestamp: number;\n /** 依赖的其他资源 ID(如 tool_result 依赖 tool_call) */\n readonly dependencies: string[];\n /** 资源元数据 */\n readonly meta: Record<string, unknown>;\n /** 是否为关键资源(压缩时不可移除) */\n readonly pinned: boolean;\n}\n\n// ─── 资源构建器 ───────────────────────────────────────────────────\n\nexport class ContextResourceBuilder {\n private _id: string;\n private _type: ResourceType = 'custom';\n private _role: ResourceRole = 'user';\n private _content: unknown = '';\n private _timestamp: number = Date.now();\n private _dependencies: string[] = [];\n private _meta: Record<string, unknown> = {};\n private _pinned: boolean = false;\n\n constructor(id?: string) {\n this._id = id || `res_${Date.now()}_${Math.random().toString(36).slice(2, 8)}`;\n }\n\n id(id: string): this {\n this._id = id;\n return this;\n }\n\n type(t: ResourceType): this {\n this._type = t;\n return this;\n }\n\n role(r: ResourceRole): this {\n this._role = r;\n return this;\n }\n\n content(c: unknown): this {\n this._content = c;\n return this;\n }\n\n timestamp(ts: number): this {\n this._timestamp = ts;\n return this;\n }\n\n dependsOn(...ids: string[]): this {\n this._dependencies.push(...ids);\n return this;\n }\n\n meta(key: string, value: unknown): this {\n this._meta[key] = value;\n return this;\n }\n\n pinned(p: boolean = true): this {\n this._pinned = p;\n return this;\n }\n\n build(): ContextResource {\n return {\n id: this._id,\n type: this._type,\n role: this._role,\n content: this._content,\n timestamp: this._timestamp,\n dependencies: this._dependencies,\n meta: this._meta,\n pinned: this._pinned,\n };\n }\n}\n\n// ─── 工厂函数 ─────────────────────────────────────────────────────\n\nexport function createMessageResource(\n role: ResourceRole,\n content: unknown,\n options?: Partial<ContextResource>,\n): ContextResource {\n const type: ResourceType =\n role === 'user' ? 'user_message'\n : role === 'assistant' ? 'assistant_message'\n : role === 'system' ? 'system_message'\n : 'custom';\n\n return new ContextResourceBuilder()\n .type(type)\n .role(role)\n .content(content)\n .timestamp(options?.timestamp ?? Date.now())\n .build();\n}\n\nexport function createToolCallResource(\n toolCallId: string,\n toolName: string,\n args: unknown,\n options?: Partial<ContextResource>,\n): ContextResource {\n return new ContextResourceBuilder()\n .id(toolCallId)\n .type('tool_call')\n .role('assistant')\n .content({ toolName, args })\n .meta('toolName', toolName)\n .meta('toolCallId', toolCallId)\n .timestamp(options?.timestamp ?? Date.now())\n .build();\n}\n\nexport function createToolResultResource(\n toolCallId: string,\n toolName: string,\n result: unknown,\n isError: boolean,\n dependsOn: string,\n options?: Partial<ContextResource>,\n): ContextResource {\n return new ContextResourceBuilder()\n .id(`${toolCallId}_result`)\n .type('tool_result')\n .role('toolResult')\n .content(result)\n .dependsOn(dependsOn)\n .meta('toolName', toolName)\n .meta('toolCallId', toolCallId)\n .meta('isError', isError)\n .timestamp(options?.timestamp ?? Date.now())\n .build();\n}\n","/**\n * TaskGraph - 任务依赖图\n *\n * 管理所有 ContextResource 之间的依赖关系,支持拓扑排序与可达性分析。\n * Runtime 在每次编译时会构建 TaskGraph,Transformer 基于图结构操作资源。\n */\n\nimport type { ContextResource, ResourceType } from './context-resource';\n\n// ─── 图节点 ───────────────────────────────────────────────────────\n\nexport interface GraphNode {\n resource: ContextResource;\n dependents: Set<string>; // 依赖此节点的节点\n dependencies: Set<string>; // 此节点依赖的节点\n}\n\n// ─── TaskGraph 接口 ───────────────────────────────────────────────\n\nexport interface TaskGraph {\n /** 添加资源到图中 */\n add(resource: ContextResource): void;\n /** 批量添加资源 */\n addAll(resources: ContextResource[]): void;\n /** 获取指定 ID 的资源 */\n resolve(id: string): ContextResource | undefined;\n /** 获取指定 ID 的节点 */\n getNode(id: string): GraphNode | undefined;\n /** 移除资源(同时清理依赖关系) */\n remove(id: string): boolean;\n /** 获取所有资源 */\n getAll(): ContextResource[];\n /** 按类型过滤资源 */\n getByType(type: ResourceType): ContextResource[];\n /** 拓扑排序 */\n topologicalSort(): ContextResource[];\n /** 检查从 from 到 to 是否可达 */\n isReachable(from: string, to: string): boolean;\n /** 获取所有叶子节点(无依赖的节点) */\n getLeaves(): ContextResource[];\n /** 获取根节点(无被依赖的节点) */\n getRoots(): ContextResource[];\n /** 获取图的大小 */\n readonly size: number;\n /** 清空图 */\n clear(): void;\n}\n\n// ─── TaskGraph 实现 ───────────────────────────────────────────────\n\nexport class TaskGraphImpl implements TaskGraph {\n private nodes = new Map<string, GraphNode>();\n private _size = 0;\n\n get size(): number {\n return this._size;\n }\n\n add(resource: ContextResource): void {\n // 如果已存在,先移除旧节点\n if (this.nodes.has(resource.id)) {\n this.remove(resource.id);\n }\n\n const node: GraphNode = {\n resource,\n dependents: new Set(),\n dependencies: new Set(),\n };\n\n // 建立依赖关系\n for (const depId of resource.dependencies) {\n node.dependencies.add(depId);\n const depNode = this.nodes.get(depId);\n if (depNode) {\n depNode.dependents.add(resource.id);\n }\n }\n\n this.nodes.set(resource.id, node);\n this._size++;\n }\n\n addAll(resources: ContextResource[]): void {\n // 先添加所有节点(不带依赖),再补充依赖关系\n for (const res of resources) {\n if (!this.nodes.has(res.id)) {\n this.nodes.set(res.id, {\n resource: res,\n dependents: new Set(),\n dependencies: new Set(),\n });\n this._size++;\n }\n }\n // 补充依赖关系\n for (const res of resources) {\n const node = this.nodes.get(res.id)!;\n for (const depId of res.dependencies) {\n node.dependencies.add(depId);\n const depNode = this.nodes.get(depId);\n if (depNode) {\n depNode.dependents.add(res.id);\n }\n }\n }\n }\n\n resolve(id: string): ContextResource | undefined {\n return this.nodes.get(id)?.resource;\n }\n\n getNode(id: string): GraphNode | undefined {\n return this.nodes.get(id);\n }\n\n remove(id: string): boolean {\n const node = this.nodes.get(id);\n if (!node) return false;\n\n // 清理依赖关系\n for (const depId of node.dependencies) {\n const depNode = this.nodes.get(depId);\n depNode?.dependents.delete(id);\n }\n for (const dependentId of node.dependents) {\n const dependentNode = this.nodes.get(dependentId);\n dependentNode?.dependencies.delete(id);\n }\n\n this.nodes.delete(id);\n this._size--;\n return true;\n }\n\n getAll(): ContextResource[] {\n return Array.from(this.nodes.values()).map(n => n.resource);\n }\n\n getByType(type: ResourceType): ContextResource[] {\n return this.getAll().filter(r => r.type === type);\n }\n\n topologicalSort(): ContextResource[] {\n const result: ContextResource[] = [];\n const visited = new Set<string>();\n const visiting = new Set<string>();\n\n const visit = (id: string): void => {\n if (visited.has(id)) return;\n if (visiting.has(id)) return; // 环检测:跳过\n\n visiting.add(id);\n const node = this.nodes.get(id);\n if (node) {\n for (const depId of node.dependencies) {\n visit(depId);\n }\n result.push(node.resource);\n }\n visiting.delete(id);\n visited.add(id);\n };\n\n for (const id of this.nodes.keys()) {\n visit(id);\n }\n\n return result;\n }\n\n isReachable(from: string, to: string): boolean {\n if (from === to) return true;\n const visited = new Set<string>();\n const queue = [from];\n\n while (queue.length > 0) {\n const current = queue.shift()!;\n if (visited.has(current)) continue;\n visited.add(current);\n\n const node = this.nodes.get(current);\n if (!node) continue;\n\n for (const depId of node.dependencies) {\n if (depId === to) return true;\n if (!visited.has(depId)) {\n queue.push(depId);\n }\n }\n }\n\n return false;\n }\n\n getLeaves(): ContextResource[] {\n return Array.from(this.nodes.values())\n .filter(n => n.dependencies.size === 0)\n .map(n => n.resource);\n }\n\n getRoots(): ContextResource[] {\n return Array.from(this.nodes.values())\n .filter(n => n.dependents.size === 0)\n .map(n => n.resource);\n }\n\n clear(): void {\n this.nodes.clear();\n this._size = 0;\n }\n}\n\n// ─── 图构建器 ─────────────────────────────────────────────────────\n\nexport class TaskGraphBuilder {\n private resources: ContextResource[] = [];\n\n add(resource: ContextResource): this {\n this.resources.push(resource);\n return this;\n }\n\n addAll(resources: ContextResource[]): this {\n this.resources.push(...resources);\n return this;\n }\n\n build(): TaskGraph {\n const graph = new TaskGraphImpl();\n graph.addAll(this.resources);\n return graph;\n }\n}\n\nexport function createTaskGraph(): TaskGraph {\n return new TaskGraphImpl();\n}\n","/**\n * Extension - 扩展插件系统\n *\n * Extension 通过 Tapable 钩子在 Runtime 生命周期的关键节点注入逻辑,\n * 无需修改 Runtime 核心,实现开闭原则。\n */\n\nimport { AsyncSeriesHook, AsyncSeriesWaterfallHook } from './tapable';\nimport type { Request } from './request';\nimport type { Result } from './result';\nimport type { Context } from './types';\nimport type { ContextResource } from './context-resource';\nimport type { BeforeToolCallDecision, AfterToolCallDecision } from './tool-hooks';\nimport type { Runtime } from './runtime';\n\n// ─── Runtime 钩子集合 ─────────────────────────────────────────────\n\nexport interface RuntimeHooks {\n /** Runtime 初始化前 */\n beforeInitialize: AsyncSeriesHook<[Request]>;\n /** Runtime 初始化后 */\n afterInitialize: AsyncSeriesHook<[Request]>;\n /** 请求处理前(可修改请求) */\n beforeRun: AsyncSeriesWaterfallHook<Request>;\n /** 资源构建后、转换前(可修改资源) */\n beforeTransform: AsyncSeriesWaterfallHook<ContextResource[]>;\n /**\n * 资源转换后、模型调用前(可修改资源)\n */\n afterTransform: AsyncSeriesWaterfallHook<ContextResource[]>;\n /**\n * 模型调用前(waterfall,可修改最终发给模型的 Context:\n * systemPrompt / messages / tools)。\n * 典型用途:插件注入 system prompt 片段或动态附加工具(如 skills 目录注入)。\n * 每次模型调用触发一次;systemPrompt 以 Runtime 持有的基准值为起点,改动不累积。\n */\n beforeModelCall: AsyncSeriesWaterfallHook<Context>;\n /** 模型调用后、结果构建前 */\n beforeEmit: AsyncSeriesHook<[Result]>;\n /** 结果构建后 */\n afterEmit: AsyncSeriesHook<[Result]>;\n /**\n * 运行结束。\n * 第二参数为最终 Request(可选,向后兼容)。\n * 单会话模式下会话标识由 Runtime 持有;多会话场景请创建独立 Runtime 实例。\n */\n done: AsyncSeriesHook<[Result, Request?]>;\n /** 运行失败 */\n failed: AsyncSeriesHook<[Error, Request]>;\n /**\n * 工具执行前(参数校验后)。流转 BeforeToolCallDecision:\n * 任一 tap 设 block 则该工具不执行(生成拒绝结果);\n * 设 terminate 则终止整个 run(本轮工具结束后停止 runLoop);\n * 可改写 args。第二参数为 ToolCallContext。\n */\n beforeToolCall: AsyncSeriesWaterfallHook<BeforeToolCallDecision>;\n /**\n * 工具执行后、最终事件发出前。流转 AfterToolCallDecision:\n * 可改写 result(waterfall),设 terminate 终止整个 run。\n * 第二参数为 ToolCallContext。\n */\n afterToolCall: AsyncSeriesWaterfallHook<AfterToolCallDecision>;\n}\n\n// ─── Extension 接口 ───────────────────────────────────────────────\n\nexport interface Extension {\n /** 扩展名称 */\n readonly name: string;\n /**\n * 应用扩展到 Runtime\n * 通过 hooks.tap 注册回调\n */\n apply(hooks: RuntimeHooks, context: ExtensionContext): void;\n}\n\n// ─── 扩展上下文 ───────────────────────────────────────────────────\n\nexport interface ExtensionContext {\n /** Runtime 配置 */\n readonly config: Record<string, unknown>;\n /** 工作区路径 */\n readonly workspace: string;\n /** 会话标识 */\n readonly sessionKey: string;\n /** 共享状态(Extension 间通信) */\n readonly shared: Map<string, unknown>;\n /**\n * 所属 Runtime 引用(可选)。\n * 供插件在 apply 阶段注册工具等(如 SkillsExtension 注册内置 skill 工具)。\n * 由 AgentRuntime.create 注入;自建 ExtensionContext 时可缺省。\n */\n readonly runtime?: Runtime;\n}\n\n// ─── Extension 管理器 ─────────────────────────────────────────────\n\nexport class ExtensionManager {\n private extensions: Extension[] = [];\n private hooks: RuntimeHooks;\n\n constructor() {\n this.hooks = this.createHooks();\n }\n\n private createHooks(): RuntimeHooks {\n return {\n beforeInitialize: new AsyncSeriesHook('beforeInitialize'),\n afterInitialize: new AsyncSeriesHook('afterInitialize'),\n beforeRun: new AsyncSeriesWaterfallHook('beforeRun'),\n beforeTransform: new AsyncSeriesWaterfallHook('beforeTransform'),\n afterTransform: new AsyncSeriesWaterfallHook('afterTransform'),\n beforeModelCall: new AsyncSeriesWaterfallHook('beforeModelCall'),\n beforeEmit: new AsyncSeriesHook('beforeEmit'),\n afterEmit: new AsyncSeriesHook('afterEmit'),\n done: new AsyncSeriesHook('done'),\n failed: new AsyncSeriesHook('failed'),\n beforeToolCall: new AsyncSeriesWaterfallHook('beforeToolCall'),\n afterToolCall: new AsyncSeriesWaterfallHook('afterToolCall'),\n };\n }\n\n /** 注册扩展 */\n register(extension: Extension): this {\n this.extensions.push(extension);\n return this;\n }\n\n /** 批量注册扩展 */\n registerAll(extensions: Extension[]): this {\n for (const ext of extensions) {\n this.register(ext);\n }\n return this;\n }\n\n /** 应用所有扩展到钩子 */\n applyAll(context: ExtensionContext): void {\n for (const ext of this.extensions) {\n try {\n ext.apply(this.hooks, context);\n } catch (err) {\n // 单个 Extension 失败不影响其他 Extension,但需可观测\n console.warn(`[Extension] \"${ext.name}\" apply 失败:`, (err as Error)?.message ?? err);\n }\n }\n }\n\n /** 获取钩子集合 */\n getHooks(): RuntimeHooks {\n return this.hooks;\n }\n\n /** 移除扩展 */\n unregister(name: string): boolean {\n const idx = this.extensions.findIndex(e => e.name === name);\n if (idx === -1) return false;\n this.extensions.splice(idx, 1);\n return true;\n }\n\n /** 获取所有已注册的扩展 */\n getExtensions(): Extension[] {\n return [...this.extensions];\n }\n\n /** 清空所有扩展 */\n clear(): void {\n this.extensions = [];\n }\n}\n\n// ─── 抽象基类 ─────────────────────────────────────────────────────\n\nexport abstract class BaseExtension implements Extension {\n abstract readonly name: string;\n\n apply(hooks: RuntimeHooks, context: ExtensionContext): void {\n this.setup(hooks, context);\n }\n\n protected abstract setup(hooks: RuntimeHooks, context: ExtensionContext): void;\n}\n","/**\n * Result - 运行结果\n *\n * Result 代表 Agent 一次运行的最终产物,\n * 包含输出内容、使用的工具、元数据、以及资源快照。\n */\n\nimport type { ContextResource } from './context-resource';\n\n// ─── 结果接口 ─────────────────────────────────────────────────────\n\nexport interface Result {\n /** 输出内容(最终回复文本) */\n readonly content: string;\n /** 使用的工具列表 */\n readonly toolsUsed: string[];\n /** Token 用量统计 */\n readonly usage: Record<string, number>;\n /** 停止原因 */\n readonly stopReason: string;\n /** 元数据 */\n readonly metadata: Record<string, unknown>;\n /** 错误信息(运行失败时) */\n readonly error?: string;\n /** 是否成功 */\n readonly success: boolean;\n /** 资源快照(运行结束时的上下文资源) */\n readonly resources?: ContextResource[];\n}\n\n// ─── 结果构建器 ───────────────────────────────────────────────────\n\nexport class ResultBuilder {\n private _content: string = '';\n private _toolsUsed: string[] = [];\n private _usage: Record<string, number> = {};\n private _stopReason: string = 'completed';\n private _metadata: Record<string, unknown> = {};\n private _error?: string;\n private _success: boolean = true;\n private _resources?: ContextResource[];\n\n content(c: string): this {\n this._content = c;\n return this;\n }\n\n toolsUsed(tools: string[]): this {\n this._toolsUsed = tools;\n return this;\n }\n\n addTool(tool: string): this {\n if (!this._toolsUsed.includes(tool)) {\n this._toolsUsed.push(tool);\n }\n return this;\n }\n\n usage(u: Record<string, number>): this {\n this._usage = u;\n return this;\n }\n\n stopReason(r: string): this {\n this._stopReason = r;\n return this;\n }\n\n metadata(key: string, value: unknown): this;\n metadata(map: Record<string, unknown>): this;\n metadata(keyOrMap: string | Record<string, unknown>, value?: unknown): this {\n if (typeof keyOrMap === 'string') {\n this._metadata[keyOrMap] = value;\n } else {\n this._metadata = { ...this._metadata, ...keyOrMap };\n }\n return this;\n }\n\n error(e?: string): this {\n if (e !== undefined) {\n this._error = e;\n this._success = false;\n this._stopReason = 'error';\n }\n return this;\n }\n\n resources(res: ContextResource[]): this {\n this._resources = res;\n return this;\n }\n\n build(): Result {\n return {\n content: this._content,\n toolsUsed: this._toolsUsed,\n usage: this._usage,\n stopReason: this._stopReason,\n metadata: this._metadata,\n error: this._error,\n success: this._success,\n resources: this._resources,\n };\n }\n}\n\n// ─── 流式事件接口 ─────────────────────────────────────────────────\n\nexport interface ResultChunk {\n /** 块类型 */\n type: 'text' | 'tool_start' | 'tool_end' | 'thinking' | 'error' | 'done';\n /** 内容 */\n content?: string;\n /** 工具名称(tool 类型) */\n toolName?: string;\n /** 工具调用 ID */\n toolCallId?: string;\n /** 是否错误 */\n isError?: boolean;\n /** done 类型:最终 Result 摘要(usage / stopReason / toolsUsed 等,供调用方统计展示) */\n result?: Result;\n}\n\n// ─── 工厂函数 ─────────────────────────────────────────────────────\n\nexport function createResult(content: string, options?: Partial<Result>): Result {\n return {\n content,\n toolsUsed: options?.toolsUsed ?? [],\n usage: options?.usage ?? {},\n stopReason: options?.stopReason ?? 'completed',\n metadata: options?.metadata ?? {},\n error: options?.error,\n success: options?.success ?? !options?.error,\n resources: options?.resources,\n };\n}\n\nexport function createErrorResult(error: string): Result {\n return new ResultBuilder()\n .error(error)\n .build();\n}\n","/**\n * packages/core/session.ts - 会话持久化契约层\n *\n * 定义会话存储的数据格式与适配器接口。\n * 实现(memory/file)位于 packages/session/,遵循单向依赖:session → core。\n *\n * 设计要点:\n * - 线性结构:messages 平铺 + 元数据(模型、用量),不做树形分支(YAGNI)\n * - version 字段预留兼容,未来结构升级可平滑迁移\n * - 存储接口仿 src/storage 的 adapter 模式,但不依赖 src/\n */\n\nimport type { Message, Usage } from './types';\n\n/** 当前会话数据格式版本 */\nexport const SESSION_VERSION = 1;\n\n/** 会话模型信息(最后使用的模型) */\nexport interface SessionModel {\n provider: string;\n modelId: string;\n}\n\n/** 持久化会话数据(线性结构) */\nexport interface StoredSession {\n key: string;\n version: number;\n messages: Message[];\n model: SessionModel | null;\n usage: Usage;\n createdAt: string;\n updatedAt: string;\n}\n\n/** 跨进程锁句柄:调用方需在 finally 中 release() */\nexport interface StorageLock {\n release(): Promise<void>;\n}\n\n/** 会话存储适配器接口 */\nexport interface SessionStorage {\n load(key: string): Promise<StoredSession | null>;\n save(key: string, session: StoredSession): Promise<void>;\n delete(key: string): Promise<boolean>;\n list(): Promise<string[]>;\n /**\n * 跨进程互斥锁(可选):fn 执行期间独占该 key 的\"读-改-写\",\n * 防止多进程并发写同一会话导致 last-write-wins 丢消息。\n * 单进程存储(如内存实现)可省略;Runtime 在非 ephemeral 请求下自动调用。\n */\n withLock?<T>(key: string, fn: () => Promise<T>): Promise<T>;\n /** 手动锁(可选,供流式等无法用回调包住的场景):finally 中 release() */\n acquireLock?(key: string): Promise<StorageLock>;\n}\n\n/** 文件存储选项 */\nexport interface FileSessionStorageOptions {\n /** 存储根目录,默认 <pwd>/.aipack/sessions */\n baseDir?: string;\n /** 过期时间(毫秒),超过 updatedAt 的会话在加载/列举时清理 */\n maxAge?: number;\n /** 持久化消息条数上限(保留最新 N 条,0 表示不限,默认 0) */\n maxStoredMessages?: number;\n /** 获取跨进程锁的最大等待时间(毫秒,默认 30000)。超时抛错 */\n lockWaitMs?: number;\n /** 锁文件视为\"陈旧\"的阈值(毫秒,默认 300000)。\n * 持有锁的进程崩溃后留下的锁文件在超过该时长后会被接管 */\n lockStaleMs?: number;\n /** 锁获取重试的基础间隔(毫秒,默认 25,指数退避至 500) */\n lockRetryMs?: number;\n}\n\n/** 内存存储选项 */\nexport interface MemorySessionStorageOptions {\n /** 过期时间(毫秒),超过 updatedAt 的会话在加载时清理 */\n maxAge?: number;\n}\n","/**\n * packages/request - 请求入口\n *\n * 独立实现,不依赖 src/。\n * 负责请求的解析、验证与标准化。\n */\n\nimport { RequestBuilder, createRequest } from '../core';\nimport type { Request, RequestType } from '../core';\n\n// ─── 请求验证 ─────────────────────────────────────────────────────\n\nexport interface ValidationResult {\n valid: boolean;\n errors: string[];\n}\n\nexport function validateRequest(request: Request): ValidationResult {\n const errors: string[] = [];\n\n if (!request.message || request.message.trim().length === 0) {\n errors.push('message 不能为空');\n }\n\n if (request.message.length > 100000) {\n errors.push('message 长度超过限制(100000 字符)');\n }\n\n return { valid: errors.length === 0, errors };\n}\n\n// ─── 请求标准化 ───────────────────────────────────────────────────\n\nexport function normalizeRequest(request: Request): Request {\n return createRequest(request.message, {\n type: request.type,\n channel: request.channel || 'cli',\n chatId: request.chatId || 'direct',\n senderId: request.senderId || 'user',\n sessionKey: request.sessionKey,\n media: request.media?.filter(Boolean) || [],\n ephemeral: request.ephemeral ?? false,\n model: request.model || undefined,\n modelPreset: request.modelPreset || undefined,\n metadata: request.metadata || {},\n });\n}\n\n// ─── 请求工厂 ─────────────────────────────────────────────────────\n\n// 渠道相关工厂(CLI / Webhook / 飞书 / SDK)不属于框架:\n// 各渠道由使用方基于 createRequest 自行拼装,例如:\n// createRequest(msg, { sessionKey: `webhook:${chatId}`, channel: 'webhook', chatId, senderId })\n\nexport { RequestBuilder, createRequest } from '../core';\nexport type { Request, RequestType } from '../core';\n","/**\n * packages/context-resource - 上下文资源适配层\n *\n * 将 core 的 Message 体系转换为 ContextResource。\n */\n\nimport type {\n Message,\n UserMessage,\n AssistantMessage,\n ToolResultMessage,\n SystemMessage,\n ContentBlock,\n Usage,\n} from '../core';\nimport {\n ContextResourceBuilder,\n createToolResultResource,\n} from '../core';\nimport type { ContextResource, ResourceType, ResourceRole } from '../core';\nimport { extractToolCalls, extractText } from '../core';\n\n// ─── Message -> ContextResource ───────────────────────────────────\n\nexport function messageToResource(msg: Message, index: number): ContextResource {\n const id = `msg_${index}`;\n const timestamp = msg.timestamp ?? Date.now();\n\n switch (msg.role) {\n case 'user': {\n return new ContextResourceBuilder()\n .id(id)\n .type('user_message')\n .role('user')\n .content(msg.content)\n .timestamp(timestamp)\n .build();\n }\n\n case 'assistant': {\n const assistant = msg as AssistantMessage;\n const builder = new ContextResourceBuilder()\n .id(id)\n .type('assistant_message')\n .role('assistant')\n .content(assistant.content)\n .timestamp(timestamp)\n .meta('model', assistant.model)\n .meta('provider', assistant.provider)\n .meta('stopReason', assistant.stopReason);\n\n if (assistant.usage) {\n builder.meta('usage', assistant.usage);\n }\n\n const toolCalls = extractToolCalls(assistant.content);\n for (const tc of toolCalls) {\n builder.dependsOn(tc.id);\n }\n\n return builder.build();\n }\n\n case 'toolResult': {\n const toolMsg = msg as ToolResultMessage;\n return createToolResultResource(\n toolMsg.toolCallId,\n toolMsg.toolName,\n toolMsg.content,\n toolMsg.isError,\n toolMsg.toolCallId,\n { timestamp },\n );\n }\n\n case 'system': {\n return new ContextResourceBuilder()\n .id(id)\n .type('system_message')\n .role('system')\n .content(msg.content)\n .timestamp(timestamp)\n .pinned()\n .build();\n }\n\n default: {\n const customMsg = msg as Message & { role: string };\n const roleStr: string = customMsg.role;\n const customType: ResourceType =\n roleStr === 'compactionSummary' ? 'compaction_summary'\n : roleStr === 'stateSnapshot' ? 'state_snapshot'\n : 'custom';\n\n const builder = new ContextResourceBuilder()\n .id(id)\n .type(customType)\n .role(roleStr as ResourceRole)\n .content(customMsg)\n .timestamp(timestamp);\n // 摘要与状态快照为关键资源:截断类转换器不可移除(pinned)\n if (customType === 'compaction_summary' || customType === 'state_snapshot') {\n builder.pinned();\n }\n return builder.build();\n }\n }\n}\n\nexport function messagesToResources(messages: Message[]): ContextResource[] {\n return messages.map((msg, index) => messageToResource(msg, index));\n}\n\n// ─── ContextResource -> Message ───────────────────────────────────\n\nexport function resourceToMessage(resource: ContextResource): Message {\n switch (resource.type) {\n case 'user_message':\n return {\n role: 'user',\n content: resource.content as string | ContentBlock[],\n timestamp: resource.timestamp,\n } as UserMessage;\n\n case 'assistant_message': {\n const meta = resource.meta;\n const content = resource.content;\n // 标准转换:resource.content 存的是 ContentBlock[],需重建完整 AssistantMessage\n if (Array.isArray(content)) {\n return {\n role: 'assistant',\n content: content as ContentBlock[],\n stopReason: meta.stopReason as string | undefined,\n usage: meta.usage as Usage | undefined,\n model: meta.model as string | undefined,\n provider: meta.provider as string | undefined,\n timestamp: resource.timestamp,\n } as AssistantMessage;\n }\n // 兼容:content 本身就是完整消息(自定义转换器可能直接存消息)\n return content as AssistantMessage;\n }\n\n case 'tool_result': {\n const meta = resource.meta;\n return {\n role: 'toolResult',\n toolCallId: meta.toolCallId as string,\n toolName: meta.toolName as string,\n content: resource.content as ContentBlock[],\n isError: meta.isError as boolean,\n timestamp: resource.timestamp,\n } as ToolResultMessage;\n }\n\n case 'system_message':\n return {\n role: 'system',\n content: resource.content as string,\n timestamp: resource.timestamp,\n } as SystemMessage;\n\n default:\n return resource.content as Message;\n }\n}\n\nexport function resourcesToMessages(resources: ContextResource[]): Message[] {\n return resources.map(resourceToMessage);\n}\n\n// ─── 工具函数 ─────────────────────────────────────────────────────\n\nexport function extractToolCallsFromResource(resource: ContextResource): string[] {\n if (resource.type !== 'assistant_message') return [];\n const content = resource.content as ContentBlock[];\n if (!Array.isArray(content)) return [];\n return extractToolCalls(content).map(tc => tc.id);\n}\n\nexport function extractTextFromResource(resource: ContextResource): string {\n const content = resource.content;\n if (typeof content === 'string') return content;\n if (Array.isArray(content)) return extractText(content);\n return '';\n}\n","// ─── 重新导出 TypeBox ───────────────────────────────────────────\nexport { Type, type Static, type TSchema } from '@sinclair/typebox';\n\n// ─── 类型 ────────────────────────────────────────────────────────\nexport type {\n Api,\n ContentBlock,\n TextContent,\n ImageContent,\n ToolCallContent,\n ThinkingContent,\n Usage,\n Model,\n UserMessage,\n AssistantMessage,\n ToolResultMessage,\n Message,\n Tool,\n Context,\n StreamEvent,\n StreamStartEvent,\n TextStartEvent,\n TextDeltaEvent,\n TextEndEvent,\n ThinkingStartEvent,\n ThinkingDeltaEvent,\n ThinkingEndEvent,\n ToolCallStartEvent,\n ToolCallDeltaEvent,\n ToolCallEndEvent,\n DoneEvent,\n ErrorEvent,\n StreamResult,\n SimpleStreamOptions,\n StreamOptions,\n ReasoningLevel,\n Provider,\n ResolvedAuth,\n ModelsOptions,\n CredentialStore,\n ImagesModel,\n ImagesProvider,\n ImageInputBlock,\n ImageOutputBlock,\n AssistantImages,\n ImagesGenerateOptions,\n} from './types';\n\n// ─── 函数 ───────────────────────────────────────────────────\nexport { hasApi, createEmptyUsage, createEmptyAssistantMessage } from './types';\n\n// ─── Models 类 ──────────────────────────────────────────────────────\nexport { Models, createModels } from './models';\n\n// ─── 图片生成 ────────────────────────────────────────────\nexport { ImagesModels, createImagesModels } from './images';\n\n// ─── 内置提供者 ──────────────────────────────────────────\nexport {\n builtinModels,\n builtinProviders,\n builtinImagesModels,\n getBuiltinModel,\n getBuiltinModels,\n getBuiltinProviders,\n} from './providers-all';\n\n// ─── 目录 ─────────────────────────────────────────────────────\nexport { BUILTIN_MODELS, BUILTIN_IMAGES_MODELS, BUILTIN_PROVIDERS, getEnvApiKey, hasProviderConfigured } from './catalog';\n\n// ─── 流式实现(供适配器直接复用) ──────────────────────────────\nexport { streamOpenAI } from './stream-openai';\nexport { streamAnthropic } from './stream-anthropic';\n\n// ─── 统一凭证解析 ─────────────────────────────────────────────\nexport {\n envKeyName,\n resolveApiKey,\n resolveApiKeyFromEnv,\n EnvCredentialStore,\n createEnvCredentialStore,\n} from './credentials';\n\n// ─── 上下文溢出检测 ────────────────────────────────────────────\nexport { isContextOverflow } from './overflow';\n\n// ─── 统一错误分类 ──────────────────────────────────────────────\nexport {\n AgentError,\n AgentErrorCategory,\n isAgentError,\n isRetryableCategory,\n classifyHttpStatus,\n classifyErrorMessage,\n classifyError,\n isContextOverflowError,\n categoryLabel,\n formatCategoryError,\n formatHttpError,\n} from './errors';\nexport type { AgentErrorOptions } from './errors';\n","/**\n * AgentError - 统一错误分类体系\n *\n * AI 调用链(stream 层 / retry 层 / 上层消费者)共享同一套错误分类:\n * - retryable 网络抖动 / 5xx 瞬时错误(可重试)\n * - rate-limit 429 限流(可重试,配合退避)\n * - timeout 超时(半开连接 / idle 断流)\n * - auth 认证失败(401/403 / 缺少 API key / key 无效)\n * - context-overflow 上下文超限(413 / context length 错误)\n * - invalid-request 请求非法(其余 4xx)\n * - unknown 未分类\n *\n * 用途:\n * 1. retry 决策(isRetryableError 优先读取 category,替代消息模式匹配)\n * 2. 上层差异化处理(如 auth 错误提示用户换 key、context-overflow 触发压缩)\n * 3. errorMessage 带 [category] 前缀,人可直接阅读\n */\n\n// ─── 分类常量 ──────────────────────────────────────────────────────\n\nexport const AgentErrorCategory = {\n RETRYABLE: 'retryable',\n TIMEOUT: 'timeout',\n AUTH: 'auth',\n CONTEXT_OVERFLOW: 'context-overflow',\n RATE_LIMIT: 'rate-limit',\n INVALID_REQUEST: 'invalid-request',\n UNKNOWN: 'unknown',\n} as const;\n\nexport type AgentErrorCategory =\n (typeof AgentErrorCategory)[keyof typeof AgentErrorCategory];\n\n// ─── AgentError 类 ─────────────────────────────────────────────────\n\nexport interface AgentErrorOptions {\n /** 错误分类(缺省 unknown) */\n category?: AgentErrorCategory;\n /** HTTP 状态码(如有) */\n status?: number;\n /** 是否可重试(缺省按分类推导:retryable / rate-limit 可重试) */\n retryable?: boolean;\n /** 原始错误(如 fetch Response / 底层 Error) */\n cause?: unknown;\n}\n\nconst RETRYABLE_CATEGORIES: ReadonlySet<AgentErrorCategory> = new Set([\n AgentErrorCategory.RETRYABLE,\n AgentErrorCategory.RATE_LIMIT,\n]);\n\n/** 该分类默认是否可重试 */\nexport function isRetryableCategory(category: AgentErrorCategory): boolean {\n return RETRYABLE_CATEGORIES.has(category);\n}\n\nexport class AgentError extends Error {\n readonly category: AgentErrorCategory;\n readonly status?: number;\n readonly retryable: boolean;\n /** 原始错误(ES2022 cause,Node 18 起 Error 构造支持 options.cause) */\n override readonly cause?: unknown;\n\n constructor(message: string, options: AgentErrorOptions = {}) {\n super(message);\n this.name = 'AgentError';\n this.category = options.category ?? AgentErrorCategory.UNKNOWN;\n this.status = options.status;\n this.retryable = options.retryable ?? isRetryableCategory(this.category);\n // 不依赖 ES2022 Error 构造 options.cause(低 target 转译可能丢失),显式赋值\n this.cause = options.cause;\n }\n}\n\n/** 类型守卫:兼容跨包/跨 realm 复制的 AgentError 对象 */\nexport function isAgentError(error: unknown): error is AgentError {\n if (error instanceof AgentError) return true;\n return (\n !!error &&\n typeof error === 'object' &&\n (error as { name?: unknown }).name === 'AgentError' &&\n typeof (error as { category?: unknown }).category === 'string'\n );\n}\n\n// ─── HTTP 状态码分类 ───────────────────────────────────────────────\n\nexport function classifyHttpStatus(status: number): AgentErrorCategory {\n if (status === 401 || status === 403) return AgentErrorCategory.AUTH;\n if (status === 429) return AgentErrorCategory.RATE_LIMIT;\n if (status === 413) return AgentErrorCategory.CONTEXT_OVERFLOW;\n if (status >= 500 && status < 600) return AgentErrorCategory.RETRYABLE;\n if (status >= 400 && status < 500) return AgentErrorCategory.INVALID_REQUEST;\n return AgentErrorCategory.UNKNOWN;\n}\n\n// ─── 错误消息分类(覆盖无 HTTP 状态码的场景)────────────────────────\n\nconst CONTEXT_OVERFLOW_PATTERNS = [\n 'context length',\n 'context window',\n 'context overflow',\n 'context too long',\n 'maximum context',\n 'too many tokens',\n 'token limit',\n 'prompt is too long',\n 'input is too long',\n 'exceeds the model',\n];\n\nconst RATE_LIMIT_PATTERNS = [\n 'rate limit',\n 'too many requests',\n 'ratelimit',\n];\n\nconst AUTH_PATTERNS = [\n 'unauthorized',\n 'authentication',\n 'invalid api key',\n 'incorrect api key',\n 'api key invalid',\n 'permission denied',\n 'forbidden',\n '401',\n '403',\n];\n\nconst TIMEOUT_PATTERNS = [\n 'timeout',\n 'timed out',\n 'etimedout',\n];\n\nexport function classifyErrorMessage(message: string): AgentErrorCategory {\n const lower = message.toLowerCase();\n if (CONTEXT_OVERFLOW_PATTERNS.some((p) => lower.includes(p))) {\n return AgentErrorCategory.CONTEXT_OVERFLOW;\n }\n if (RATE_LIMIT_PATTERNS.some((p) => lower.includes(p))) {\n return AgentErrorCategory.RATE_LIMIT;\n }\n if (AUTH_PATTERNS.some((p) => lower.includes(p))) {\n return AgentErrorCategory.AUTH;\n }\n if (TIMEOUT_PATTERNS.some((p) => lower.includes(p))) {\n return AgentErrorCategory.TIMEOUT;\n }\n return AgentErrorCategory.UNKNOWN;\n}\n\n// ─── 分类组合 ──────────────────────────────────────────────────────\n\n/**\n * 从任意错误对象推导分类:\n * AgentError 优先;有 status 按状态码;否则按消息模式。\n */\nexport function classifyError(error: unknown): AgentErrorCategory {\n if (isAgentError(error)) return error.category;\n const status = (error as { status?: unknown } | null)?.status;\n if (typeof status === 'number') return classifyHttpStatus(status);\n const msg = (error as Error | null)?.message ?? String(error ?? '');\n return classifyErrorMessage(msg);\n}\n\n/** 是否属于\"上下文超限\"(供压缩/截断策略复用) */\nexport function isContextOverflowError(error: unknown): boolean {\n return classifyError(error) === AgentErrorCategory.CONTEXT_OVERFLOW;\n}\n\n// ─── 格式化 ────────────────────────────────────────────────────────\n\n/** 分类标签(如 [auth]),unknown 分类返回空串 */\nexport function categoryLabel(category: AgentErrorCategory): string {\n return category === AgentErrorCategory.UNKNOWN ? '' : `[${category}] `;\n}\n\n/**\n * 构造带分类前缀的 errorMessage:\n * [auth] API error 401: Invalid API key\n * [rate-limit] API error 429: Too many requests\n * [timeout] Stream idle timeout after 60000ms\n */\nexport function formatCategoryError(\n category: AgentErrorCategory,\n message: string,\n): string {\n return `${categoryLabel(category)}${message}`;\n}\n\n/**\n * 基于 HTTP 状态码构造分类错误消息:\n * apiErrorLabel 形如 \"API error\" / \"Anthropic API error\"\n */\nexport function formatHttpError(\n status: number,\n message: string,\n apiErrorLabel = 'API error',\n): string {\n const category = classifyHttpStatus(status);\n return formatCategoryError(category, `${apiErrorLabel} ${status}: ${message}`);\n}\n","/**\n * 上下文溢出检测\n *\n * 通过匹配各提供商的错误消息模式,检测 API 返回是否因输入超出上下文窗口导致。\n * 支持五种溢出/可恢复截断模式:\n * 1. 显式溢出:provider 返回错误消息\n * 2. 静默溢出:provider 接受请求但 usage.input > contextWindow\n * 3. 截断溢出(输入侧):provider 截断输入后无输出空间(output=0)\n * 4. 截断溢出(输出侧,thinking 耗尽):stopReason=\"length\" 且模型只有 thinking\n * 块、没有实际 text/tool_call 产出(reasoning 模型常见,maxTokens 预算被 thinking\n * 吃光导致用户侧零产出,必须恢复,否则只能手动点「继续」)\n * 5. 截断溢出(输出侧,output 接近上限):stopReason=\"length\" 且 usage.output 占\n * 满 maxTokens(传入),视为本回合预算耗尽,需要外部继续\n */\n\n// ─── 溢出模式 ──────────────────────────────────────────────────────\n\nconst OVERFLOW_PATTERNS: RegExp[] = [\n // 本框架 formatCategoryError 产出的分类前缀(errors.ts),\n // 覆盖消息体不含已知关键词但已带分类前缀的场景\n /^\\[context-overflow\\]/i,\n // Anthropic\n /prompt is too long/i,\n /request_too_large/i,\n // Amazon Bedrock\n /input is too long for requested model/i,\n // OpenAI & 兼容\n /exceeds the context window/i,\n /exceeds (?:the )?(?:model'?s )?maximum context length(?: of [\\d,]+ tokens?|\\s*\\([\\d,]+\\))/i,\n /input token count.*exceeds the maximum/i,\n // xAI Grok\n /maximum prompt length is \\d+/i,\n // Groq\n /reduce the length of the messages/i,\n // OpenRouter\n /maximum context length is \\d+ tokens/i,\n /exceeds (?:the )?maximum allowed input length of [\\d,]+ tokens?/i,\n // Together AI\n /input \\(\\d+ tokens\\) is longer than the model'?s context length \\(\\d+ tokens\\)/i,\n // GitHub Copilot\n /exceeds the limit of \\d+/i,\n // llama.cpp\n /exceeds the available context size/i,\n // LM Studio\n /greater than the context length/i,\n // MiniMax\n /context window exceeds limit/i,\n // Kimi\n /exceeded model token limit/i,\n // Mistral\n /too large for model with \\d+ maximum context length/i,\n // DS4\n /prompt has [\\d,]+ tokens?, but the configured context size is [\\d,]+ tokens?/i,\n // z.ai\n /model_context_window_exceeded/i,\n // Ollama\n /prompt too long; exceeded (?:max )?context length/i,\n // DashScope / Qwen\n /range of input length should be/i,\n // 通用回退\n /context[_ ]length[_ ]exceeded/i,\n /too many tokens/i,\n /token limit exceeded/i,\n // Cerebras: 400/413 无 body\n /^4(?:00|13)\\s*(?:status code)?\\s*\\(no body\\)/i,\n];\n\n// ─── 非溢出的排除模式 ─────────────────────────────────────────────\n\nconst NON_OVERFLOW_PATTERNS: RegExp[] = [\n /^(Throttling error|Service unavailable):/i,\n /rate limit/i,\n /too many requests/i,\n];\n\n// ─── 导出函数 ──────────────────────────────────────────────────────\n\ntype MinimalBlock =\n | { type: 'text'; text?: string }\n | { type: 'toolCall'; id?: string }\n | { type: 'thinking'; thinking?: string; text?: string }\n | { type: string };\n\n/**\n * 溢出检测所需的消息最小形状。\n * 兼容 core(stopReason/usage 可缺省)与 ai(必填)两套 AssistantMessage 定义。\n */\nexport interface OverflowProbeMessage {\n stopReason?: string;\n errorMessage?: string;\n usage?: {\n input: number;\n output: number;\n cacheRead?: number;\n reasoning?: number;\n };\n /** assistant message 的 content block(可缺省);用于检测「只有 thinking 没有有效产出」 */\n content?: string | MinimalBlock[];\n /** 传给 overflow 检测的上限:模型本轮的 max_output_tokens;用于识别 output 被打满的 length 截断 */\n maxTokens?: number;\n}\n\n/**\n * 判断一条 assistant message 是否为上下文溢出错误。\n *\n * @param message - 要检查的 assistant message\n * @param contextWindow - 可选的上下文窗口大小,用于检测静默溢出(如 z.ai)\n */\nexport function isContextOverflow(\n message: OverflowProbeMessage,\n contextWindow?: number,\n): boolean {\n // 情况 1:检查错误消息模式(显式溢出)\n if (message.stopReason === 'error' && message.errorMessage) {\n const errMsg: string = message.errorMessage;\n const isNonOverflow = NON_OVERFLOW_PATTERNS.some((p) => p.test(errMsg));\n if (!isNonOverflow && OVERFLOW_PATTERNS.some((p) => p.test(errMsg))) {\n return true;\n }\n }\n\n // 情况 2:静默溢出(z.ai 风格)— 成功但 usage 超出上下文\n if (contextWindow && message.stopReason === 'stop' && message.usage) {\n const inputTokens = message.usage.input + (message.usage.cacheRead ?? 0);\n if (inputTokens > contextWindow) {\n return true;\n }\n }\n\n // 情况 3:截断溢出(输入侧)— 截断输入后无输出空间\n if (\n contextWindow &&\n message.stopReason === 'length' &&\n message.usage &&\n message.usage.output === 0\n ) {\n const inputTokens = message.usage.input + (message.usage.cacheRead ?? 0);\n if (inputTokens >= contextWindow * 0.99) {\n return true;\n }\n }\n\n // 情况 4:截断溢出(输出侧 thinking 耗尽)\n // reasoning 模型 maxTokens 预算被 thinking 吃光:stopReason=\"length\" 且 content\n // 里没有任何非空 text、也没有 tool_call(可能只有 thinking 块)。\n // 典型场景:deepseek-v4-flash maxTokens=8192,output=8192 全是 reasoning,\n // 用户视角「模型什么都没回复就停了」,必须视为可恢复溢出。\n if (message.stopReason === 'length' && message.content) {\n const blocks = Array.isArray(message.content) ? message.content : null;\n if (blocks) {\n const hasMeaningfulText = blocks.some(\n (b) =>\n b.type === 'text' &&\n typeof (b as any).text === 'string' &&\n (b as any).text.trim().length > 0,\n );\n const hasToolCall = blocks.some((b) => b.type === 'toolCall');\n const hasThinking = blocks.some((b) => b.type === 'thinking');\n // 没有有效文本、没有工具调用、但至少有 thinking → 典型 reasoning 耗尽\n if (!hasMeaningfulText && !hasToolCall && hasThinking) {\n return true;\n }\n }\n }\n\n // 情况 5:截断溢出(输出侧打满)\n // stopReason=\"length\" 且 usage.output ≥ 0.95 × maxTokens → 本轮 output token\n // 预算被打满,后续内容会被截断,需要恢复流程(压缩 / 继续)。\n if (\n message.maxTokens &&\n message.maxTokens > 0 &&\n message.stopReason === 'length' &&\n message.usage\n ) {\n if (message.usage.output >= Math.floor(message.maxTokens * 0.95)) {\n return true;\n }\n }\n\n return false;\n}\n\n/**\n * 获取溢出模式列表(用于测试)\n */\nexport function getOverflowPatterns(): RegExp[] {\n return [...OVERFLOW_PATTERNS];\n}\n","/**\n * packages/transformer - 上下文转换器\n *\n * 独立实现的 ContextTransformer,不依赖 src/。\n * 提供工具配对修复、状态快照注入、消息截断等内置转换器。\n * 用户可通过 BaseTransformer 实现自定义转换器(如上下文压缩)。\n */\n\nimport { BaseTransformer } from '../core';\nimport type { ContextResource, TransformContext } from '../core';\nimport type { Message, ToolCallContent, ContentBlock } from '../core';\nimport { extractToolCalls } from '../core';\nimport { messagesToResources, resourcesToMessages } from '../context-resource';\n\n// ─── token 估算 ───────────────────────────────────────────────────\n\n/**\n * 粗略 token 估算:约 4 字符/token(对中英文混合近似可用)。\n * 不引入 tokenizer 依赖;若需要精确计数,使用方可注入自定义转换器替换。\n */\nfunction estimateTokens(text: string): number {\n if (!text) return 0;\n return Math.ceil(text.length / 4);\n}\n\n/** 估算单个资源的 token 数(序列化内容后计数) */\nfunction estimateResourceTokens(resource: ContextResource): number {\n const content = resource.content;\n if (typeof content === 'string') return estimateTokens(content);\n try {\n return estimateTokens(JSON.stringify(content ?? ''));\n } catch {\n return 0;\n }\n}\n\n/** 序列化资源内容为可读文本,用于 token 估算 */\nfunction resourceText(resource: ContextResource): string {\n const content = resource.content;\n if (typeof content === 'string') return content;\n try {\n return JSON.stringify(content ?? '');\n } catch {\n return '';\n }\n}\n\n// ─── 工具配对转换器 ───────────────────────────────────────────────\n\n/**\n * 确保上下文中 tool_call 与 tool_result 的配对完整性。\n * 移除孤立的工具调用或工具结果消息。\n *\n * 建议放在 transformers 数组最后(兜底修复)。\n * 必须晚于 TruncationTransformer:截断会丢弃旧资源,可能打破配对\n * (例如丢掉 toolCall 但保留 toolResult,或反之),需要本转换器作为\n * 最终兜底重新修复,否则破坏后的消息序列会导致下一次模型调用 400。\n */\nexport class ToolPairingTransformer extends BaseTransformer {\n readonly name = 'tool-pairing';\n\n protected async run(\n resources: ContextResource[],\n _context: TransformContext,\n ): Promise<ContextResource[]> {\n const messages = resourcesToMessages(resources);\n const paired = ensureToolPairing(messages);\n return messagesToResources(paired);\n }\n}\n\n/**\n * 确保 tool_call 与 tool_result 配对完整\n */\nexport function ensureToolPairing(messages: Message[]): Message[] {\n const toolCallIds = new Set<string>();\n const toolResultIds = new Set<string>();\n\n // 收集所有 tool_call ID\n for (const msg of messages) {\n if (msg.role === 'assistant') {\n const content = msg.content;\n if (Array.isArray(content)) {\n for (const tc of extractToolCalls(content)) {\n toolCallIds.add(tc.id);\n }\n }\n }\n if (msg.role === 'toolResult') {\n toolResultIds.add((msg as any).toolCallId);\n }\n }\n\n // 找出孤立的 tool_call(无对应 result)和孤立的 tool_result(无对应 call)\n const orphanedCalls = new Set<string>();\n const orphanedResults = new Set<string>();\n\n for (const id of toolCallIds) {\n if (!toolResultIds.has(id)) orphanedCalls.add(id);\n }\n for (const id of toolResultIds) {\n if (!toolCallIds.has(id)) orphanedResults.add(id);\n }\n\n if (orphanedCalls.size === 0 && orphanedResults.size === 0) {\n return messages;\n }\n\n // 过滤消息\n const result: Message[] = [];\n for (const msg of messages) {\n if (msg.role === 'assistant') {\n const content = msg.content;\n if (Array.isArray(content)) {\n // 移除孤立的 tool_call\n const filteredContent = content.filter(block => {\n if (block.type === 'toolCall') {\n return !orphanedCalls.has((block as ToolCallContent).id);\n }\n return true;\n });\n // 如果所有内容都被移除,跳过这条消息\n if (filteredContent.length === 0 && content.length > 0) continue;\n result.push({ ...msg, content: filteredContent });\n } else {\n result.push(msg);\n }\n } else if (msg.role === 'toolResult') {\n // 移除孤立的 tool_result\n if (!orphanedResults.has((msg as any).toolCallId)) {\n result.push(msg);\n }\n } else {\n result.push(msg);\n }\n }\n\n return result;\n}\n\n// ─── 状态快照注入转换器 ───────────────────────────────────────────\n\n/**\n * 在上下文开头注入状态快照。\n */\nexport class StateSnapshotTransformer extends BaseTransformer {\n readonly name = 'state-snapshot';\n\n constructor(private getStateSnapshot: () => string | null) {\n super();\n }\n\n protected async run(\n resources: ContextResource[],\n _context: TransformContext,\n ): Promise<ContextResource[]> {\n const snapshot = this.getStateSnapshot();\n if (!snapshot) return resources;\n\n const snapshotResource: ContextResource = {\n id: `snapshot_${Date.now()}`,\n type: 'state_snapshot',\n role: 'system',\n content: snapshot,\n timestamp: Date.now(),\n dependencies: [],\n meta: { injected: true },\n pinned: true,\n };\n\n return [snapshotResource, ...resources];\n }\n}\n\n// ─── 消息截断转换器 ───────────────────────────────────────────────\n\n/**\n * 当资源总数超过限制时,移除最旧的非关键资源。\n *\n * 截断按\"配对组\"丢弃:丢弃一个带 toolCall 的 assistant 资源时,会一并丢弃\n * 对应的 toolResult 资源,避免留下孤立结果(孤立结果虽会被 ToolPairingTransformer\n * 兜底清理,但会浪费保留预算)。\n */\nexport class TruncationTransformer extends BaseTransformer {\n readonly name = 'truncation';\n\n constructor(private maxResources: number = 200) {\n super();\n }\n\n protected async run(\n resources: ContextResource[],\n _context: TransformContext,\n ): Promise<ContextResource[]> {\n if (resources.length <= this.maxResources) return resources;\n\n const pinned = resources.filter(r => r.pinned);\n const unpinned = resources.filter(r => !r.pinned);\n const keepCount = this.maxResources - pinned.length;\n\n if (keepCount <= 0) return pinned;\n\n // 保留最新的 keepCount 个,但需按\"配对组\"整体丢弃头部。\n // 从尾部回溯收集要保留的资源,遇到 assistant(toolCall) 时把对应的\n // toolResult 也纳入保留集合(即便它位于 keepCount 边界之外)。\n const keep = new Set<number>();\n const toolCallIdsInRange = new Set<string>();\n\n for (let i = unpinned.length - 1; i >= 0 && keep.size < keepCount; i--) {\n const res = unpinned[i];\n keep.add(i);\n if (res.type === 'assistant_message') {\n for (const dep of res.dependencies) toolCallIdsInRange.add(dep);\n }\n if (res.type === 'tool_result') {\n const tcId = (res.meta as { toolCallId?: string } | undefined)?.toolCallId;\n if (tcId) toolCallIdsInRange.add(tcId);\n }\n }\n\n // 二次扫描:把与已保留 toolCall 配对的 toolResult(或反之)一并保留,\n // 防止截断打破配对。\n for (let i = 0; i < unpinned.length; i++) {\n if (keep.has(i)) continue;\n const res = unpinned[i];\n if (res.type === 'tool_result') {\n const tcId = (res.meta as { toolCallId?: string } | undefined)?.toolCallId;\n if (tcId && toolCallIdsInRange.has(tcId)) keep.add(i);\n }\n }\n\n const kept = unpinned.filter((_, i) => keep.has(i));\n return [...pinned, ...kept].sort((a, b) => a.timestamp - b.timestamp);\n }\n}\n\n// ─── Token 预算截断转换器 ─────────────────────────────────────────\n\n/**\n * 按模型 contextWindow 的 token 预算截断上下文。\n *\n * 条数截断(TruncationTransformer)无法防止 token 溢出:200 条消息可能远超\n * 模型上下文窗口。本转换器按 token 估算从最旧的非关键\n * 资源开始丢弃,直到总 token 低于预算(默认 contextWindow * 0.8,预留输出空间)。\n */\nexport class TokenBudgetTransformer extends BaseTransformer {\n readonly name = 'token-budget';\n\n constructor(private ratio: number = 0.8) {\n super();\n }\n\n protected async run(\n resources: ContextResource[],\n context: TransformContext,\n ): Promise<ContextResource[]> {\n const contextWindow = context.runtime.contextWindow;\n if (!contextWindow || contextWindow <= 0) return resources;\n\n const ratio = context.runtime.contextBudgetRatio ?? this.ratio ?? 0.8;\n const budget = Math.floor(contextWindow * ratio);\n\n const pinned = resources.filter(r => r.pinned);\n const unpinned = resources.filter(r => !r.pinned); // 按时间顺序:旧在前\n\n let total = pinned.reduce((sum, r) => sum + estimateResourceTokens(r), 0)\n + unpinned.reduce((sum, r) => sum + estimateResourceTokens(r), 0);\n if (total <= budget) return resources;\n\n // 从头部(最旧)开始丢弃,直到总 token <= 预算。\n // 配对组感知:丢弃 assistant(toolCall) 时记录其 toolCallId,\n // 后续对应的 toolResult 也一并丢弃。\n const droppedToolCallIds = new Set<string>();\n let i = 0;\n while (i < unpinned.length && total > budget) {\n const res = unpinned[i];\n total -= estimateResourceTokens(res);\n if (res.type === 'assistant_message') {\n for (const dep of res.dependencies) droppedToolCallIds.add(dep);\n }\n i++;\n }\n\n // 保留未丢弃部分,并移除与已丢弃 toolCall 配对的 toolResult\n const kept = unpinned.slice(i).filter(res => {\n if (res.type === 'tool_result') {\n const tcId = (res.meta as { toolCallId?: string } | undefined)?.toolCallId;\n if (tcId && droppedToolCallIds.has(tcId)) return false;\n }\n return true;\n });\n\n return [...pinned, ...kept].sort((a, b) => a.timestamp - b.timestamp);\n }\n}\n\n// ─── 系统消息清理转换器 ───────────────────────────────────────────\n\n/**\n * 移除重复的系统消息,只保留最后一条。\n */\nexport class SystemMessageCleanerTransformer extends BaseTransformer {\n readonly name = 'system-message-cleaner';\n\n protected async run(\n resources: ContextResource[],\n _context: TransformContext,\n ): Promise<ContextResource[]> {\n const systemMessages = resources.filter(r => r.type === 'system_message');\n if (systemMessages.length <= 1) return resources;\n\n // 保留最后一条系统消息\n const lastSystem = systemMessages[systemMessages.length - 1];\n return resources.filter(r => r.type !== 'system_message' || r === lastSystem);\n }\n}\n\n// ─── 转换器工厂 ───────────────────────────────────────────────────\n\nexport function createDefaultTransformers(options?: {\n getStateSnapshot?: () => string | null;\n maxResources?: number;\n contextBudgetRatio?: number;\n}): import('../core').ContextTransformer[] {\n const transformers: import('../core').ContextTransformer[] = [\n new SystemMessageCleanerTransformer(),\n new TruncationTransformer(options?.maxResources ?? 200),\n new TokenBudgetTransformer(options?.contextBudgetRatio ?? 0.8),\n new ToolPairingTransformer(), // 放在最后,兜底修复配对\n ];\n\n if (options?.getStateSnapshot) {\n transformers.push(new StateSnapshotTransformer(options.getStateSnapshot));\n }\n\n return transformers;\n}\n","/**\n * packages/runtime - 运行时核心实现\n *\n * 独立实现的 Runtime,不依赖 src/。\n * Runtime 是整个 Agent 系统的核心调度器,\n * 负责协调对话循环、工具执行、上下文转换和插件钩子。\n */\n\nimport type {\n Runtime,\n Compilation,\n RuntimeOptions,\n CompactionOptions,\n Request,\n Result,\n ResultChunk,\n Extension,\n RuntimeHooks,\n ExtensionContext,\n ContextTransformer,\n TransformContext,\n ToolCallContext,\n BeforeToolCallDecision,\n AfterToolCallDecision,\n PermissionRequest,\n PermissionPolicy,\n ApprovalManager,\n} from '../core';\nimport {\n ExtensionManager,\n createTaskGraph,\n ResultBuilder,\n isErrorToolResult,\n} from '../core';\nimport type {\n Model,\n Tool,\n StreamFn,\n Message,\n UserMessage,\n AssistantMessage,\n ToolResultMessage,\n ContentBlock,\n ToolCallContent,\n ImageContent,\n Usage,\n Context,\n StreamOptions,\n StreamEvent,\n ThinkingLevel,\n ToolResult,\n} from '../core';\nimport {\n extractText,\n extractToolCalls,\n createTextContent,\n createEmptyUsage,\n SESSION_VERSION,\n} from '../core';\nimport type {\n SessionStorage,\n StoredSession,\n SessionModel,\n} from '../core';\nimport type { Telemetry, ErrorClass, CompactionTelemetryInfo } from '../telemetry';\nimport { validateRequest, normalizeRequest } from '../request';\nimport {\n messagesToResources,\n resourcesToMessages,\n} from '../context-resource';\nimport { classifyError, isAgentError, isContextOverflow } from '../ai';\nimport { ensureToolPairing } from '../transformer';\nimport { randomUUID } from 'node:crypto';\n\n// ─── traceId / spanId 生成(零新依赖)────────────────────────────\n\nfunction newTraceId(): string {\n return `${Date.now().toString(36)}-${randomUUID()}`;\n}\n\nfunction newSpanId(): string {\n return randomUUID();\n}\n\n/** 从流错误消息的 \"[category]\" 前缀解析错误分类(formatCategoryError 产出) */\nfunction errorClassFromMessage(message: string): string | undefined {\n const m = message.match(/^\\[([^\\]]+)\\]/);\n return m ? m[1] : undefined;\n}\n\n/** 工具结果状态分类:error(执行失败) / ok(正常)。blocked/skipped 不进入 onToolCall */\nfunction toolResultStatus(result: ToolResult): 'ok' | 'error' | 'blocked' | 'skipped' {\n if (result.details && typeof result.details === 'object' && 'error' in result.details) {\n return 'error';\n }\n const d = result.details as { blocked?: boolean; skipped?: boolean } | undefined;\n if (d?.blocked) return 'blocked';\n if (d?.skipped) return 'skipped';\n return 'ok';\n}\n\n/** 从重试错误对象提取 HTTP 状态码(AgentError 或 fetch Response) */\nfunction statusOfRetryError(error: unknown): number | undefined {\n if (isAgentError(error)) return error.status;\n const s = (error as { status?: unknown } | null)?.status;\n return typeof s === 'number' ? s : undefined;\n}\n\n// ─── 会话状态 ─────────────────────────────────────────────────────\n\ninterface SessionState {\n messages: Message[];\n isStreaming: boolean;\n abortController: AbortController | null;\n createdAt: string; // 会话首次创建时间,持久化时保留\n hydrated: boolean; // 是否已从存储恢复(串行化后无竞态)\n /** 串行队列:同一会话的 run/stream 依次执行,避免消息数组交错与 abort 覆盖 */\n queue: Promise<void>;\n /** 等待空闲的 resolver,isStreaming 变 false 时逐个唤醒 */\n idleResolvers: Array<() => void>;\n /** 是否持有执行锁(acquire 后 → release 前)。LRU 淘汰时保护刚入队未开始运行的会话 */\n lockHeld: boolean;\n}\n\n/** 内存会话状态表 LRU 上限(仅清理内存态,不删存储;超限淘汰最久未用) */\nconst DEFAULT_MAX_SESSIONS = 256;\n\nfunction createSessionState(): SessionState {\n return {\n messages: [],\n isStreaming: false,\n abortController: null,\n createdAt: new Date().toISOString(),\n hydrated: false,\n queue: Promise.resolve(),\n idleResolvers: [],\n lockHeld: false,\n };\n}\n\n// ─── 工具超时信号(Node 18 无 AbortSignal.any,手动桥接)─────────\n\nfunction withTimeoutSignal(\n parent: AbortSignal | undefined,\n ms: number,\n): { signal: AbortSignal; clear: () => void } {\n const controller = new AbortController();\n const timer = setTimeout(\n () => controller.abort(new Error(`Tool execution timeout after ${ms}ms`)),\n ms,\n );\n if (parent) {\n if (parent.aborted) {\n controller.abort(parent.reason);\n } else {\n parent.addEventListener(\n 'abort',\n () => controller.abort(parent.reason),\n { once: true },\n );\n }\n }\n return { signal: controller.signal, clear: () => clearTimeout(timer) };\n}\n\n// ─── 媒体附件 → ImageContent ──────────────────────────────────────\n\nfunction buildImageContent(media: string): ImageContent {\n const dataMatch = media.match(/^data:([^;]+);base64,(.*)$/s);\n if (dataMatch) {\n return { type: 'image', mimeType: dataMatch[1], data: dataMatch[2] };\n }\n // 非 data URI 视为 URL(ImageContent.data 字段同时接受 base64 与 URL)\n return { type: 'image', mimeType: 'image/url', data: media };\n}\n\n// ─── 上下文溢出自动恢复 ────────────────────────────────────────────\n\n/** 单回合内溢出恢复重试上限(截断后仍溢出最多再试 2 次,防止死循环) */\nconst OVERFLOW_RECOVERY_LIMIT = 2;\n\n/** 粗略 token 估算(与 transformer 层同口径:约 4 字符/token) */\nfunction estimateMessageTokens(message: Message): number {\n const content = message.content;\n if (typeof content === 'string') return Math.ceil(content.length / 4);\n try {\n return Math.ceil(JSON.stringify(content ?? []).length / 4);\n } catch {\n return 0;\n }\n}\n\n/** 估算文本 token(与 estimateMessageTokens 同口径) */\nfunction estimateTextTokens(text: string): number {\n return Math.ceil(text.length / 4);\n}\n\n// ─── 内置摘要压缩 ─────────────────────────────────────────────────\n\n/**\n * 摘要请求输入预算:占 contextWindow 的比例。\n * 被压缩段序列化后超过该预算时不再发起摘要请求(请求本身必然超窗),\n * 直接降级硬截断,避免 doomed 调用。\n */\nconst COMPACTION_SUMMARY_BUDGET_RATIO = 0.6;\n\n/** 摘要请求单条消息的序列化字符上限(防单条巨型 toolResult 撑爆摘要请求) */\nconst COMPACTION_LINE_CLAMP = 4000;\n\n/** 默认摘要指令 */\nconst DEFAULT_COMPACTION_PROMPT = [\n '你是对话历史压缩器。请将以下对话历史压缩为一份信息密度高的摘要,供后续对话作为上下文参考。',\n '要求:',\n '1. 保留关键事实、决策、结论与未完成事项;',\n '2. 保留用户明确的偏好与约束;',\n '3. 保留重要工具调用的目的与结果要点(细节可省略);',\n '4. 丢弃寒暄、重复与无关细节;',\n '5. 直接输出摘要正文,不要任何前后缀说明。',\n].join('\\n');\n\n/** compactionSummary 消息发给 provider 时转换后的 user 消息前缀 */\nconst COMPACTION_USER_PREFIX = '[以下为此前对话历史的压缩摘要,作为上下文参考]';\n\n/** 序列化单条消息为摘要输入行;system 等无关角色返回空串 */\nfunction messageToSummaryLine(msg: Message): string {\n const clamp = (text: string): string =>\n text.length > COMPACTION_LINE_CLAMP\n ? `${text.slice(0, COMPACTION_LINE_CLAMP)}…(已截断)`\n : text;\n\n switch (msg.role) {\n case 'user': {\n const text = typeof msg.content === 'string' ? msg.content : extractText(msg.content);\n return `[用户] ${clamp(text)}`;\n }\n case 'assistant': {\n const parts: string[] = [];\n const content = msg.content;\n if (typeof content === 'string') {\n parts.push(content);\n } else {\n for (const block of content) {\n if (block.type === 'text') parts.push(block.text);\n else if (block.type === 'toolCall') {\n parts.push(`调用工具 ${block.name}(${JSON.stringify(block.arguments)})`);\n }\n }\n }\n return `[助手] ${clamp(parts.join(';'))}`;\n }\n case 'toolResult': {\n const m = msg as ToolResultMessage;\n const text = typeof m.content === 'string' ? m.content : extractText(m.content);\n return `[工具结果 ${m.toolName}] ${clamp(text)}`;\n }\n default: {\n // Message union 之外的扩展 role(compactionSummary / stateSnapshot 等)\n const role = (msg as { role: string }).role;\n // 已有的旧摘要/状态快照融入新摘要,避免反复压缩丢失早期信息\n if (role === 'compactionSummary' || role === 'stateSnapshot') {\n const text = typeof msg.content === 'string' ? msg.content : extractText(msg.content);\n return `[${role === 'compactionSummary' ? '历史摘要' : '状态快照'}] ${clamp(text)}`;\n }\n return '';\n }\n }\n}\n\n// ─── 工具执行结果(含 terminate 信号) ─────────────────────────────\n\n/**\n * 单次/一组工具执行的产出。除结果列表外,携带 terminate 信号:\n * beforeToolCall / afterToolCall 可请求终止整个 run,\n * runLoop 检测到后停止循环(本轮工具结果仍写入会话以保持配对完整)。\n */\ninterface ToolExecutionOutcome {\n results: ToolResult[];\n /** 是否请求终止整个 run */\n terminate: boolean;\n /** 终止原因(写入 Result.metadata.terminateReason) */\n terminateReason?: string;\n}\n\n/** 单个工具执行的产出(含 terminate 信号) */\ninterface SingleToolOutcome {\n result: ToolResult;\n terminate: boolean;\n terminateReason?: string;\n}\n\n// ─── AgentRuntime: Runtime 接口的独立实现 ─────────────────────────\n\nexport class AgentRuntime implements Runtime {\n private _config: Record<string, unknown>;\n private _extensions: ExtensionManager;\n private _hooks: RuntimeHooks;\n /** 上下文转换器列表,按数组顺序链式执行(上一个输出作为下一个输入) */\n private _transformers: ContextTransformer[];\n\n private _model: Model;\n private _streamFn: StreamFn;\n private _systemPrompt: string;\n private _thinkingLevel: ThinkingLevel;\n private _globalTools: Map<string, Tool> = new Map();\n\n /** 多会话状态表:key = sessionKey。模型/工具/扩展/转换器等资源跨会话共享 */\n private _sessions: Map<string, SessionState>;\n /** 默认会话 key(常量 'default';请求未指定 sessionKey 时路由到此会话) */\n private _sessionKey: string;\n /** 内存会话状态表 LRU 上限 */\n private _maxSessions: number;\n private _sessionStorage: SessionStorage | undefined;\n /** Extension 应用时的上下文(shared Map 供 ToolCallContext 引用) */\n private _extensionContext?: ExtensionContext;\n\n private _maxTurns: number;\n private _toolTimeoutMs: number;\n private _parallelToolCalls: boolean;\n private _contextBudgetRatio: number;\n /** 内置摘要压缩配置(未配置 = 保持旧行为,仅硬截断兜底) */\n private _compaction: CompactionOptions | undefined;\n private _telemetry: Telemetry | undefined;\n /** 框架级工具权限策略(未配置 → 放行,向后兼容) */\n private _permissionPolicy: PermissionPolicy | undefined;\n /** 审批管理器(pending 决策挂起等待外部批准;未配置 → pending 视为 deny) */\n private _approvals: ApprovalManager | undefined;\n /** 审批等待超时(毫秒) */\n private _approvalTimeoutMs: number;\n /** traceId 生成器(测试可注入确定性 id) */\n private _traceIdGenerator: (() => string) | undefined;\n\n private constructor(options: RuntimeOptions) {\n this._config = options.config ?? {};\n this._extensions = new ExtensionManager();\n this._hooks = this._extensions.getHooks();\n // 转换器按传入顺序链式执行(上一个输出作为下一个输入)\n this._transformers = [...(options.transformers ?? [])];\n\n this._model = options.model ?? {\n id: 'unknown',\n name: 'unknown',\n provider: 'unknown',\n contextWindow: 128000,\n maxTokens: 8192,\n reasoning: false,\n };\n\n this._streamFn = options.streamFn ?? (async function* () {\n throw new Error('streamFn 未设置,请通过 setStreamFn() 或 RuntimeOptions.streamFn 提供');\n });\n\n this._systemPrompt = options.systemPrompt ?? '';\n this._thinkingLevel = options.thinkingLevel ?? 'off';\n this._sessionStorage = options.sessionStorage;\n\n this._maxTurns = options.maxTurns ?? 50;\n this._toolTimeoutMs = options.toolTimeoutMs ?? 120_000;\n this._parallelToolCalls = options.parallelToolCalls ?? true;\n this._contextBudgetRatio = options.contextBudgetRatio ?? 0.8;\n this._compaction = options.compaction;\n this._telemetry = options.telemetry;\n this._permissionPolicy = options.permissionPolicy;\n this._approvals = options.approvals;\n this._approvalTimeoutMs = options.approvalTimeoutMs ?? 300_000;\n this._traceIdGenerator = options.traceIdGenerator;\n\n // 注册初始工具\n if (options.tools) {\n for (const tool of options.tools) {\n this._globalTools.set(tool.name, tool);\n }\n }\n\n this._sessionKey = 'default';\n this._maxSessions = options.maxSessions ?? DEFAULT_MAX_SESSIONS;\n // 默认会话预先入表,保证未指定 sessionKey 的请求路由到它\n this._sessions = new Map([[this._sessionKey, createSessionState()]]);\n }\n\n // ─── 静态工厂 ───────────────────────────────────────────────────\n\n static create(options: RuntimeOptions = {}): AgentRuntime {\n const runtime = new AgentRuntime(options);\n\n // 注册扩展\n if (options.extensions) {\n runtime._extensions.registerAll(options.extensions);\n }\n\n // 应用扩展到钩子\n const ctx: ExtensionContext = {\n config: runtime._config,\n workspace: options.workspace ?? process.cwd(),\n sessionKey: runtime._sessionKey,\n shared: new Map(),\n runtime,\n };\n runtime._extensionContext = ctx;\n runtime._extensions.applyAll(ctx);\n\n return runtime;\n }\n\n // ─── Runtime 接口实现 ───────────────────────────────────────────\n\n get config(): Record<string, unknown> {\n return this._config;\n }\n\n get extensions(): ExtensionManager {\n return this._extensions;\n }\n\n get hooks(): RuntimeHooks {\n return this._hooks;\n }\n\n // ─── 工具/模型/流管理 ───────────────────────────────────────────\n\n registerTool(tool: Tool): this {\n if (this._globalTools.has(tool.name)) {\n console.warn(`[Runtime] 工具 \"${tool.name}\" 已存在,将被覆盖`);\n }\n this._globalTools.set(tool.name, tool);\n return this;\n }\n\n registerTools(tools: Tool[]): this {\n for (const tool of tools) {\n this.registerTool(tool);\n }\n return this;\n }\n\n unregisterTool(name: string): boolean {\n return this._globalTools.delete(name);\n }\n\n setModel(model: Model): this {\n this._model = model;\n return this;\n }\n\n setSystemPrompt(prompt: string): this {\n this._systemPrompt = prompt;\n return this;\n }\n\n setThinkingLevel(level: ThinkingLevel): this {\n this._thinkingLevel = level;\n return this;\n }\n\n setStreamFn(fn: StreamFn): this {\n this._streamFn = fn;\n return this;\n }\n\n registerExtension(extension: Extension): this {\n this._extensions.register(extension);\n return this;\n }\n\n useTransformer(transformer: ContextTransformer): this {\n this._transformers.push(transformer);\n return this;\n }\n\n /** 获取指定会话的消息列表(默认会话;会话不存在返回空数组) */\n getMessages(sessionKey?: string): Message[] {\n const session = this._sessions.get(sessionKey ?? this._sessionKey);\n if (!session) return [];\n // 返回深拷贝,避免外部直接修改会话内部状态\n const messages = session.messages;\n try {\n return structuredClone(messages);\n } catch {\n return JSON.parse(JSON.stringify(messages));\n }\n }\n\n // ─── 核心运行逻辑 ───────────────────────────────────────────────\n\n /** 解析请求路由的会话 key:request.sessionKey ?? 默认会话 key */\n private resolveSessionKey(request: Request): string {\n return request.sessionKey ?? this._sessionKey;\n }\n\n /**\n * 获取(懒创建)会话状态。同一 Runtime 下不同 sessionKey 的消息历史、\n * 串行队列、abort 控制相互独立;共享模型/工具/扩展/转换器。\n * 超过 _maxSessions 时淘汰最久未用的非活动会话(仅清内存态,不删存储)。\n */\n private getSession(key: string): SessionState {\n let session = this._sessions.get(key);\n if (session) {\n // 刷新 LRU 顺序(Map 尾 = 最近使用)\n this._sessions.delete(key);\n this._sessions.set(key, session);\n return session;\n }\n session = createSessionState();\n this._sessions.set(key, session);\n this.evictIdleSessions();\n return session;\n }\n\n /** LRU 淘汰:仅淘汰非活动(未运行、未排队)的最久未用会话 */\n private evictIdleSessions(): void {\n if (this._sessions.size <= this._maxSessions) return;\n for (const [key, session] of this._sessions) {\n if (this._sessions.size <= this._maxSessions) break;\n // 运行中 / 已持有锁(入队待执行)不淘汰\n if (session.isStreaming || session.lockHeld) continue;\n this._sessions.delete(key);\n }\n }\n\n /** 当前活跃的会话 key 列表(含默认会话) */\n getSessionKeys(): string[] {\n return Array.from(this._sessions.keys());\n }\n\n /** 某会话是否存在(内存中) */\n hasSession(sessionKey: string): boolean {\n return this._sessions.has(sessionKey);\n }\n\n async run(request: Request): Promise<Result> {\n // 0. 校验请求\n const validation = validateRequest(request);\n if (!validation.valid) {\n const invalidResult = new ResultBuilder()\n .error(`请求校验失败: ${validation.errors.join('; ')}`)\n .build();\n // 校验失败也要可观测(errorClass='validation'),不进入排队\n await this.emitTelemetry('onRunEnd', {\n traceId: this.newTraceId(),\n sessionKey: this.resolveSessionKey(request),\n request,\n durationMs: 0,\n activeMs: 0,\n queuedMs: 0,\n turnCount: 0,\n result: invalidResult,\n success: false,\n errorClass: 'validation',\n tokens: { input: 0, output: 0 },\n });\n return invalidResult;\n }\n const finalRequest = normalizeRequest(request);\n const sessionKey = this.resolveSessionKey(finalRequest);\n const traceId = this.newTraceId();\n const queuedAt = Date.now();\n\n // 1. 入队前:onRunStart(配合 onRunEnd 求排队时长 queuedMs)\n await this.emitTelemetry('onRunStart', {\n traceId,\n sessionKey,\n request: finalRequest,\n queuedAt,\n });\n\n // 2. 串行化:同一会话的请求依次执行\n const session = this.getSession(sessionKey);\n const release = await this.acquire(session);\n const queuedMs = Date.now() - queuedAt;\n\n try {\n return await this.runWithStorageLock(finalRequest, sessionKey, () =>\n this._run(finalRequest, sessionKey, session, traceId, queuedMs),\n );\n } finally {\n release();\n }\n }\n\n async *stream(request: Request): AsyncGenerator<ResultChunk> {\n // 0. 校验请求\n const validation = validateRequest(request);\n if (!validation.valid) {\n const message = `请求校验失败: ${validation.errors.join('; ')}`;\n await this.emitTelemetry('onRunEnd', {\n traceId: this.newTraceId(),\n sessionKey: this.resolveSessionKey(request),\n request,\n durationMs: 0,\n activeMs: 0,\n queuedMs: 0,\n turnCount: 0,\n result: new ResultBuilder().error(message).build(),\n success: false,\n errorClass: 'validation',\n tokens: { input: 0, output: 0 },\n });\n yield { type: 'error', content: message };\n yield { type: 'done' };\n return;\n }\n const finalRequest = normalizeRequest(request);\n const sessionKey = this.resolveSessionKey(finalRequest);\n const traceId = this.newTraceId();\n const queuedAt = Date.now();\n\n await this.emitTelemetry('onRunStart', {\n traceId,\n sessionKey,\n request: finalRequest,\n queuedAt,\n });\n\n // 1. 串行化\n const session = this.getSession(sessionKey);\n const release = await this.acquire(session);\n const queuedMs = Date.now() - queuedAt;\n\n try {\n yield* this.streamWithStorageLock(finalRequest, sessionKey, () =>\n this._stream(finalRequest, sessionKey, session, traceId, queuedMs),\n );\n } finally {\n release();\n }\n }\n\n /**\n * 非 ephemeral 请求在\"读(load)-改(run)-写(save)\"全程持有存储级锁,\n * 防止多进程并发写同一会话导致 last-write-wins 丢消息。\n * ephemeral / 无锁支持 / 无存储时直接执行。\n */\n private async runWithStorageLock<T>(\n request: Request,\n sessionKey: string,\n fn: () => Promise<T>,\n ): Promise<T> {\n const storage = this._sessionStorage;\n if (request.ephemeral || !storage?.withLock) return fn();\n return storage.withLock(sessionKey, fn);\n }\n\n /** 流式版本:无法用回调包住生成器,改用手动锁(acquire/release) */\n private async *streamWithStorageLock(\n request: Request,\n sessionKey: string,\n gen: () => AsyncGenerator<ResultChunk>,\n ): AsyncGenerator<ResultChunk> {\n const storage = this._sessionStorage;\n if (request.ephemeral || !storage?.acquireLock) {\n yield* gen();\n return;\n }\n const lock = await storage.acquireLock(sessionKey);\n try {\n yield* gen();\n } finally {\n await lock.release();\n }\n }\n\n private async _run(\n request: Request,\n sessionKey: string,\n session: SessionState,\n traceId: string,\n queuedMs: number,\n ): Promise<Result> {\n const activeStartedAt = Date.now();\n\n // 1. 触发 beforeInitialize / afterInitialize\n await this._hooks.beforeInitialize.promise(request);\n await this._hooks.afterInitialize.promise(request);\n\n // 2. beforeRun(waterfall,可修改请求)\n const finalRequest = await this._hooks.beforeRun.promise(request);\n\n // 3. 会话持久化:从存储恢复历史消息(ephemeral 跳过)\n if (!finalRequest.ephemeral) {\n await this.hydrateSession(sessionKey, session);\n }\n\n // 4. 创建编译上下文\n const compilation = this.createCompilation(finalRequest, sessionKey, session, traceId);\n\n // 5. 添加用户消息(含媒体附件)\n compilation.messages.push(this.buildUserMessage(finalRequest));\n\n // 6. 运行对话循环\n try {\n await this.runLoop(compilation, finalRequest, session);\n\n // 7. 构建结果\n const result = this.buildResult(compilation);\n\n // 8. 触发 beforeEmit / afterEmit\n await this._hooks.beforeEmit.promise(result);\n await this._hooks.afterEmit.promise(result);\n\n // 9. 触发 done(携带最终 Request,供钩子按会话配对)\n await this._hooks.done.promise(result, finalRequest);\n\n compilation.completed = true;\n await this.emitRunEnd(finalRequest, sessionKey, compilation, result, queuedMs, activeStartedAt);\n return result;\n } catch (err) {\n const error = err as Error;\n // 非中止错误打印栈,便于线上排障(此前 catch 全部静默转 Result.error,丢栈)\n if (error?.name !== 'AbortError') {\n console.error('[Runtime] 运行失败:', error?.stack ?? error);\n }\n await this._hooks.failed.promise(error, finalRequest);\n\n const result = new ResultBuilder()\n .error(error.message)\n .build();\n await this.emitRunEnd(finalRequest, sessionKey, compilation, result, queuedMs, activeStartedAt);\n return result;\n } finally {\n // 10. 结束前最终保存会话(ephemeral 不持久化;失败不影响运行结果)\n await this.persistSessionSafe(finalRequest, sessionKey);\n }\n }\n\n private async *_stream(\n request: Request,\n sessionKey: string,\n session: SessionState,\n traceId: string,\n queuedMs: number,\n ): AsyncGenerator<ResultChunk> {\n const activeStartedAt = Date.now();\n\n // 1. 钩子\n await this._hooks.beforeInitialize.promise(request);\n await this._hooks.afterInitialize.promise(request);\n const finalRequest = await this._hooks.beforeRun.promise(request);\n\n // 2. 会话持久化:从存储恢复历史消息(ephemeral 跳过)\n if (!finalRequest.ephemeral) {\n await this.hydrateSession(sessionKey, session);\n }\n\n // 3. 创建编译上下文\n const compilation = this.createCompilation(finalRequest, sessionKey, session, traceId);\n\n // 4. 添加用户消息(含媒体附件)\n compilation.messages.push(this.buildUserMessage(finalRequest));\n\n // 5. 流式对话循环\n try {\n for await (const chunk of this.runLoopStream(compilation, finalRequest, session)) {\n yield chunk;\n }\n\n // 6. 构建并触发结果钩子\n const result = this.buildResult(compilation);\n await this._hooks.beforeEmit.promise(result);\n await this._hooks.afterEmit.promise(result);\n await this._hooks.done.promise(result, finalRequest);\n\n yield { type: 'done', result };\n await this.emitRunEnd(finalRequest, sessionKey, compilation, result, queuedMs, activeStartedAt);\n } catch (err) {\n const error = err as Error;\n if (error?.name !== 'AbortError') {\n console.error('[Runtime] 流式运行失败:', error?.stack ?? error);\n }\n await this._hooks.failed.promise(error, finalRequest);\n const result = new ResultBuilder().error(error.message).build();\n yield { type: 'error', content: error.message };\n yield { type: 'done', result };\n await this.emitRunEnd(finalRequest, sessionKey, compilation, result, queuedMs, activeStartedAt);\n } finally {\n await this.persistSessionSafe(finalRequest, sessionKey);\n }\n }\n\n createCompilation(request: Request, sessionKey?: string, session?: SessionState, traceId?: string): Compilation {\n return {\n request,\n graph: createTaskGraph(),\n resources: [],\n messages: (session ?? this.getSession(sessionKey ?? this._sessionKey)).messages,\n completed: false,\n traceId: traceId ?? this.newTraceId(),\n };\n }\n\n async close(): Promise<void> {\n // 等待所有会话的在途任务完成,再清理\n await Promise.allSettled(Array.from(this._sessions.values(), s => s.queue));\n\n for (const session of this._sessions.values()) {\n session.messages = [];\n session.hydrated = false;\n }\n this._sessions.clear();\n this._extensions.clear();\n this._transformers = [];\n }\n\n // ─── 对话循环(同步) ───────────────────────────────────────────\n\n private async runLoop(\n compilation: Compilation,\n request: Request,\n session: SessionState,\n ): Promise<void> {\n session.isStreaming = true;\n session.abortController = new AbortController();\n // 多会话路由:本次循环所属会话(请求携带的 sessionKey 优先)\n const sessionKey = this.resolveSessionKey(request);\n\n try {\n let maxTurns = this._maxTurns;\n let turnCount = 0; // step 长度:实际对话轮数(与 maxTurns 上限解耦)\n\n while (maxTurns-- > 0) {\n turnCount += 1;\n\n // 1. 链式转换上下文(原地替换,保持 session 引用)\n await this.transformMessages(compilation, sessionKey);\n\n // 1.5 阈值触发内置摘要压缩(估算 token 超窗口比例时,先摘要后截断兜底)\n await this.maybeCompactByThreshold(\n compilation, sessionKey, session.abortController!.signal,\n );\n\n // 2. 调用模型(streamModel 内部走统一埋点 streamModelEvents,\n // 含溢出自动恢复:检测 → 截断历史 → 同回合重试)\n const assistantMessage = await this.streamModel(\n compilation,\n session.abortController!.signal,\n sessionKey,\n );\n\n compilation.messages.push(assistantMessage);\n // 3.1 实时持久化:assistant 回复完成即落盘(运行中可查看最新会话)\n await this.persistSessionSafe(request, sessionKey);\n\n // 4. 检查工具调用\n const toolCalls = extractToolCalls(assistantMessage.content);\n\n if (toolCalls.length === 0) {\n break; // 无工具调用,结束循环\n }\n\n // 5. 执行工具(可选并行)\n const outcome = await this.executeToolCalls(\n compilation,\n toolCalls,\n session.abortController!.signal,\n );\n // 5.1 实时持久化:工具结果落盘\n await this.persistSessionSafe(request, sessionKey);\n // 5.2 beforeToolCall/afterToolCall 请求终止:停止循环\n if (outcome.terminate) {\n compilation.terminateReason = outcome.terminateReason ?? 'terminated';\n break;\n }\n }\n\n // 回合上限耗尽(循环条件失效而非 break 退出,maxTurns 已减至 -1):\n // 模型仍请求工具调用但被截断,标记供 buildResult 输出 'max_turns'\n if (maxTurns < 0) compilation.maxTurnsExhausted = true;\n compilation.turnCount = turnCount;\n } finally {\n this.markIdle(session);\n }\n }\n\n // ─── 对话循环(流式) ───────────────────────────────────────────\n\n private async *runLoopStream(\n compilation: Compilation,\n request: Request,\n session: SessionState,\n ): AsyncGenerator<ResultChunk> {\n session.isStreaming = true;\n session.abortController = new AbortController();\n // 多会话路由:本次流式循环所属会话\n const sessionKey = this.resolveSessionKey(request);\n\n try {\n let maxTurns = this._maxTurns;\n let turnCount = 0; // step 长度:实际对话轮数(与 maxTurns 上限解耦)\n\n while (maxTurns-- > 0) {\n turnCount += 1;\n\n // 1. 链式转换上下文(原地替换,保持 session 引用)\n await this.transformMessages(compilation, sessionKey);\n\n // 1.5 阈值触发内置摘要压缩(估算 token 超窗口比例时,先摘要后截断兜底)\n await this.maybeCompactByThreshold(\n compilation, sessionKey, session.abortController!.signal,\n );\n\n // 2. 流式调用模型(统一埋点 + 溢出自动恢复:可恢复的溢出错误\n // 吞掉 error chunk,截断历史后同回合重试)\n const turn = this.modelTurnWithRecovery(\n compilation,\n session.abortController!.signal,\n sessionKey,\n true, // stream 模式:同时统计首 token 延迟\n );\n let turnResult = await turn.next();\n while (!turnResult.done) {\n yield turnResult.value;\n turnResult = await turn.next();\n }\n const assistantMessage = turnResult.value;\n\n if (!assistantMessage) break;\n compilation.messages.push(assistantMessage);\n // 3.1 实时持久化:assistant 回复完成即落盘(运行中可查看最新会话)\n await this.persistSessionSafe(request, sessionKey);\n\n // 4. 检查工具调用\n const toolCalls = extractToolCalls(assistantMessage.content);\n\n if (toolCalls.length === 0) {\n break;\n }\n\n // 5. 执行工具\n for (const toolCall of toolCalls) {\n yield {\n type: 'tool_start',\n toolName: toolCall.name,\n toolCallId: toolCall.id,\n };\n }\n\n const outcome = await this.executeToolCallsStreaming(\n compilation,\n toolCalls,\n session.abortController!.signal,\n );\n // 5.1 实时持久化:工具结果落盘\n await this.persistSessionSafe(request, sessionKey);\n\n // 5.2 yield tool_end(block 的工具也产出事件,便于前端展示被拒调用)\n for (let i = 0; i < toolCalls.length; i++) {\n yield {\n type: 'tool_end',\n toolName: toolCalls[i].name,\n toolCallId: toolCalls[i].id,\n isError: this.isErrorResult(outcome.results[i]),\n };\n }\n\n // 5.3 beforeToolCall/afterToolCall 请求终止:tool_end 之后再停止循环\n if (outcome.terminate) {\n compilation.terminateReason = outcome.terminateReason ?? 'terminated';\n break;\n }\n }\n\n // 回合上限耗尽(循环条件失效而非 break 退出,maxTurns 已减至 -1):\n // 模型仍请求工具调用但被截断,标记供 buildResult 输出 'max_turns'\n if (maxTurns < 0) compilation.maxTurnsExhausted = true;\n compilation.turnCount = turnCount;\n } finally {\n this.markIdle(session);\n }\n }\n\n // ─── 工具执行 ───────────────────────────────────────────────────\n\n /** 同步循环:执行工具调用并将结果消息按原顺序追加 */\n private async executeToolCalls(\n compilation: Compilation,\n toolCalls: ToolCallContent[],\n signal: AbortSignal,\n ): Promise<ToolExecutionOutcome> {\n const outcome = await this.runTools(toolCalls, signal, compilation.request, compilation.traceId);\n for (let i = 0; i < toolCalls.length; i++) {\n compilation.messages.push(\n this.buildToolResultMessage(toolCalls[i], outcome.results[i]),\n );\n }\n return outcome;\n }\n\n /** 流式循环:执行工具调用,返回结果(消息由调用方追加) */\n private async executeToolCallsStreaming(\n compilation: Compilation,\n toolCalls: ToolCallContent[],\n signal: AbortSignal,\n ): Promise<ToolExecutionOutcome> {\n const outcome = await this.runTools(toolCalls, signal, compilation.request, compilation.traceId);\n for (let i = 0; i < toolCalls.length; i++) {\n compilation.messages.push(\n this.buildToolResultMessage(toolCalls[i], outcome.results[i]),\n );\n }\n return outcome;\n }\n\n /**\n * 执行一组工具调用:parallelToolCalls 为 true 时并行,否则串行。\n * 返回 ToolExecutionOutcome:任一工具请求 terminate 即终止整个 run;\n * 串行模式下 terminate 后剩余工具生成 skipped 结果以保持配对完整。\n */\n private async runTools(\n toolCalls: ToolCallContent[],\n signal: AbortSignal,\n request: Request,\n traceId: string,\n ): Promise<ToolExecutionOutcome> {\n const execute = (tc: ToolCallContent) => this.executeTool(tc, signal, request, traceId);\n\n if (this._parallelToolCalls && toolCalls.length > 1) {\n // 并行:全部执行,聚合 terminate(取第一个命中的原因)\n const outcomes = await Promise.all(toolCalls.map(execute));\n const terminated = outcomes.find(o => o.terminate);\n return {\n results: outcomes.map(o => o.result),\n terminate: !!terminated,\n terminateReason: terminated?.terminateReason,\n };\n }\n\n // 串行:依次执行;遇 terminate 后剩余工具跳过执行(生成 skipped 结果保持配对)\n const results: ToolResult[] = [];\n let terminate = false;\n let terminateReason: string | undefined;\n for (const tc of toolCalls) {\n if (terminate) {\n results.push(this.makeSkippedResult(tc));\n continue;\n }\n const outcome = await execute(tc);\n results.push(outcome.result);\n if (outcome.terminate) {\n terminate = true;\n terminateReason = outcome.terminateReason;\n }\n }\n return { results, terminate, terminateReason };\n }\n\n private async executeTool(\n toolCall: ToolCallContent,\n signal: AbortSignal | undefined,\n request: Request,\n traceId: string,\n ): Promise<SingleToolOutcome> {\n const tool = this._globalTools.get(toolCall.name);\n\n if (!tool) {\n return {\n result: {\n content: [createTextContent(`Tool \"${toolCall.name}\" not found`)],\n details: { error: `Tool \"${toolCall.name}\" not found` },\n },\n terminate: false,\n };\n }\n\n // ─── 参数预处理(权限裁决与执行钩子均基于处理后的 args)───\n let args: unknown = toolCall.arguments;\n if (tool.prepareArguments) {\n args = tool.prepareArguments(toolCall.arguments);\n }\n\n // ─── PermissionPolicy:框架级安全底线,先于扩展钩子裁决 ───\n // 未配置策略 → 放行(向后兼容);deny / confirm 未批准 → blocked 结果;\n // pending → 挂起等待外部审批(超时 / run abort 均视为拒绝)\n if (this._permissionPolicy) {\n const permissionReq: PermissionRequest = {\n toolName: toolCall.name,\n permissions: tool.permissions ?? [],\n args,\n sessionKey: request.sessionKey ?? this._sessionKey,\n request,\n shared: this._extensionContext?.shared ?? new Map(),\n };\n const decision = await this._permissionPolicy.check(permissionReq);\n let allowed = decision === 'allow';\n if (decision === 'confirm') {\n allowed = this._permissionPolicy.confirm\n ? await this._permissionPolicy.confirm(permissionReq)\n : false;\n }\n if (decision === 'pending') {\n // 挂起等待外部审批(异步 Human-in-the-loop);\n // 未配置审批管理器 → 保守拒绝(与 confirm 未提供回调的行为一致)\n if (this._approvals) {\n const approval = this._approvals.create(permissionReq, {\n timeoutMs: this._approvalTimeoutMs,\n signal,\n });\n await this.emitTelemetry('onApprovalPending', {\n traceId,\n sessionKey: permissionReq.sessionKey,\n approvalId: approval.id,\n toolName: toolCall.name,\n permissions: permissionReq.permissions,\n args,\n expiresAt: approval.expiresAt,\n });\n const outcome = await this._approvals.wait(approval);\n allowed = outcome.status === 'approved';\n await this.emitTelemetry('onApprovalResolved', {\n traceId,\n sessionKey: permissionReq.sessionKey,\n approvalId: approval.id,\n toolName: toolCall.name,\n outcome: outcome.status,\n waitedMs: outcome.waitedMs,\n });\n } else {\n allowed = false;\n }\n }\n if (!allowed) {\n const reason = `permission denied by policy for tool \"${toolCall.name}\"`;\n await this.emitTelemetry('onPermissionDenied', {\n traceId,\n sessionKey: permissionReq.sessionKey,\n toolName: toolCall.name,\n permissions: permissionReq.permissions,\n args,\n reason,\n });\n return {\n result: this.makeBlockedResult(reason),\n terminate: false,\n };\n }\n }\n\n // ─── 工具超时信号:权限裁决(含审批挂起)完成后起表,\n // 审批等待不占用工具执行超时 ───\n const { signal: timedSignal, clear } = withTimeoutSignal(signal, this._toolTimeoutMs);\n try {\n // ─── beforeToolCall:参数校验后、执行前(可 block / terminate / 改写 args)───\n const beforeCtx = this.buildToolCallContext(toolCall, tool, args, request, timedSignal);\n const before: BeforeToolCallDecision = await this._hooks.beforeToolCall.promise(\n { block: false, terminate: false, args },\n beforeCtx,\n );\n\n if (before.terminate) {\n const reason = before.reason ?? 'terminated by beforeToolCall';\n return {\n result: this.makeBlockedResult(reason),\n terminate: true,\n terminateReason: reason,\n };\n }\n if (before.block) {\n const reason = before.reason ?? 'blocked by beforeToolCall';\n return {\n result: this.makeBlockedResult(reason),\n terminate: false,\n };\n }\n // 允许 beforeToolCall 改写参数\n args = before.args;\n\n // ─── 执行工具 ───\n const toolStartedAt = Date.now();\n let result: ToolResult;\n try {\n result = await tool.execute(toolCall.id, args, timedSignal);\n } catch (err) {\n const message = (err as Error)?.message ?? String(err);\n result = {\n content: [createTextContent(message)],\n details: { error: message },\n };\n }\n\n const status = toolResultStatus(result);\n await this.emitTelemetry('onToolCall', {\n traceId,\n spanId: newSpanId(),\n sessionKey: request.sessionKey ?? this._sessionKey,\n toolName: toolCall.name,\n args,\n durationMs: Date.now() - toolStartedAt,\n result,\n success: status === 'ok',\n status,\n errorClass:\n status === 'error'\n ? (errorClassFromMessage(String((result.details as { error?: unknown })?.error ?? '')) as ErrorClass | undefined) ?? 'tool_error'\n : undefined,\n });\n\n // ─── afterToolCall:执行后、事件发出前(可改写 result / terminate)───\n // 用更新后的 args 重建 ctx,让 afterToolCall 看到改写后的参数\n const afterCtx = this.buildToolCallContext(toolCall, tool, args, request, timedSignal);\n const after: AfterToolCallDecision = await this._hooks.afterToolCall.promise(\n { result, terminate: false },\n afterCtx,\n );\n\n return {\n result: after.result,\n terminate: after.terminate,\n terminateReason: after.terminate ? 'terminated by afterToolCall' : undefined,\n };\n } finally {\n clear();\n }\n }\n\n private isErrorResult(result: ToolResult): boolean {\n return !!(result.details && typeof result.details === 'object' && 'error' in result.details);\n }\n\n /** beforeToolCall 阻断/终止时生成拒绝结果(非执行错误,isError=false) */\n private makeBlockedResult(reason: string): ToolResult {\n return {\n content: [createTextContent(`[blocked] ${reason}`)],\n details: { blocked: true, reason },\n };\n }\n\n /** 串行模式下前序工具 terminate 后,剩余工具生成 skipped 结果保持配对 */\n private makeSkippedResult(toolCall: ToolCallContent): ToolResult {\n return {\n content: [createTextContent(`[skipped] run terminated by prior tool: ${toolCall.name}`)],\n details: { skipped: true, toolName: toolCall.name },\n };\n }\n\n /** 构建 ToolCallContext:beforeToolCall/afterToolCall 的调用上下文 */\n private buildToolCallContext(\n toolCall: ToolCallContent,\n tool: Tool,\n args: unknown,\n request: Request,\n signal: AbortSignal,\n ): ToolCallContext {\n return {\n toolCall,\n tool,\n args,\n sessionKey: request.sessionKey ?? this._sessionKey,\n request,\n shared: this._extensionContext?.shared ?? new Map(),\n signal,\n };\n }\n\n private buildToolResultMessage(\n toolCall: ToolCallContent,\n result: ToolResult,\n ): ToolResultMessage {\n return {\n role: 'toolResult',\n content: result.content,\n toolCallId: toolCall.id,\n toolName: toolCall.name,\n isError: this.isErrorResult(result),\n timestamp: Date.now(),\n };\n }\n\n private buildUserMessage(request: Request): UserMessage {\n if (request.media && request.media.length > 0) {\n const blocks: ContentBlock[] = [\n createTextContent(request.message),\n ...request.media.filter(Boolean).map(buildImageContent),\n ];\n return {\n role: 'user',\n content: blocks,\n timestamp: Date.now(),\n };\n }\n return {\n role: 'user',\n content: request.message,\n timestamp: Date.now(),\n };\n }\n\n // ─── 内部方法 ───────────────────────────────────────────────────\n\n /**\n * 获取同一会话的执行锁:返回 release 函数,调用后释放。\n * 同一 sessionKey 的 run/stream 会串行执行,避免消息数组交错、\n * abortController 互相覆盖、hydrate 竞态。\n */\n private async acquire(session: SessionState): Promise<() => void> {\n let release!: () => void;\n const prev = session.queue;\n session.queue = new Promise<void>(resolve => {\n release = () => resolve();\n });\n await prev;\n session.lockHeld = true;\n return () => {\n session.lockHeld = false;\n release();\n };\n }\n\n /** 标记会话空闲并唤醒所有 waitForIdle 等待者 */\n private markIdle(session: SessionState): void {\n session.isStreaming = false;\n session.abortController = null;\n if (session.idleResolvers.length > 0) {\n const resolvers = session.idleResolvers.splice(0);\n for (const resolve of resolvers) resolve();\n }\n }\n\n // ─── 会话持久化 ─────────────────────────────────────────────────\n\n /** 从存储懒加载会话(串行化后无竞态,每个会话仅恢复一次) */\n private async hydrateSession(\n sessionKey: string,\n session: SessionState,\n ): Promise<void> {\n if (!this._sessionStorage) return;\n if (session.hydrated) return;\n session.hydrated = true;\n\n const stored = await this._sessionStorage.load(sessionKey);\n if (!stored) return;\n\n session.messages = stored.messages;\n session.createdAt = stored.createdAt;\n }\n\n /** 整体保存指定会话(ephemeral 跳过;失败不影响运行结果) */\n private async persistSession(\n sessionKey: string,\n session: SessionState,\n ): Promise<void> {\n if (!this._sessionStorage) return;\n\n const stored: StoredSession = {\n key: sessionKey,\n version: SESSION_VERSION,\n messages: session.messages,\n model: this.deriveModel(session.messages),\n usage: this.sumUsage(session.messages),\n createdAt: session.createdAt,\n updatedAt: new Date().toISOString(),\n };\n await this._sessionStorage.save(sessionKey, stored);\n }\n\n /**\n * 实时持久化指定会话:每轮 assistant 回复/工具结果完成后调用,\n * 让运行中的会话随时可被持久化数据观测到。ephemeral 跳过;\n * 存储失败仅告警,不影响对话循环继续。\n */\n private async persistSessionSafe(\n request: Request,\n sessionKey: string,\n ): Promise<void> {\n if (request.ephemeral || !this._sessionStorage) return;\n try {\n const session = this._sessions.get(sessionKey);\n if (!session) return; // 会话已被淘汰/删除,跳过\n await this.persistSession(sessionKey, session);\n } catch (err) {\n console.warn('[Runtime] 会话持久化失败:', (err as Error)?.message);\n }\n }\n\n /** 从消息中推导最后使用的模型 */\n private deriveModel(messages: Message[]): SessionModel | null {\n for (let i = messages.length - 1; i >= 0; i--) {\n const msg = messages[i];\n if (msg.role === 'assistant' && (msg as AssistantMessage).model) {\n return {\n provider: (msg as AssistantMessage).provider ?? this._model.provider,\n modelId: (msg as AssistantMessage).model as string,\n };\n }\n }\n return null;\n }\n\n /** 汇总所有 assistant 消息的 token 用量(含 cache) */\n private sumUsage(messages: Message[]): Usage {\n const usage = createEmptyUsage();\n for (const msg of messages) {\n if (msg.role === 'assistant') {\n const u = (msg as AssistantMessage).usage;\n if (u) {\n usage.input += u.input;\n usage.output += u.output;\n usage.total += u.total;\n usage.cacheRead = (usage.cacheRead ?? 0) + (u.cacheRead ?? 0);\n usage.cacheWrite = (usage.cacheWrite ?? 0) + (u.cacheWrite ?? 0);\n usage.reasoning = (usage.reasoning ?? 0) + (u.reasoning ?? 0);\n }\n }\n }\n return usage;\n }\n\n /** 链式执行上下文转换器(按数组顺序,上一个输出作为下一个输入) */\n private async transformMessages(\n compilation: Compilation,\n sessionKey: string,\n ): Promise<void> {\n if (this._transformers.length === 0) {\n return;\n }\n\n let resources = messagesToResources(compilation.messages);\n const context: TransformContext = {\n graph: compilation.graph,\n runtime: {\n sessionKey,\n turn: compilation.messages.length,\n contextWindow: this._model.contextWindow,\n maxTokens: this._model.maxTokens,\n contextBudgetRatio: this._contextBudgetRatio,\n },\n };\n\n for (const transformer of this._transformers) {\n try {\n resources = await transformer.transform(resources, context);\n } catch (err) {\n // 单个转换器失败时跳过,保持当前资源不变,但需可观测\n console.warn(\n `[Runtime] 转换器 \"${transformer.name}\" 失败,已跳过:`,\n (err as Error)?.message ?? err,\n );\n }\n }\n\n const messages = resourcesToMessages(resources);\n // 原地替换而非重新赋值:createCompilation 将 session.messages 按引用共享,\n // 重新赋值会导致后续 push 的 assistant/tool 消息脱离会话(持久化丢失)\n compilation.messages.splice(0, compilation.messages.length, ...messages);\n }\n\n private buildContext(messages: Message[]): Context {\n const tools = Array.from(this._globalTools.values());\n return {\n systemPrompt: this._systemPrompt,\n // compactionSummary 为内部扩展 role,provider 适配层仅支持\n // user/assistant/toolResult,发出前统一转为带标注的 user 消息\n messages: messages\n .filter(m => m.role !== 'system')\n .map(m => ((m as { role: string }).role === 'compactionSummary'\n ? this.compactionSummaryToUser(m)\n : m)),\n tools: tools.length > 0 ? tools : undefined,\n };\n }\n\n /** compactionSummary 消息 → user 消息(所有 provider 均兼容 user role) */\n private compactionSummaryToUser(msg: Message): Message {\n const text = typeof msg.content === 'string' ? msg.content : extractText(msg.content);\n return {\n role: 'user',\n content: `${COMPACTION_USER_PREFIX}\\n${text}`,\n timestamp: msg.timestamp,\n } as Message;\n }\n\n private async streamModel(\n compilation: Compilation,\n signal: AbortSignal,\n sessionKey: string,\n ): Promise<AssistantMessage> {\n // 含溢出自动恢复(modelTurnWithRecovery);非流式路径丢弃事件 chunk\n const turn = this.modelTurnWithRecovery(compilation, signal, sessionKey, false);\n let r = await turn.next();\n while (!r.done) r = await turn.next();\n return r.value ?? this.emptyAssistantMessage();\n }\n\n /** 空的 assistant 消息(流异常中断无 done/error 事件时的兜底,与旧 streamModel 行为一致) */\n private emptyAssistantMessage(): AssistantMessage {\n return {\n role: 'assistant',\n content: [],\n stopReason: 'stop',\n usage: createEmptyUsage(),\n model: this._model.id,\n provider: this._model.provider,\n timestamp: Date.now(),\n };\n }\n\n /**\n * 单回合模型调用 + 上下文溢出自动恢复闭环。\n *\n * 检测(isContextOverflow,统一传入 model.contextWindow / content / maxTokens,\n * 覆盖显式错误 / 静默溢出 / 输入截断溢出 / 输出 thinking 耗尽 / 输出打满 五模式)\n * → 丢弃失败的 assistant 消息 → 截断会话历史 → 同回合重试(不消耗回合数,\n * 上限 OVERFLOW_RECOVERY_LIMIT):\n *\n * - 显式错误 / 零产出截断溢出 / thinking 耗尽溢出 / 输出打满溢出:丢弃失败\n * 消息后重试;流式路径吞掉可恢复的 error chunk(消费者看不到瞬态错误),\n * 不可恢复时补发。\n * - 静默溢出(stop + 有完整产出):保留回复,仅压缩旧上下文供后续轮次。\n * - 恢复耗尽或单请求超窗(无可丢弃):返回最后一次错误消息,维持旧行为。\n *\n * 流式路径 yield 模型事件 chunk;非流式路径由 streamModel 消费(chunk 丢弃)。\n * 返回最终 assistant 消息;无 done/error 事件时返回 null。\n */\n private async *modelTurnWithRecovery(\n compilation: Compilation,\n signal: AbortSignal,\n sessionKey: string,\n stream: boolean,\n ): AsyncGenerator<ResultChunk, AssistantMessage | null> {\n const contextWindow = this._model.contextWindow;\n const maxTokens = this._model.maxTokens;\n let recoveries = 0;\n\n // 把 content / maxTokens 一并塞入 OverflowProbeMessage,供 isContextOverflow\n // 识别「只有 thinking 没有有效产出」和「output 打满 maxTokens」两种可恢复截断。\n const toProbe = (m: AssistantMessage) => ({\n stopReason: m.stopReason,\n errorMessage: m.errorMessage,\n usage: m.usage,\n content: m.content,\n maxTokens,\n });\n\n while (true) {\n let assistant: AssistantMessage | null = null;\n /** 被吞掉的可恢复溢出错误消息(等待恢复决策:重试则丢弃,不可恢复则补发 chunk) */\n let suppressed: AssistantMessage | null = null;\n\n for await (const event of this.streamModelEvents(compilation, signal, stream)) {\n if (event.type === 'error') {\n const msg = event.message;\n if (\n recoveries < OVERFLOW_RECOVERY_LIMIT &&\n isContextOverflow(toProbe(msg), contextWindow)\n ) {\n suppressed = msg; // 吞掉 error chunk,稍后恢复重试\n continue;\n }\n const chunk = this.streamEventToChunk(event);\n if (chunk) yield chunk;\n assistant = msg;\n } else {\n const chunk = this.streamEventToChunk(event);\n if (chunk) yield chunk;\n if (event.type === 'done') assistant = event.message;\n }\n }\n\n const final = assistant ?? suppressed;\n if (!final) return null; // 流异常中断(无 done/error 事件)\n\n if (isContextOverflow(toProbe(final), contextWindow)) {\n // failed:需要丢弃上轮并立即重试的场景\n // - stop=error 或 output=0:原有判定\n // - stop=length 但 content 里只有 thinking(零有效产出):reasoning 预算耗尽\n // 必须重跑(catalog 已给更高 maxTokens,但仍有可能碰到边界)\n // - stop=length 且 output 打满 maxTokens:回复被截断,丢弃并压缩后重试\n const output = final.usage?.output ?? 0;\n const blocks = Array.isArray(final.content) ? final.content : null;\n const hasMeaningfulText = blocks?.some(\n (b) => b.type === 'text' && 'text' in b && typeof b.text === 'string' && b.text.trim().length > 0,\n );\n const hasToolCall = blocks?.some((b) => b.type === 'toolCall');\n const thinkingOnly = blocks\n ? !hasMeaningfulText && !hasToolCall && blocks.some((b) => b.type === 'thinking')\n : false;\n const outputFull = maxTokens > 0 && output >= Math.floor(maxTokens * 0.95);\n\n const failed = final.stopReason === 'error' || output === 0 || thinkingOnly || outputFull;\n if (failed && recoveries < OVERFLOW_RECOVERY_LIMIT) {\n recoveries += 1;\n if (await this.recoverFromOverflow(compilation, recoveries, sessionKey, signal)) {\n const reason =\n thinkingOnly ? 'thinking 耗尽' : outputFull ? 'output 打满' : final.stopReason;\n console.warn(\n `[Runtime] 上下文溢出(${reason}),已压缩历史并同回合重试(${recoveries}/${OVERFLOW_RECOVERY_LIMIT})`,\n );\n await this.emitTelemetry('onRetry', {\n traceId: compilation.traceId,\n provider: this._model.provider,\n modelId: this._model.id,\n attempt: recoveries,\n errorClass: 'context-overflow',\n delayMs: 0,\n willRetry: true,\n });\n continue; // 同回合重试(不消耗回合数)\n }\n // 无可丢弃(单条请求即超窗):补发被吞的 error chunk 后原样返回\n if (suppressed) {\n yield { type: 'error', content: final.errorMessage || '模型调用出错' };\n }\n return final;\n }\n if (failed) return final; // 恢复次数耗尽,维持旧行为(错误消息落库)\n // 静默溢出(stop + 有完整产出):保留回复,仅压缩旧上下文供后续轮次\n await this.recoverFromOverflow(compilation, 1, sessionKey, signal);\n console.warn('[Runtime] 检测到静默上下文溢出(usage 超窗),已压缩历史消息');\n }\n\n return final;\n }\n }\n\n /**\n * 计算溢出恢复的截断点:按 token 预算从最旧消息开始丢弃。\n *\n * 预算随恢复次数指数收紧(contextWindow × ratio × 0.5^recovery),且每次\n * 至少丢弃可丢弃部分的一半,保证重试规模必然小于上次溢出(token 估算\n * 偏小时也成立)。最后一条消息(当前请求/最新产出)始终保留。\n * 返回被压缩段的结束下标(messages[0..split) 为被压缩段);0 = 已到\n * 最小集,单条请求即超窗,无法恢复。\n */\n private computeOverflowSplit(messages: Message[], recovery: number): number {\n const contextWindow = this._model.contextWindow;\n if (!contextWindow || contextWindow <= 0) return 0;\n const target = Math.max(\n Math.floor(contextWindow * this._contextBudgetRatio * 0.5 ** recovery),\n 1,\n );\n\n let total = 0;\n for (const m of messages) total += estimateMessageTokens(m);\n\n const droppable = messages.length - 1; // 最后一条必保\n if (droppable <= 0) return 0;\n // 至少丢弃一半可丢弃消息,保证恢复必然缩小规模(估算偏小时的兜底)\n const mustDrop = Math.max(Math.floor(droppable / 2), 1);\n\n let dropUntil = 0;\n while (dropUntil < droppable && (dropUntil < mustDrop || total > target)) {\n total -= estimateMessageTokens(messages[dropUntil]);\n dropUntil += 1;\n }\n return dropUntil;\n }\n\n /**\n * 溢出恢复:摘要优先、硬截断兜底(原地修改会话消息)。\n *\n * 开启 compaction(默认)时,被压缩段先尝试 LLM 摘要替换(compactionSummary\n * 消息),摘要失败或序列化超摘要预算(请求本身会超窗)则降级纯丢弃;\n * 关闭 compaction 时维持旧行为纯截断。截断/摘要后均经 ensureToolPairing\n * 修复保留段的工具配对。返回是否执行了恢复动作(false = 无可压缩,单条\n * 请求即超窗)。\n */\n private async recoverFromOverflow(\n compilation: Compilation,\n recovery: number,\n sessionKey: string,\n signal: AbortSignal,\n ): Promise<boolean> {\n const messages = compilation.messages;\n const split = this.computeOverflowSplit(messages, recovery);\n if (split <= 0) return false;\n\n const useCompaction =\n !!this._compaction &&\n this._compaction.enabled !== false &&\n this._compaction.onOverflow !== false;\n if (useCompaction) {\n await this.compactOrTruncate(\n messages, split, sessionKey, compilation.traceId, signal, 'overflow',\n );\n return true;\n }\n\n const kept = ensureToolPairing(messages.slice(split));\n messages.splice(0, messages.length, ...kept);\n return true;\n }\n\n /**\n * 阈值触发内置摘要压缩(runLoop 每轮模型调用前检查,低频):\n * 估算 token 超过 contextWindow × triggerRatio(默认 contextBudgetRatio)\n * 时,将历史压缩到 targetRatio(默认 0.5)——最新消息保留目标的一半,\n * 其余部分摘要替换;摘要失败降级硬截断。\n */\n private async maybeCompactByThreshold(\n compilation: Compilation,\n sessionKey: string,\n signal: AbortSignal,\n ): Promise<void> {\n // 未配置 compaction = 保持旧行为(不压缩,溢出时硬截断兜底)\n if (!this._compaction || this._compaction.enabled === false) return;\n const contextWindow = this._model.contextWindow;\n if (!contextWindow || contextWindow <= 0) return;\n\n const messages = compilation.messages;\n const triggerTokens = Math.floor(\n contextWindow * (this._compaction?.triggerRatio ?? this._contextBudgetRatio),\n );\n\n let total = 0;\n for (const m of messages) total += estimateMessageTokens(m);\n if (total <= triggerTokens) return;\n\n // 从尾部累计保留最新消息,保留量为压缩目标的一半\n const targetTokens = Math.floor(\n contextWindow * (this._compaction?.targetRatio ?? 0.5),\n );\n const keepTokens = Math.max(Math.floor(targetTokens / 2), 1);\n\n let kept = 0;\n let split = messages.length;\n for (let i = messages.length - 1; i >= 0; i--) {\n if (kept >= keepTokens) {\n split = i + 1;\n break;\n }\n kept += estimateMessageTokens(messages[i]);\n split = i;\n }\n // 无可压缩段(最新消息已占满保留预算):等待下一轮\n if (split <= 0 || split >= messages.length) return;\n\n const mode = await this.compactOrTruncate(\n messages, split, sessionKey, compilation.traceId, signal, 'threshold',\n );\n console.warn(\n `[Runtime] 上下文达阈值(约 ${total} token > ${triggerTokens}),已${mode === 'summary' ? '摘要压缩' : '截断'}历史`,\n );\n }\n\n /**\n * 手动压缩指定会话(交互命令 /compact 等):跳过阈值判断,\n * 直接将历史压缩至 targetRatio 保留量(复用 maybeCompactByThreshold\n * 的保留段计算与 compactOrTruncate 执行路径),压缩后持久化。\n */\n async compact(sessionKey?: string): Promise<'summary' | 'truncate' | null> {\n if (!this._compaction || this._compaction.enabled === false) return null;\n const key = sessionKey ?? this._sessionKey;\n const session = this.getSession(key);\n const messages = session.messages;\n if (messages.length === 0) return null;\n\n const contextWindow = this._model.contextWindow;\n if (!contextWindow || contextWindow <= 0) return null;\n\n // 与 maybeCompactByThreshold 相同的保留段计算:保留 target 的一半(最新消息)\n const targetTokens = Math.floor(\n contextWindow * (this._compaction.targetRatio ?? 0.5),\n );\n const keepTokens = Math.max(Math.floor(targetTokens / 2), 1);\n\n let kept = 0;\n let split = messages.length;\n for (let i = messages.length - 1; i >= 0; i--) {\n if (kept >= keepTokens) {\n split = i + 1;\n break;\n }\n kept += estimateMessageTokens(messages[i]);\n split = i;\n }\n // 无可压缩段(最新消息已占满保留预算)\n if (split <= 0 || split >= messages.length) return null;\n\n const mode = await this.compactOrTruncate(\n messages, split, key, `manual-${Date.now().toString(36)}`,\n new AbortController().signal, 'threshold',\n );\n try {\n await this.persistSession(key, session);\n } catch (err) {\n console.warn('[Runtime] 手动压缩后持久化失败:', (err as Error)?.message);\n }\n return mode;\n }\n\n /**\n * 执行压缩:messages[0..split) 为被压缩段,原地替换。\n *\n * 摘要成功 → 被压缩段替换为单条 compactionSummary 消息(资源层 pinned);\n * 序列化超摘要预算或摘要调用失败 → 降级纯丢弃(旧行为)。两种路径均对\n * 保留段执行 ensureToolPairing(被压缩段边界可能截断工具配对)。上报\n * onCompaction 遥测。\n */\n private async compactOrTruncate(\n messages: Message[],\n split: number,\n sessionKey: string,\n traceId: string,\n signal: AbortSignal,\n trigger: 'threshold' | 'overflow',\n ): Promise<'summary' | 'truncate'> {\n const compacted = messages.slice(0, split);\n const tokensBefore = messages.reduce((sum, m) => sum + estimateMessageTokens(m), 0);\n\n let mode: 'summary' | 'truncate' = 'truncate';\n let summaryText = '';\n\n const summaryEnabled = !!this._compaction && this._compaction.enabled !== false;\n if (summaryEnabled && compacted.length > 0) {\n const summaryBudget = Math.floor(\n this._model.contextWindow * COMPACTION_SUMMARY_BUDGET_RATIO,\n );\n const inputText = compacted\n .map(m => messageToSummaryLine(m))\n .filter(line => line.length > 0)\n .join('\\n');\n // 预算判断:被压缩段超预算时摘要请求自身必然超窗,不发 doomed 请求\n if (inputText && estimateTextTokens(inputText) <= summaryBudget) {\n const summary = await this.summarizeMessages(\n inputText, sessionKey, traceId, signal,\n );\n if (summary && summary.trim()) {\n summaryText = summary.trim();\n mode = 'summary';\n }\n }\n }\n\n let tokensAfter: number;\n if (mode === 'summary') {\n const summaryMsg = this.createCompactionSummaryMessage(summaryText);\n const kept = ensureToolPairing(messages.slice(split));\n messages.splice(0, messages.length, summaryMsg, ...kept);\n tokensAfter = estimateMessageTokens(summaryMsg)\n + kept.reduce((sum, m) => sum + estimateMessageTokens(m), 0);\n } else {\n const kept = ensureToolPairing(messages.slice(split));\n messages.splice(0, messages.length, ...kept);\n tokensAfter = kept.reduce((sum, m) => sum + estimateMessageTokens(m), 0);\n }\n\n await this.emitTelemetry('onCompaction', {\n traceId,\n sessionKey,\n mode,\n trigger,\n tokensBefore,\n tokensAfter,\n droppedMessages: split,\n summary: mode === 'summary' ? summaryText : undefined,\n } satisfies CompactionTelemetryInfo);\n return mode;\n }\n\n /**\n * 调用模型生成摘要文本。失败(模型错误/中止/空产出)返回 null,\n * 由调用方降级硬截断——摘要失败不影响主流程。\n */\n private async summarizeMessages(\n inputText: string,\n sessionKey: string,\n traceId: string,\n signal: AbortSignal,\n ): Promise<string | null> {\n const prompt = this._compaction?.prompt ?? DEFAULT_COMPACTION_PROMPT;\n const context: Context = {\n systemPrompt: prompt,\n messages: [{ role: 'user', content: inputText, timestamp: Date.now() }],\n };\n\n const startedAt = Date.now();\n let text = '';\n let usage: Usage | undefined;\n let failed = false;\n try {\n for await (const event of this._streamFn(this._model, context, { signal })) {\n if (event.type === 'text_delta') {\n text += event.delta;\n } else if (event.type === 'error') {\n failed = true;\n usage = event.message.usage;\n break;\n } else if (event.type === 'done') {\n usage = event.message.usage;\n if (event.message.stopReason === 'error') failed = true;\n // 非流式式产出兜底:done 前无 text_delta 时从消息体取文本\n if (!text) text = extractText(event.message.content);\n break;\n }\n }\n } catch {\n return null; // 摘要异常(网络/中止等):降级截断\n }\n if (failed || !text.trim()) return null;\n\n // 摘要调用也计入 onModelCall(成本对账):独立 span,stream=false\n await this.emitTelemetry('onModelCall', {\n traceId,\n spanId: newSpanId(),\n sessionKey,\n modelId: this._model.id,\n attempts: 1,\n inputTokens: usage?.input ?? estimateTextTokens(inputText),\n outputTokens: usage?.output ?? estimateTextTokens(text),\n durationMs: Date.now() - startedAt,\n stream: false,\n });\n return text;\n }\n\n /** 构造 compactionSummary 消息(内部扩展 role,发出前经 buildContext 转 user) */\n private createCompactionSummaryMessage(text: string): Message {\n return {\n role: 'compactionSummary',\n content: text,\n timestamp: Date.now(),\n } as unknown as Message;\n }\n\n /**\n * 统一模型调用埋点生成器:run()(streamModel)与 stream()(runLoopStream)两路径共用。\n * 职责:模型调用计时、spanId、attempts 累计、onRetry 转发、onModelCall 上报\n * (含 tokens / cost / errorClass / ttft)。\n */\n private async *streamModelEvents(\n compilation: Compilation,\n signal: AbortSignal,\n stream: boolean,\n ): AsyncGenerator<StreamEvent> {\n const sessionKey = this.resolveSessionKey(compilation.request);\n const modelStartedAt = Date.now();\n const spanId = newSpanId();\n let attempts = 1; // 含首次调用\n let ttftAt: number | undefined;\n let lastAssistant: AssistantMessage | undefined;\n\n const options: StreamOptions = { signal };\n if (this._thinkingLevel !== 'off' && this._model.reasoning) {\n options.reasoning = this._thinkingLevel;\n }\n // provider 内部 retry() 真正退避时回调:累计 attempts + 转发 onRetry 事件\n options.onRetryAttempt = (info) => {\n attempts += 1;\n void this.emitTelemetry('onRetry', {\n traceId: compilation.traceId,\n spanId, // P2:重试明细关联到本模型调用 span\n provider: this._model.provider,\n modelId: this._model.id,\n attempt: info.attempt,\n errorClass: classifyError(info.error),\n status: statusOfRetryError(info.error),\n delayMs: info.delayMs,\n willRetry: true,\n });\n };\n\n try {\n // beforeModelCall:插件可在此改写最终 Context(如 skills 目录注入 / 工具附加)\n const context = await this._hooks.beforeModelCall.promise(\n this.buildContext(compilation.messages),\n );\n for await (const event of this._streamFn(this._model, context, options)) {\n if (stream && event.type === 'text_delta' && ttftAt === undefined) {\n ttftAt = Date.now();\n }\n if (event.type === 'done' || event.type === 'error') {\n lastAssistant = event.message;\n }\n yield event;\n }\n } finally {\n const assistant = lastAssistant;\n const errorClass = assistant?.errorMessage\n ? (errorClassFromMessage(assistant.errorMessage) as ErrorClass | undefined) ?? 'unknown'\n : undefined;\n await this.emitTelemetry('onModelCall', {\n traceId: compilation.traceId,\n spanId,\n sessionKey,\n modelId: this._model.id,\n attempts,\n inputTokens: assistant?.usage?.input ?? 0,\n outputTokens: assistant?.usage?.output ?? 0,\n cacheRead: assistant?.usage?.cacheRead,\n cacheWrite: assistant?.usage?.cacheWrite,\n durationMs: Date.now() - modelStartedAt,\n stream,\n errorClass,\n });\n // 流式:记录首个模型调用的首 token 延迟(run 级 onRunEnd 读取)\n if (stream && ttftAt !== undefined && compilation.ttftMs === undefined) {\n compilation.ttftMs = ttftAt - modelStartedAt;\n }\n }\n }\n\n /**\n * 触发遥测回调。全可选、失败不阻断主流程。\n */\n private async emitTelemetry<E extends keyof Telemetry>(\n event: E,\n info: Parameters<NonNullable<Telemetry[E]>>[0],\n ): Promise<void> {\n const fn = this._telemetry?.[event];\n if (!fn) return;\n try {\n await Promise.resolve((fn as (arg: unknown) => unknown)(info));\n } catch (err) {\n // 遥测失败不应影响主流程\n console.warn(`[aipack] telemetry \"${String(event)}\" 上报失败:`, err);\n }\n }\n\n /** traceId 生成:优先用注入的生成器(测试可确定性) */\n private newTraceId(): string {\n return this._traceIdGenerator ? this._traceIdGenerator() : newTraceId();\n }\n\n /** 组装并上报 run 级完成事件(_run/_stream 内部统一调用) */\n private async emitRunEnd(\n request: Request,\n sessionKey: string,\n compilation: Compilation,\n result: Result,\n queuedMs: number,\n activeStartedAt: number,\n ): Promise<void> {\n const activeMs = Date.now() - activeStartedAt;\n await this.emitTelemetry('onRunEnd', {\n traceId: compilation.traceId,\n sessionKey,\n // 请求未显式指定 model 时补实际模型(模型排行按 run 级 requests 统计,缺省会落入 'unknown')\n request: request.model ? request : { ...request, model: this._model.id },\n durationMs: activeMs + queuedMs,\n activeMs,\n queuedMs,\n turnCount: compilation.turnCount ?? 0,\n result,\n success: result.success,\n errorClass: this.runErrorClass(compilation),\n tokens: {\n input: result.usage.input ?? 0,\n output: result.usage.output ?? 0,\n cacheRead: result.usage.cacheRead,\n cacheWrite: result.usage.cacheWrite,\n },\n ttftMs: compilation.ttftMs,\n });\n }\n\n /** run 级错误分类:terminate → 'terminated';否则只看最后一条 assistant 消息(与 buildResult 的 result.success 同口径) */\n private runErrorClass(compilation: Compilation): ErrorClass | undefined {\n if (compilation.terminateReason) return 'terminated';\n const messages = compilation.messages;\n for (let i = messages.length - 1; i >= 0; i--) {\n const m = messages[i];\n if (m.role === 'assistant') {\n // 最后一条 assistant 无 errorMessage → run 成功(早期轮次失败已被后续轮次恢复,不判错误)\n if (!(m as AssistantMessage).errorMessage) return undefined;\n const cls = errorClassFromMessage((m as AssistantMessage).errorMessage!);\n return (cls as ErrorClass | undefined) ?? 'unknown';\n }\n }\n return undefined;\n }\n\n private buildResult(compilation: Compilation): Result {\n const messages = compilation.messages;\n let content = '';\n let stopReason = 'completed';\n let error: string | undefined;\n const toolsUsed: string[] = [];\n const usage: Record<string, number> = {};\n\n for (const msg of messages) {\n if (msg.role === 'assistant') {\n const assistant = msg as AssistantMessage;\n content = extractText(assistant.content);\n stopReason = assistant.stopReason ?? 'completed';\n error = assistant.errorMessage;\n if (assistant.usage) {\n usage.input = (usage.input ?? 0) + assistant.usage.input;\n usage.output = (usage.output ?? 0) + assistant.usage.output;\n usage.total = (usage.total ?? 0) + assistant.usage.total;\n if (assistant.usage.cacheRead) usage.cacheRead = (usage.cacheRead ?? 0) + assistant.usage.cacheRead;\n if (assistant.usage.cacheWrite) usage.cacheWrite = (usage.cacheWrite ?? 0) + assistant.usage.cacheWrite;\n }\n }\n if (msg.role === 'toolResult') {\n const toolMsg = msg as ToolResultMessage;\n if (!toolsUsed.includes(toolMsg.toolName)) {\n toolsUsed.push(toolMsg.toolName);\n }\n }\n }\n\n // 填充资源快照(此前 Result.resources 永远 undefined)\n const resources = messagesToResources(messages);\n\n const builder = new ResultBuilder()\n .content(content)\n .toolsUsed(toolsUsed)\n .usage(usage)\n .stopReason(stopReason)\n .error(error)\n .resources(resources)\n .metadata('traceId', compilation.traceId);\n\n // beforeToolCall/afterToolCall 请求终止:覆盖 stopReason 并记录原因\n if (compilation.terminateReason) {\n builder.stopReason('terminated').metadata('terminateReason', compilation.terminateReason);\n }\n\n // 回合上限耗尽:调用方据此区分\"正常完成\"与\"被截断\"(模型仍想调用工具)\n if (compilation.maxTurnsExhausted) {\n builder.stopReason('max_turns').metadata('maxTurns', true);\n }\n\n return builder.build();\n }\n\n private streamEventToChunk(event: StreamEvent): ResultChunk | null {\n switch (event.type) {\n case 'text_delta':\n return { type: 'text', content: event.delta };\n case 'thinking_delta':\n return { type: 'thinking', content: event.delta };\n case 'error':\n // 模型调用错误(无 API Key / 鉴权失败 / 网络错误 / HTTP 4xx-5xx 等)\n // 以 error 事件流入,errorMessage 已由 stream-openai/anthropic 填好。\n return {\n type: 'error',\n content: event.message.errorMessage || '模型调用出错',\n };\n default:\n return null;\n }\n }\n\n // ─── 便捷方法 ───────────────────────────────────────────────────\n\n /** 终止指定会话的运行(默认会话;会话不存在为 no-op) */\n abort(sessionKey?: string): void {\n this._sessions.get(sessionKey ?? this._sessionKey)?.abortController?.abort();\n }\n\n /** 检查指定会话是否正在运行(默认会话;会话不存在返回 false) */\n isBusy(sessionKey?: string): boolean {\n return this._sessions.get(sessionKey ?? this._sessionKey)?.isStreaming ?? false;\n }\n\n /** 等待指定会话空闲(默认会话;基于 promise,无轮询) */\n async waitForIdle(sessionKey?: string, timeoutMs?: number): Promise<void> {\n const session = this._sessions.get(sessionKey ?? this._sessionKey);\n if (!session || !session.isStreaming) return;\n\n if (timeoutMs === undefined) {\n await new Promise<void>(resolve => {\n session.idleResolvers.push(resolve);\n });\n return;\n }\n\n // 带超时等待:超时 reject 并把自己从等待队列移除,避免 markIdle 唤醒残留 resolver\n await new Promise<void>((resolve, reject) => {\n const resolver = () => {\n clearTimeout(timer);\n resolve();\n };\n const timer = setTimeout(() => {\n const i = session.idleResolvers.indexOf(resolver);\n if (i >= 0) session.idleResolvers.splice(i, 1);\n reject(new Error(\n `[Runtime] waitForIdle 超时(${timeoutMs}ms): ${sessionKey ?? 'default'}`,\n ));\n }, timeoutMs);\n session.idleResolvers.push(resolver);\n });\n }\n\n /** 清除指定会话消息(仅内存;下次 run 会从存储恢复) */\n clearSession(sessionKey?: string): void {\n const session = this._sessions.get(sessionKey ?? this._sessionKey);\n if (!session) return;\n session.messages = [];\n session.hydrated = false;\n }\n\n /** 删除指定会话(内存 + 存储),返回是否删除成功 */\n async deleteSession(sessionKey?: string): Promise<boolean> {\n const key = sessionKey ?? this._sessionKey;\n const session = this._sessions.get(key);\n // 等待在途任务完成后再清理\n if (session) {\n await session.queue;\n this._sessions.delete(key);\n }\n if (!this._sessionStorage) return true;\n const storage = this._sessionStorage;\n if (!storage.withLock) return storage.delete(key);\n // 删除同样持存储锁,避免与另一进程的写入竞争\n return storage.withLock(key, () => storage.delete(key));\n }\n}\n\n// ─── 工厂函数 ─────────────────────────────────────────────────────\n\nexport function createRuntime(options?: RuntimeOptions): Runtime {\n return AgentRuntime.create(options);\n}\n","/**\n * core/executor.ts - 图执行引擎\n *\n * 负责 AgentGraph 的执行逻辑:从入口节点出发,\n * 根据边条件遍历图,依次执行各节点的 Runtime。\n */\n\nimport type { Runtime, RuntimeOptions, Result, Request } from '@aipack-ai/agent';\nimport { createRuntime } from '@aipack-ai/agent';\nimport { createRequest } from '@aipack-ai/agent';\nimport type {\n AgentNode,\n AgentEdge,\n SharedContext,\n MultiAgentResult,\n MultiAgentEvent,\n NodeExecutionState,\n GraphExecutionState,\n} from './types';\nimport { createSharedContext } from './context';\n\n// ─── ensureRuntime: 确保 AgentNode 拥有 Runtime 实例 ────────────\n\nconst runtimeCache = new WeakMap<AgentNode, Runtime>();\n\nexport function ensureRuntime(node: AgentNode): Runtime {\n let rt = runtimeCache.get(node);\n if (rt) return rt;\n\n if (typeof (node.runtime as Runtime).run === 'function') {\n rt = node.runtime as Runtime;\n } else {\n rt = createRuntime(node.runtime as RuntimeOptions);\n }\n runtimeCache.set(node, rt);\n return rt;\n}\n\n// ─── executeNode: 执行单个 Agent 节点 ───────────────────────────\n\nexport async function executeNode(\n node: AgentNode,\n input: string | Request,\n ctx: SharedContext,\n): Promise<Result> {\n const runtime = ensureRuntime(node);\n\n // 构建 Request\n let req: Request;\n if (typeof input === 'string') {\n req = createRequest(input, { sessionKey: `multi-agent:${node.id}` });\n } else {\n req = { ...input, sessionKey: input.sessionKey ?? `multi-agent:${node.id}` };\n }\n\n // 执行\n const result = await runtime.run(req);\n\n // 输出映射\n if (node.outputMapping) {\n node.outputMapping(result, ctx);\n }\n\n return result;\n}\n\n// ─── resolveInput: 解析下一个节点的输入 ─────────────────────────\n\nexport function resolveInput(\n edge: AgentEdge | undefined,\n prevResult: Result,\n ctx: SharedContext,\n node: AgentNode,\n originalInput: string | Request,\n): string | Request {\n // 优先级:edge.transform > node.inputMapping > 传递上一个结果\n if (edge?.transform) {\n return edge.transform(prevResult, ctx);\n }\n if (node.inputMapping) {\n return node.inputMapping(ctx);\n }\n return prevResult.content;\n}\n\n// ─── findNextEdges: 查找满足条件的出边 ─────────────────────────\n\nexport function findNextEdges(\n fromId: string,\n edges: AgentEdge[],\n result: Result,\n ctx: SharedContext,\n): AgentEdge[] {\n const outEdges = edges.filter(e => e.from === fromId);\n const matched: AgentEdge[] = [];\n\n for (const edge of outEdges) {\n // 无条件边默认匹配\n if (!edge.condition || edge.condition(result, ctx)) {\n matched.push(edge);\n }\n }\n return matched;\n}\n\n// ─── GraphExecutor: 图执行器 ─────────────────────────────────────\n\nexport class GraphExecutor {\n private nodes: Map<string, AgentNode> = new Map();\n private edges: AgentEdge[] = [];\n private entryId?: string;\n private finishCondition?: (ctx: SharedContext) => boolean;\n private abortController = new AbortController();\n private state: GraphExecutionState = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n\n addNode(node: AgentNode): this {\n this.nodes.set(node.id, node);\n this.state.nodeStates.set(node.id, 'pending');\n return this;\n }\n\n addEdge(edge: AgentEdge): this {\n this.edges.push(edge);\n return this;\n }\n\n setEntry(agentId: string): this {\n this.entryId = agentId;\n return this;\n }\n\n setFinish(condition: (ctx: SharedContext) => boolean): this {\n this.finishCondition = condition;\n return this;\n }\n\n getState(): GraphExecutionState {\n return { ...this.state };\n }\n\n abort(): void {\n this.abortController.abort();\n }\n\n /** 同步执行图 */\n async run(input: string | Request): Promise<MultiAgentResult> {\n // 前置校验:入口节点相关错误直接抛出\n if (!this.entryId) {\n throw new Error('AgentGraph: 入口节点未设置,请调用 setEntry()');\n }\n if (!this.nodes.has(this.entryId)) {\n throw new Error(`AgentGraph: 入口节点 \"${this.entryId}\" 不存在`);\n }\n\n const ctx = createSharedContext({\n meta: { traceId: `ma-${Date.now()}`, startTime: Date.now() },\n });\n const events: MultiAgentEvent[] = [];\n\n try {\n const result = await this.executeGraph(input, ctx, event => events.push(event));\n return result;\n } catch (err) {\n return {\n content: '',\n lastAgentId: this.state.currentAgentId ?? '',\n agentResults: this.state.nodeResults,\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: 'error',\n context: ctx,\n success: false,\n error: err instanceof Error ? err.message : String(err),\n };\n }\n }\n\n /** 流式执行图 */\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n // 前置校验\n if (!this.entryId) {\n throw new Error('AgentGraph: 入口节点未设置,请调用 setEntry()');\n }\n if (!this.nodes.has(this.entryId)) {\n throw new Error(`AgentGraph: 入口节点 \"${this.entryId}\" 不存在`);\n }\n\n const ctx = createSharedContext({\n meta: { traceId: `ma-${Date.now()}`, startTime: Date.now() },\n });\n\n const eventQueue: MultiAgentEvent[] = [];\n let resolveEvent: (() => void) | null = null;\n let done = false;\n\n const emit = (event: MultiAgentEvent) => {\n eventQueue.push(event);\n resolveEvent?.();\n };\n\n const graphPromise = this.executeGraph(input, ctx, emit).then(\n (result) => {\n emit({ type: 'graph_done', result });\n },\n (err) => {\n emit({ type: 'graph_error', error: err instanceof Error ? err.message : String(err) });\n },\n ).finally(() => {\n done = true;\n resolveEvent?.();\n });\n\n // 产出事件\n while (!done || eventQueue.length > 0) {\n if (eventQueue.length > 0) {\n yield eventQueue.shift()!;\n } else {\n await new Promise<void>(resolve => {\n resolveEvent = resolve;\n });\n }\n }\n\n await graphPromise;\n }\n\n /** 核心执行逻辑 */\n private async executeGraph(\n input: string | Request,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n ): Promise<MultiAgentResult> {\n const entryNode = this.nodes.get(this.entryId!)!;\n\n let currentId = this.entryId!;\n let currentInput: string | Request = input;\n let lastResult: Result | undefined;\n let lastAgentId = currentId;\n let stepsCompleted = 0;\n const totalUsage: Record<string, number> = {};\n\n // 执行入口节点\n this.state.currentAgentId = currentId;\n this.state.nodeStates.set(currentId, 'running');\n emit({ type: 'agent_start', agentId: currentId, agentName: entryNode.name });\n\n try {\n lastResult = await executeNode(entryNode, currentInput, ctx);\n this.state.nodeStates.set(currentId, 'completed');\n this.state.nodeResults.set(currentId, lastResult);\n this.mergeUsage(totalUsage, lastResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: currentId, agentName: entryNode.name, result: lastResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(currentId, 'failed');\n emit({ type: 'agent_error', agentId: currentId, agentName: entryNode.name, error: errorMsg });\n throw err;\n }\n\n lastAgentId = currentId;\n\n // 检查终止条件\n if (this.finishCondition?.(ctx)) {\n return this.buildResult(lastResult!, lastAgentId, ctx, totalUsage, stepsCompleted, 'finish_condition');\n }\n\n // 沿边遍历\n const visited = new Set<string>();\n // 允许环形(如review→coder),用计数防止无限循环\n const visitCount = new Map<string, number>();\n const MAX_VISITS_PER_NODE = 10;\n\n while (lastResult) {\n const nextEdges = findNextEdges(currentId, this.edges, lastResult, ctx);\n\n if (nextEdges.length === 0) {\n // 无出边,图执行完毕\n break;\n }\n\n // 取第一条匹配边(P0 不支持并行分支,按顺序取第一条)\n const edge = nextEdges[0];\n const nextNode = this.nodes.get(edge.to);\n\n if (!nextNode) {\n throw new Error(`AgentGraph: 目标节点 \"${edge.to}\" 不存在`);\n }\n\n // 防止无限循环\n const count = (visitCount.get(edge.to) ?? 0) + 1;\n if (count > MAX_VISITS_PER_NODE) {\n break;\n }\n visitCount.set(edge.to, count);\n\n // 解析输入\n currentInput = resolveInput(edge, lastResult, ctx, nextNode, input);\n\n // 执行下一节点\n currentId = edge.to;\n this.state.currentAgentId = currentId;\n this.state.nodeStates.set(currentId, 'running');\n emit({ type: 'edge_traversed', from: edge.from, to: edge.to });\n emit({ type: 'agent_start', agentId: currentId, agentName: nextNode.name });\n\n try {\n lastResult = await executeNode(nextNode, currentInput, ctx);\n this.state.nodeStates.set(currentId, 'completed');\n this.state.nodeResults.set(currentId, lastResult);\n this.mergeUsage(totalUsage, lastResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: currentId, agentName: nextNode.name, result: lastResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(currentId, 'failed');\n emit({ type: 'agent_error', agentId: currentId, agentName: nextNode.name, error: errorMsg });\n throw err;\n }\n\n lastAgentId = currentId;\n\n // 检查终止条件\n if (this.finishCondition?.(ctx)) {\n return this.buildResult(lastResult, lastAgentId, ctx, totalUsage, stepsCompleted, 'finish_condition');\n }\n }\n\n return this.buildResult(lastResult!, lastAgentId, ctx, totalUsage, stepsCompleted, 'completed');\n }\n\n private buildResult(\n lastResult: Result,\n lastAgentId: string,\n ctx: SharedContext,\n totalUsage: Record<string, number>,\n stepsCompleted: number,\n stopReason: string,\n ): MultiAgentResult {\n this.state.finished = true;\n return {\n content: lastResult.content,\n lastAgentId,\n agentResults: new Map(this.state.nodeResults),\n totalUsage,\n stepsCompleted,\n stopReason,\n context: ctx,\n success: lastResult.success,\n error: lastResult.error,\n };\n }\n\n private mergeUsage(total: Record<string, number>, usage: Record<string, number>): void {\n for (const [key, value] of Object.entries(usage)) {\n total[key] = (total[key] ?? 0) + value;\n }\n }\n}\n","/**\n * core/graph.ts - AgentGraph 实现\n *\n * 基于声明式 API(addNode/addEdge/setEntry/setFinish)构建图,\n * 委托 GraphExecutor 执行。\n */\n\nimport type { Request } from '@aipack-ai/agent';\nimport type { AgentNode, AgentEdge, AgentGraph, SharedContext, EventListener, MultiAgentResult, MultiAgentEvent, GraphExecutionState } from './types';\nimport { GraphExecutor } from './executor';\n\n// ─── AgentGraphImpl ──────────────────────────────────────────────\n\nclass AgentGraphImpl implements AgentGraph {\n private executor = new GraphExecutor();\n private eventListeners = new Map<string, Set<EventListener>>();\n\n addNode(node: AgentNode): this {\n this.executor.addNode(node);\n return this;\n }\n\n addEdge(edge: AgentEdge): this {\n this.executor.addEdge(edge);\n return this;\n }\n\n setEntry(agentId: string): this {\n this.executor.setEntry(agentId);\n return this;\n }\n\n setFinish(condition: (ctx: SharedContext) => boolean): this {\n this.executor.setFinish(condition);\n return this;\n }\n\n async run(input: string | Request): Promise<MultiAgentResult> {\n return this.executor.run(input);\n }\n\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n yield* this.executor.stream(input);\n }\n\n getState(): GraphExecutionState {\n return this.executor.getState();\n }\n\n abort(): void {\n this.executor.abort();\n }\n\n on(event: string, listener: EventListener): this {\n let set = this.eventListeners.get(event);\n if (!set) {\n set = new Set();\n this.eventListeners.set(event, set);\n }\n set.add(listener);\n return this;\n }\n}\n\n// ─── createAgentGraph 工厂函数 ───────────────────────────────────\n\n/** 创建空的 AgentGraph,通过链式调用定义图结构 */\nexport function createAgentGraph(): AgentGraph {\n return new AgentGraphImpl();\n}\n","/**\n * patterns/pipeline.ts - Pipeline 顺序链模式\n *\n * 将多个 Agent 按顺序串联:A → B → C → ...\n * 前一个 Agent 的输出作为后一个 Agent 的输入。\n */\n\nimport type { AgentNode, AgentGraph, PipelineOpts } from '../core/types';\nimport { createAgentGraph } from '../core/graph';\n\n/**\n * 创建 Pipeline 顺序链\n *\n * @param agents - 按顺序排列的 Agent 节点列表\n * @param opts - Pipeline 配置选项\n * @returns AgentGraph 实例\n */\nexport function createPipeline(\n agents: AgentNode[],\n opts?: PipelineOpts,\n): AgentGraph {\n if (agents.length === 0) {\n throw new Error('Pipeline: 至少需要一个 Agent 节点');\n }\n\n const graph = createAgentGraph();\n\n // 添加所有节点\n for (const agent of agents) {\n graph.addNode(agent);\n }\n\n // 设置入口\n graph.setEntry(agents[0].id);\n\n // 添加顺序边\n for (let i = 0; i < agents.length - 1; i++) {\n const from = agents[i];\n const to = agents[i + 1];\n\n graph.addEdge({\n from: from.id,\n to: to.id,\n // 边上的转换:将前一个Agent的输出传递给下一个Agent\n transform: opts?.outputTransform\n ? (result, ctx) => opts.outputTransform!(result, ctx)\n : undefined,\n });\n }\n\n return graph;\n}\n","/**\n * patterns/router.ts - Router 条件路由模式\n *\n * 路由器 Agent 根据输入选择目标 Agent 执行。\n * 结构:Router → (条件匹配) → Target Agent\n */\n\nimport type { AgentNode, AgentGraph, RouterOpts } from '../core/types';\nimport { createAgentGraph } from '../core/graph';\n\n/**\n * 创建 Router 条件路由\n *\n * @param router - 路由器 Agent(负责意图识别)\n * @param targets - 目标 Agent 列表\n * @param opts - Router 配置选项(必须提供 resolve 函数)\n * @returns AgentGraph 实例\n */\nexport function createRouter(\n router: AgentNode,\n targets: AgentNode[],\n opts: RouterOpts,\n): AgentGraph {\n if (targets.length === 0) {\n throw new Error('Router: 至少需要一个目标 Agent');\n }\n\n const graph = createAgentGraph();\n\n // 添加路由器节点\n graph.addNode(router);\n\n // 添加目标节点\n for (const target of targets) {\n graph.addNode(target);\n }\n\n // 设置入口为路由器\n graph.setEntry(router.id);\n\n // 构建目标 ID 集合,用于校验\n const targetIds = new Set(targets.map(t => t.id));\n\n // 路由器到每个目标的条件边\n for (const target of targets) {\n graph.addEdge({\n from: router.id,\n to: target.id,\n // 条件:从路由器结果中解析目标ID,匹配当前目标\n condition: (routerResult, _ctx) => {\n const resolvedId = opts.resolve(routerResult);\n return resolvedId === target.id;\n },\n // 转换:决定传给目标Agent的输入\n transform: (_routerResult, _ctx) => {\n // 默认传递原始输入(passOriginalInput=true)\n // 原始输入在 graph run 时传入,这里通过 blackboard 获取\n const originalInput = _ctx.blackboard.get('__original_input__');\n if (opts.passOriginalInput === false) {\n // 传递路由器的输出\n return _routerResult.content;\n }\n return (originalInput as string) ?? _routerResult.content;\n },\n });\n }\n\n // 默认路由边(如果指定了 defaultTarget)\n if (opts.defaultTarget && targetIds.has(opts.defaultTarget)) {\n // 默认边已在上面添加,这里无需额外处理\n // resolve 函数应返回 defaultTarget 作为兜底\n }\n\n return graph;\n}\n","/**\n * core/supervisor-executor.ts - Supervisor 执行器\n *\n * 实现 Supervisor 层级委派模式:\n * 1. Supervisor Agent 先执行,拆解任务并写入 SharedContext\n * 2. Worker Agents 根据调度策略执行(parallel / sequential / auto)\n * 3. 汇总所有 Worker 结果\n */\n\nimport type { Result, Request } from '@aipack-ai/agent';\nimport type {\n AgentNode,\n SharedContext,\n MultiAgentResult,\n MultiAgentEvent,\n SupervisorOpts,\n ScheduleMode,\n NodeExecutionState,\n GraphExecutionState,\n} from './types';\nimport { createSharedContext } from './context';\nimport { executeNode } from './executor';\n\n// ─── SupervisorExecutor ──────────────────────────────────────────\n\nexport class SupervisorExecutor {\n private supervisorNode: AgentNode;\n private workerNodes: AgentNode[];\n private opts: Required<SupervisorOpts>;\n private state: GraphExecutionState = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n\n constructor(supervisor: AgentNode, workers: AgentNode[], opts?: SupervisorOpts) {\n this.supervisorNode = supervisor;\n this.workerNodes = workers;\n this.opts = {\n schedule: opts?.schedule ?? 'parallel',\n concurrency: opts?.concurrency ?? Infinity,\n passOriginalInput: opts?.passOriginalInput ?? true,\n };\n\n // 初始化状态\n this.state.nodeStates.set(supervisor.id, 'pending');\n for (const w of workers) {\n this.state.nodeStates.set(w.id, 'pending');\n }\n }\n\n getState(): GraphExecutionState {\n return { ...this.state };\n }\n\n /** 执行 Supervisor 模式 */\n async run(input: string | Request): Promise<MultiAgentResult> {\n const ctx = createSharedContext({\n meta: { traceId: `sv-${Date.now()}`, startTime: Date.now() },\n });\n\n // 存储原始输入到 blackboard\n if (this.opts.passOriginalInput) {\n const inputText = typeof input === 'string' ? input : input.message;\n ctx.blackboard.set('__original_input__', inputText);\n }\n\n try {\n return await this.executeSupervisor(input, ctx, () => {});\n } catch (err) {\n return this.buildErrorResult(ctx, err);\n }\n }\n\n /** 流式执行 Supervisor 模式 */\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n const ctx = createSharedContext({\n meta: { traceId: `sv-${Date.now()}`, startTime: Date.now() },\n });\n\n if (this.opts.passOriginalInput) {\n const inputText = typeof input === 'string' ? input : input.message;\n ctx.blackboard.set('__original_input__', inputText);\n }\n\n const eventQueue: MultiAgentEvent[] = [];\n let resolveEvent: (() => void) | null = null;\n let done = false;\n\n const emit = (event: MultiAgentEvent) => {\n eventQueue.push(event);\n resolveEvent?.();\n };\n\n const graphPromise = this.executeSupervisor(input, ctx, emit).then(\n (result) => { emit({ type: 'graph_done', result }); },\n (err) => { emit({ type: 'graph_error', error: err instanceof Error ? err.message : String(err) }); },\n ).finally(() => {\n done = true;\n resolveEvent?.();\n });\n\n while (!done || eventQueue.length > 0) {\n if (eventQueue.length > 0) {\n yield eventQueue.shift()!;\n } else {\n await new Promise<void>(resolve => { resolveEvent = resolve; });\n }\n }\n\n await graphPromise;\n }\n\n /** 核心执行逻辑 */\n private async executeSupervisor(\n input: string | Request,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n ): Promise<MultiAgentResult> {\n let stepsCompleted = 0;\n const totalUsage: Record<string, number> = {};\n\n // ── Step 1: 执行 Supervisor ────────────────────────────────\n this.state.currentAgentId = this.supervisorNode.id;\n this.state.nodeStates.set(this.supervisorNode.id, 'running');\n emit({ type: 'agent_start', agentId: this.supervisorNode.id, agentName: this.supervisorNode.name });\n\n let supervisorResult: Result;\n try {\n supervisorResult = await executeNode(this.supervisorNode, input, ctx);\n this.state.nodeStates.set(this.supervisorNode.id, 'completed');\n this.state.nodeResults.set(this.supervisorNode.id, supervisorResult);\n this.mergeUsage(totalUsage, supervisorResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: this.supervisorNode.id, agentName: this.supervisorNode.name, result: supervisorResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(this.supervisorNode.id, 'failed');\n emit({ type: 'agent_error', agentId: this.supervisorNode.id, agentName: this.supervisorNode.name, error: errorMsg });\n throw err;\n }\n\n // ── Step 2: 调度 Worker 执行 ──────────────────────────────\n const schedule = this.opts.schedule;\n let workerResults: Map<string, Result>;\n\n if (schedule === 'parallel') {\n workerResults = await this.executeWorkersParallel(ctx, emit, totalUsage);\n } else if (schedule === 'sequential') {\n workerResults = await this.executeWorkersSequential(ctx, emit, totalUsage);\n } else {\n // auto: 分析依赖,分层执行\n workerResults = await this.executeWorkersAuto(ctx, emit, totalUsage);\n }\n\n stepsCompleted += workerResults.size;\n this.state.stepsCompleted = stepsCompleted;\n\n // ── Step 3: 汇总结果 ──────────────────────────────────────\n // 找到最后一个完成的 worker 的结果作为最终结果\n const lastWorkerId = this.workerNodes[this.workerNodes.length - 1].id;\n const finalResult = workerResults.get(lastWorkerId) ?? supervisorResult;\n\n this.state.finished = true;\n return {\n content: finalResult.content,\n lastAgentId: lastWorkerId,\n agentResults: new Map(this.state.nodeResults),\n totalUsage,\n stepsCompleted,\n stopReason: 'completed',\n context: ctx,\n success: true,\n };\n }\n\n /** 并行执行所有 Worker */\n private async executeWorkersParallel(\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Map<string, Result>> {\n const results = new Map<string, Result>();\n const workers = this.workerNodes;\n const concurrency = this.opts.concurrency;\n\n emit({ type: 'parallel_start', agentIds: workers.map(w => w.id) });\n\n if (concurrency >= workers.length) {\n // 无限制并发,全部并行\n const promises = workers.map(async (worker) => {\n return this.executeWorker(worker, ctx, emit, totalUsage);\n });\n const settled = await Promise.allSettled(promises);\n for (let i = 0; i < settled.length; i++) {\n const s = settled[i];\n if (s.status === 'fulfilled') {\n results.set(workers[i].id, s.value);\n }\n // rejected 的已经在 executeWorker 中处理了\n }\n } else {\n // 限制并发数\n let index = 0;\n const executing = new Set<Promise<Result>>();\n\n const enqueue = (): Promise<Result> | null => {\n if (index >= workers.length) return null;\n const worker = workers[index++];\n const p = this.executeWorker(worker, ctx, emit, totalUsage).then(r => {\n results.set(worker.id, r);\n executing.delete(p);\n return r;\n });\n executing.add(p);\n return p;\n };\n\n // 初始填充\n for (let i = 0; i < concurrency && index < workers.length; i++) {\n enqueue();\n }\n\n while (executing.size > 0) {\n await Promise.race(executing);\n enqueue();\n }\n }\n\n emit({ type: 'parallel_done', results });\n return results;\n }\n\n /** 顺序执行所有 Worker */\n private async executeWorkersSequential(\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Map<string, Result>> {\n const results = new Map<string, Result>();\n\n for (const worker of this.workerNodes) {\n const result = await this.executeWorker(worker, ctx, emit, totalUsage);\n results.set(worker.id, result);\n }\n\n return results;\n }\n\n /** 自动调度:根据 inputMapping 依赖分层执行 */\n private async executeWorkersAuto(\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Map<string, Result>> {\n const results = new Map<string, Result>();\n\n // 简化 auto 策略:\n // - 没有 inputMapping 的 worker(只依赖 supervisor 输出)→ 第一批并行\n // - 有 inputMapping 的 worker(可能依赖其他 worker 结果)→ 第二批顺序执行\n const noInputMapping = this.workerNodes.filter(w => !w.inputMapping);\n const withInputMapping = this.workerNodes.filter(w => !!w.inputMapping);\n\n // 第一批:并行执行无 inputMapping 的 worker\n if (noInputMapping.length > 0) {\n emit({ type: 'parallel_start', agentIds: noInputMapping.map(w => w.id) });\n const batchResults = await Promise.all(\n noInputMapping.map(w => this.executeWorker(w, ctx, emit, totalUsage)),\n );\n for (let i = 0; i < noInputMapping.length; i++) {\n results.set(noInputMapping[i].id, batchResults[i]);\n }\n emit({ type: 'parallel_done', results: new Map(results) });\n }\n\n // 第二批:顺序执行有 inputMapping 的 worker\n for (const worker of withInputMapping) {\n const result = await this.executeWorker(worker, ctx, emit, totalUsage);\n results.set(worker.id, result);\n }\n\n return results;\n }\n\n /** 执行单个 Worker */\n private async executeWorker(\n worker: AgentNode,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Result> {\n this.state.currentAgentId = worker.id;\n this.state.nodeStates.set(worker.id, 'running');\n emit({ type: 'agent_start', agentId: worker.id, agentName: worker.name });\n\n try {\n // 解析输入:优先 inputMapping,否则用 supervisor 的输出\n let workerInput: string | Request;\n if (worker.inputMapping) {\n workerInput = worker.inputMapping(ctx);\n } else {\n // 从 blackboard 获取 supervisor 分配给该 worker 的任务\n const tasks = ctx.blackboard.get('tasks') as Array<{ assignee: string; task: string }> | undefined;\n const myTask = tasks?.find(t => t.assignee === worker.id);\n workerInput = myTask ? myTask.task : (ctx.blackboard.get('__original_input__') as string ?? '');\n }\n\n const result = await executeNode(worker, workerInput, ctx);\n this.state.nodeStates.set(worker.id, 'completed');\n this.state.nodeResults.set(worker.id, result);\n this.mergeUsage(totalUsage, result.usage);\n\n // 自动将 worker 结果写入 blackboard(方便后续 worker 读取)\n ctx.blackboard.set(`${worker.id}_result`, result.content);\n\n emit({ type: 'agent_result', agentId: worker.id, agentName: worker.name, result });\n return result;\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(worker.id, 'failed');\n emit({ type: 'agent_error', agentId: worker.id, agentName: worker.name, error: errorMsg });\n throw err;\n }\n }\n\n private buildErrorResult(ctx: SharedContext, err: unknown): MultiAgentResult {\n this.state.finished = true;\n return {\n content: '',\n lastAgentId: this.supervisorNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: 'error',\n context: ctx,\n success: false,\n error: err instanceof Error ? err.message : String(err),\n };\n }\n\n private mergeUsage(total: Record<string, number>, usage: Record<string, number>): void {\n for (const [key, value] of Object.entries(usage)) {\n total[key] = (total[key] ?? 0) + value;\n }\n }\n}\n","/**\n * patterns/supervisor.ts - Supervisor 层级委派模式\n *\n * Supervisor Agent 拆解任务分配给 Worker Agents,\n * 根据调度策略执行(parallel / sequential / auto)。\n */\n\nimport type { AgentNode, AgentGraph, SupervisorOpts, EventListener, MultiAgentResult, MultiAgentEvent } from '../core/types';\nimport { SupervisorExecutor } from '../core/supervisor-executor';\nimport type { Request } from '@aipack-ai/agent';\n\n// ─── SupervisorGraphImpl ─────────────────────────────────────────\n\nclass SupervisorGraphImpl implements AgentGraph {\n private executor: SupervisorExecutor;\n private eventListeners = new Map<string, Set<EventListener>>();\n\n constructor(supervisor: AgentNode, workers: AgentNode[], opts?: SupervisorOpts) {\n this.executor = new SupervisorExecutor(supervisor, workers, opts);\n }\n\n // AgentGraph 接口方法(Supervisor 不使用 addNode/addEdge/setEntry/setFinish)\n addNode(): this {\n throw new Error('Supervisor 模式不支持手动 addNode,请在 createSupervisor() 中配置');\n }\n addEdge(): this {\n throw new Error('Supervisor 模式不支持手动 addEdge,调度由 Supervisor 自动管理');\n }\n setEntry(): this {\n throw new Error('Supervisor 模式不支持 setEntry,入口固定为 Supervisor');\n }\n setFinish(): this {\n throw new Error('Supervisor 模式不支持 setFinish,终止由 Supervisor 判定');\n }\n\n async run(input: string | Request): Promise<MultiAgentResult> {\n return this.executor.run(input);\n }\n\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n yield* this.executor.stream(input);\n }\n\n getState() {\n return this.executor.getState();\n }\n\n abort(): void {\n // SupervisorExecutor 当前未实现 abort,预留接口\n }\n\n on(event: string, listener: EventListener): this {\n let set = this.eventListeners.get(event);\n if (!set) {\n set = new Set();\n this.eventListeners.set(event, set);\n }\n set.add(listener);\n return this;\n }\n}\n\n// ─── createSupervisor 工厂函数 ───────────────────────────────────\n\n/**\n * 创建 Supervisor 层级委派模式\n *\n * @param supervisor - Supervisor Agent(负责拆解任务并分配)\n * @param workers - Worker Agent 列表(负责执行具体任务)\n * @param opts - Supervisor 配置选项\n * @returns AgentGraph 实例\n */\nexport function createSupervisor(\n supervisor: AgentNode,\n workers: AgentNode[],\n opts?: SupervisorOpts,\n): AgentGraph {\n if (workers.length === 0) {\n throw new Error('Supervisor: 至少需要一个 Worker Agent');\n }\n\n return new SupervisorGraphImpl(supervisor, workers, opts);\n}\n","/**\n * core/debate-executor.ts - Debate 对抗评审执行器\n *\n * 实现 proposer ↔ reviewer 循环辩论模式:\n * 1. Proposer 生成初始结果\n * 2. Reviewer 审查并给出反馈\n * 3. 如果未收敛,将反馈转为 proposer 输入,回到步骤 1\n * 4. 收敛或达最大轮次时结束\n */\n\nimport type { Result, Request } from '@aipack-ai/agent';\nimport type {\n AgentNode,\n SharedContext,\n MultiAgentResult,\n MultiAgentEvent,\n DebateOpts,\n GraphExecutionState,\n} from './types';\nimport { createSharedContext } from './context';\nimport { executeNode } from './executor';\n\n// ─── DebateExecutor ──────────────────────────────────────────────\n\nexport class DebateExecutor {\n private proposerNode: AgentNode;\n private reviewerNode: AgentNode;\n private maxRounds: number;\n private convergeWhen: (reviewerResult: Result) => boolean;\n private feedbackTransform: (reviewerResult: Result, proposerResult: Result) => string;\n private state: GraphExecutionState = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n\n constructor(proposer: AgentNode, reviewer: AgentNode, opts: DebateOpts) {\n this.proposerNode = proposer;\n this.reviewerNode = reviewer;\n this.maxRounds = opts.maxRounds ?? 3;\n this.convergeWhen = opts.convergeWhen;\n this.feedbackTransform = opts.feedbackTransform ?? ((reviewerResult, proposerResult) => {\n return `以下是审查意见:\\n${reviewerResult.content}\\n\\n请修复以上问题并重新提交。原始输出:\\n${proposerResult.content}`;\n });\n\n this.state.nodeStates.set(proposer.id, 'pending');\n this.state.nodeStates.set(reviewer.id, 'pending');\n }\n\n getState(): GraphExecutionState {\n return { ...this.state };\n }\n\n /** 执行 Debate */\n async run(input: string | Request): Promise<MultiAgentResult> {\n const ctx = createSharedContext({\n meta: { traceId: `debate-${Date.now()}`, startTime: Date.now() },\n });\n\n try {\n return await this.executeDebate(input, ctx, () => {});\n } catch (err) {\n return this.buildErrorResult(ctx, err);\n }\n }\n\n /** 流式执行 Debate */\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n const ctx = createSharedContext({\n meta: { traceId: `debate-${Date.now()}`, startTime: Date.now() },\n });\n\n const eventQueue: MultiAgentEvent[] = [];\n let resolveEvent: (() => void) | null = null;\n let done = false;\n\n const emit = (event: MultiAgentEvent) => {\n eventQueue.push(event);\n resolveEvent?.();\n };\n\n const graphPromise = this.executeDebate(input, ctx, emit).then(\n (result) => { emit({ type: 'graph_done', result }); },\n (err) => { emit({ type: 'graph_error', error: err instanceof Error ? err.message : String(err) }); },\n ).finally(() => {\n done = true;\n resolveEvent?.();\n });\n\n while (!done || eventQueue.length > 0) {\n if (eventQueue.length > 0) {\n yield eventQueue.shift()!;\n } else {\n await new Promise<void>(resolve => { resolveEvent = resolve; });\n }\n }\n\n await graphPromise;\n }\n\n /** 核心执行逻辑 */\n private async executeDebate(\n input: string | Request,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n ): Promise<MultiAgentResult> {\n let stepsCompleted = 0;\n const totalUsage: Record<string, number> = {};\n let lastProposerResult!: Result;\n let lastReviewerResult!: Result;\n let convergedRound = 0;\n let convergeReason = '';\n let currentInput: string | Request = input;\n\n for (let round = 1; round <= this.maxRounds; round++) {\n emit({ type: 'round_start', round });\n\n // ── 执行 Proposer ──────────────────────────────────────\n this.state.currentAgentId = this.proposerNode.id;\n this.state.nodeStates.set(this.proposerNode.id, 'running');\n emit({ type: 'agent_start', agentId: this.proposerNode.id, agentName: this.proposerNode.name });\n\n try {\n lastProposerResult = await executeNode(this.proposerNode, currentInput, ctx);\n this.state.nodeStates.set(this.proposerNode.id, 'completed');\n this.state.nodeResults.set(`${this.proposerNode.id}_r${round}`, lastProposerResult);\n this.mergeUsage(totalUsage, lastProposerResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: this.proposerNode.id, agentName: this.proposerNode.name, result: lastProposerResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(this.proposerNode.id, 'failed');\n emit({ type: 'agent_error', agentId: this.proposerNode.id, agentName: this.proposerNode.name, error: errorMsg });\n throw err;\n }\n\n // ── 执行 Reviewer ──────────────────────────────────────\n this.state.currentAgentId = this.reviewerNode.id;\n this.state.nodeStates.set(this.reviewerNode.id, 'running');\n emit({ type: 'agent_start', agentId: this.reviewerNode.id, agentName: this.reviewerNode.name });\n\n try {\n lastReviewerResult = await executeNode(this.reviewerNode, lastProposerResult.content, ctx);\n this.state.nodeStates.set(this.reviewerNode.id, 'completed');\n this.state.nodeResults.set(`${this.reviewerNode.id}_r${round}`, lastReviewerResult);\n this.mergeUsage(totalUsage, lastReviewerResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: this.reviewerNode.id, agentName: this.reviewerNode.name, result: lastReviewerResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(this.reviewerNode.id, 'failed');\n emit({ type: 'agent_error', agentId: this.reviewerNode.id, agentName: this.reviewerNode.name, error: errorMsg });\n throw err;\n }\n\n // ── 检查收敛 ────────────────────────────────────────────\n if (this.convergeWhen(lastReviewerResult)) {\n convergedRound = round;\n convergeReason = `收敛于第 ${round} 轮:reviewer 输出满足收敛条件`;\n emit({ type: 'converged', round, reason: convergeReason });\n break;\n }\n\n // ── 准备下一轮输入 ──────────────────────────────────────\n currentInput = this.feedbackTransform(lastReviewerResult, lastProposerResult);\n }\n\n // 最终结果:收敛时取 proposer 最后一轮输出,未收敛时也取 proposer 输出\n const finalResult = lastProposerResult;\n const stopReason = convergedRound > 0\n ? `converged_at_round_${convergedRound}`\n : `max_rounds_reached`;\n\n this.state.finished = true;\n return {\n content: finalResult.content,\n lastAgentId: this.reviewerNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage,\n stepsCompleted,\n stopReason,\n context: ctx,\n success: true,\n };\n }\n\n private buildErrorResult(ctx: SharedContext, err: unknown): MultiAgentResult {\n this.state.finished = true;\n return {\n content: '',\n lastAgentId: this.proposerNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: 'error',\n context: ctx,\n success: false,\n error: err instanceof Error ? err.message : String(err),\n };\n }\n\n private mergeUsage(total: Record<string, number>, usage: Record<string, number>): void {\n for (const [key, value] of Object.entries(usage)) {\n total[key] = (total[key] ?? 0) + value;\n }\n }\n}\n","/**\n * patterns/debate.ts - Debate 对抗评审模式\n *\n * Proposer 和 Reviewer 循环辩论,直到收敛或达最大轮次。\n */\n\nimport type { AgentNode, AgentGraph, DebateOpts, EventListener, MultiAgentResult, MultiAgentEvent } from '../core/types';\nimport { DebateExecutor } from '../core/debate-executor';\nimport type { Request } from '@aipack-ai/agent';\n\n// ─── DebateGraphImpl ─────────────────────────────────────────────\n\nclass DebateGraphImpl implements AgentGraph {\n private executor: DebateExecutor;\n private eventListeners = new Map<string, Set<EventListener>>();\n\n constructor(proposer: AgentNode, reviewer: AgentNode, opts: DebateOpts) {\n this.executor = new DebateExecutor(proposer, reviewer, opts);\n }\n\n addNode(): this { throw new Error('Debate 模式不支持手动 addNode'); }\n addEdge(): this { throw new Error('Debate 模式不支持手动 addEdge'); }\n setEntry(): this { throw new Error('Debate 模式不支持 setEntry'); }\n setFinish(): this { throw new Error('Debate 模式不支持 setFinish'); }\n\n async run(input: string | Request): Promise<MultiAgentResult> {\n return this.executor.run(input);\n }\n\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n yield* this.executor.stream(input);\n }\n\n getState() { return this.executor.getState(); }\n abort(): void {}\n\n on(event: string, listener: EventListener): this {\n let set = this.eventListeners.get(event);\n if (!set) { set = new Set(); this.eventListeners.set(event, set); }\n set.add(listener);\n return this;\n }\n}\n\n// ─── createDebate 工厂函数 ───────────────────────────────────────\n\n/**\n * 创建 Debate 对抗评审模式\n *\n * @param proposer - 生成/修复方 Agent\n * @param reviewer - 审查方 Agent\n * @param opts - Debate 配置选项(必须提供 convergeWhen)\n * @returns AgentGraph 实例\n */\nexport function createDebate(\n proposer: AgentNode,\n reviewer: AgentNode,\n opts: DebateOpts,\n): AgentGraph {\n return new DebateGraphImpl(proposer, reviewer, opts);\n}\n","/**\n * core/map-reduce-executor.ts - MapReduce 并行聚合执行器\n *\n * 实现 MapReduce 模式:\n * 1. split:将输入拆分为多个子任务\n * 2. map:用 mapper Agent 并行处理每个子任务\n * 3. reduce:用 reducer Agent 汇总所有 mapper 结果\n */\n\nimport type { Result, Request } from '@aipack-ai/agent';\nimport type {\n AgentNode,\n SharedContext,\n MultiAgentResult,\n MultiAgentEvent,\n MapReduceOpts,\n GraphExecutionState,\n} from './types';\nimport { createSharedContext } from './context';\nimport { executeNode } from './executor';\n\n// ─── MapReduceExecutor ───────────────────────────────────────────\n\nexport class MapReduceExecutor {\n private mapperNode: AgentNode;\n private reducerNode: AgentNode;\n private split: (input: string) => string[];\n private concurrency: number;\n private reduceInputFormat: (mapperResults: Map<number, Result>) => string;\n private state: GraphExecutionState = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n\n constructor(mapper: AgentNode, reducer: AgentNode, opts: MapReduceOpts) {\n this.mapperNode = mapper;\n this.reducerNode = reducer;\n this.split = opts.split;\n this.concurrency = opts.concurrency ?? Infinity;\n this.reduceInputFormat = opts.reduceInputFormat ?? ((mapperResults) => {\n const parts: string[] = [];\n for (const [idx, result] of mapperResults) {\n parts.push(`--- 子任务 ${idx + 1} ---\\n${result.content}`);\n }\n return parts.join('\\n\\n');\n });\n\n this.state.nodeStates.set(mapper.id, 'pending');\n this.state.nodeStates.set(reducer.id, 'pending');\n }\n\n getState(): GraphExecutionState {\n return { ...this.state };\n }\n\n /** 执行 MapReduce */\n async run(input: string | Request): Promise<MultiAgentResult> {\n // 前置校验:split 结果\n const inputText = typeof input === 'string' ? input : input.message;\n const chunks = this.split(inputText);\n if (chunks.length === 0) {\n throw new Error('MapReduce: split 函数返回了空数组,至少需要一个子任务');\n }\n\n const ctx = createSharedContext({\n meta: { traceId: `mr-${Date.now()}`, startTime: Date.now() },\n });\n\n try {\n return await this.executeMapReduce(input, ctx, () => {});\n } catch (err) {\n return this.buildErrorResult(ctx, err);\n }\n }\n\n /** 流式执行 MapReduce */\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n // 前置校验\n const inputText = typeof input === 'string' ? input : input.message;\n const chunks = this.split(inputText);\n if (chunks.length === 0) {\n throw new Error('MapReduce: split 函数返回了空数组,至少需要一个子任务');\n }\n\n const ctx = createSharedContext({\n meta: { traceId: `mr-${Date.now()}`, startTime: Date.now() },\n });\n\n const eventQueue: MultiAgentEvent[] = [];\n let resolveEvent: (() => void) | null = null;\n let done = false;\n\n const emit = (event: MultiAgentEvent) => {\n eventQueue.push(event);\n resolveEvent?.();\n };\n\n const graphPromise = this.executeMapReduce(input, ctx, emit).then(\n (result) => { emit({ type: 'graph_done', result }); },\n (err) => { emit({ type: 'graph_error', error: err instanceof Error ? err.message : String(err) }); },\n ).finally(() => {\n done = true;\n resolveEvent?.();\n });\n\n while (!done || eventQueue.length > 0) {\n if (eventQueue.length > 0) {\n yield eventQueue.shift()!;\n } else {\n await new Promise<void>(resolve => { resolveEvent = resolve; });\n }\n }\n\n await graphPromise;\n }\n\n /** 核心执行逻辑 */\n private async executeMapReduce(\n input: string | Request,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n ): Promise<MultiAgentResult> {\n let stepsCompleted = 0;\n const totalUsage: Record<string, number> = {};\n const inputText = typeof input === 'string' ? input : input.message;\n\n // ── Step 1: Split ──────────────────────────────────────────\n const chunks = this.split(inputText);\n // 校验已在 run()/stream() 中完成\n\n // ── Step 2: Map(并行执行 mapper) ─────────────────────────\n const mapperResults = new Map<number, Result>();\n this.state.nodeStates.set(this.mapperNode.id, 'running');\n\n // 为每个子任务生成虚拟 ID\n const mapperAgentIds = chunks.map((_, i) => `${this.mapperNode.id}_${i}`);\n emit({ type: 'parallel_start', agentIds: mapperAgentIds });\n\n if (this.concurrency >= chunks.length) {\n // 无限制并发\n const promises = chunks.map(async (chunk, index) => {\n emit({ type: 'agent_start', agentId: `${this.mapperNode.id}_${index}`, agentName: `${this.mapperNode.name}#${index + 1}` });\n try {\n const result = await executeNode(this.mapperNode, chunk, ctx);\n this.state.nodeResults.set(`${this.mapperNode.id}_${index}`, result);\n this.mergeUsage(totalUsage, result.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: `${this.mapperNode.id}_${index}`, agentName: `${this.mapperNode.name}#${index + 1}`, result });\n return { index, result };\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n emit({ type: 'agent_error', agentId: `${this.mapperNode.id}_${index}`, agentName: `${this.mapperNode.name}#${index + 1}`, error: errorMsg });\n throw err;\n }\n });\n\n const settled = await Promise.allSettled(promises);\n for (const s of settled) {\n if (s.status === 'fulfilled') {\n mapperResults.set(s.value.index, s.value.result);\n }\n }\n } else {\n // 限制并发数\n let index = 0;\n const executing = new Set<Promise<void>>();\n\n const enqueue = (): Promise<void> | null => {\n if (index >= chunks.length) return null;\n const currentIndex = index++;\n const chunk = chunks[currentIndex];\n\n const p = (async () => {\n emit({ type: 'agent_start', agentId: `${this.mapperNode.id}_${currentIndex}`, agentName: `${this.mapperNode.name}#${currentIndex + 1}` });\n try {\n const result = await executeNode(this.mapperNode, chunk, ctx);\n mapperResults.set(currentIndex, result);\n this.state.nodeResults.set(`${this.mapperNode.id}_${currentIndex}`, result);\n this.mergeUsage(totalUsage, result.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: `${this.mapperNode.id}_${currentIndex}`, agentName: `${this.mapperNode.name}#${currentIndex + 1}`, result });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n emit({ type: 'agent_error', agentId: `${this.mapperNode.id}_${currentIndex}`, agentName: `${this.mapperNode.name}#${currentIndex + 1}`, error: errorMsg });\n throw err;\n }\n })();\n\n executing.add(p);\n p.finally(() => executing.delete(p));\n return p;\n };\n\n for (let i = 0; i < this.concurrency && index < chunks.length; i++) {\n enqueue();\n }\n\n while (executing.size > 0) {\n await Promise.race(executing);\n enqueue();\n }\n }\n\n this.state.nodeStates.set(this.mapperNode.id, 'completed');\n const mapperResultsForEmit = new Map<string, Result>();\n for (const [idx, result] of mapperResults) {\n mapperResultsForEmit.set(`${this.mapperNode.id}_${idx}`, result);\n }\n emit({ type: 'parallel_done', results: mapperResultsForEmit });\n\n // 将 mapper 结果写入 blackboard\n ctx.blackboard.set('mapper_results', mapperResults);\n\n // ── Step 3: Reduce ─────────────────────────────────────────\n const reduceInput = this.reduceInputFormat(mapperResults);\n\n this.state.currentAgentId = this.reducerNode.id;\n this.state.nodeStates.set(this.reducerNode.id, 'running');\n emit({ type: 'agent_start', agentId: this.reducerNode.id, agentName: this.reducerNode.name });\n\n let reducerResult: Result;\n try {\n reducerResult = await executeNode(this.reducerNode, reduceInput, ctx);\n this.state.nodeStates.set(this.reducerNode.id, 'completed');\n this.state.nodeResults.set(this.reducerNode.id, reducerResult);\n this.mergeUsage(totalUsage, reducerResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: this.reducerNode.id, agentName: this.reducerNode.name, result: reducerResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(this.reducerNode.id, 'failed');\n emit({ type: 'agent_error', agentId: this.reducerNode.id, agentName: this.reducerNode.name, error: errorMsg });\n throw err;\n }\n\n this.state.finished = true;\n return {\n content: reducerResult.content,\n lastAgentId: this.reducerNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage,\n stepsCompleted,\n stopReason: 'completed',\n context: ctx,\n success: true,\n };\n }\n\n private buildErrorResult(ctx: SharedContext, err: unknown): MultiAgentResult {\n this.state.finished = true;\n return {\n content: '',\n lastAgentId: this.mapperNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: 'error',\n context: ctx,\n success: false,\n error: err instanceof Error ? err.message : String(err),\n };\n }\n\n private mergeUsage(total: Record<string, number>, usage: Record<string, number>): void {\n for (const [key, value] of Object.entries(usage)) {\n total[key] = (total[key] ?? 0) + value;\n }\n }\n}\n","/**\n * patterns/map-reduce.ts - MapReduce 并行聚合模式\n *\n * 将输入拆分为子任务,用 mapper 并行处理,再用 reducer 汇总。\n */\n\nimport type { AgentNode, AgentGraph, MapReduceOpts, EventListener, MultiAgentResult, MultiAgentEvent } from '../core/types';\nimport { MapReduceExecutor } from '../core/map-reduce-executor';\nimport type { Request } from '@aipack-ai/agent';\n\n// ─── MapReduceGraphImpl ──────────────────────────────────────────\n\nclass MapReduceGraphImpl implements AgentGraph {\n private executor: MapReduceExecutor;\n private eventListeners = new Map<string, Set<EventListener>>();\n\n constructor(mapper: AgentNode, reducer: AgentNode, opts: MapReduceOpts) {\n this.executor = new MapReduceExecutor(mapper, reducer, opts);\n }\n\n addNode(): this { throw new Error('MapReduce 模式不支持手动 addNode'); }\n addEdge(): this { throw new Error('MapReduce 模式不支持手动 addEdge'); }\n setEntry(): this { throw new Error('MapReduce 模式不支持 setEntry'); }\n setFinish(): this { throw new Error('MapReduce 模式不支持 setFinish'); }\n\n async run(input: string | Request): Promise<MultiAgentResult> {\n return this.executor.run(input);\n }\n\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n yield* this.executor.stream(input);\n }\n\n getState() { return this.executor.getState(); }\n abort(): void {}\n\n on(event: string, listener: EventListener): this {\n let set = this.eventListeners.get(event);\n if (!set) { set = new Set(); this.eventListeners.set(event, set); }\n set.add(listener);\n return this;\n }\n}\n\n// ─── createMapReduce 工厂函数 ────────────────────────────────────\n\n/**\n * 创建 MapReduce 并行聚合模式\n *\n * @param mapper - 映射方 Agent(处理单个子任务)\n * @param reducer - 汇总方 Agent(合并所有 mapper 结果)\n * @param opts - MapReduce 配置选项(必须提供 split 函数)\n * @returns AgentGraph 实例\n */\nexport function createMapReduce(\n mapper: AgentNode,\n reducer: AgentNode,\n opts: MapReduceOpts,\n): AgentGraph {\n return new MapReduceGraphImpl(mapper, reducer, opts);\n}\n","/**\n * jsonrpc.ts - JSON-RPC 2.0 编解码 + 消息分类(纯函数)\n *\n * 不依赖任何 Node API,可在任意 JS 运行时使用。stdio 传输层以行分隔\n * 逐条调用 parseMessage / serialize。\n */\n\nexport type JsonRpcId = number | string | null;\n\nexport interface JsonRpcRequest {\n jsonrpc: '2.0';\n id: Exclude<JsonRpcId, null>;\n method: string;\n params?: unknown;\n}\n\nexport interface JsonRpcNotification {\n jsonrpc: '2.0';\n method: string;\n params?: unknown;\n}\n\nexport interface JsonRpcSuccessResponse {\n jsonrpc: '2.0';\n id: JsonRpcId;\n result: unknown;\n}\n\nexport interface JsonRpcErrorResponse {\n jsonrpc: '2.0';\n id: JsonRpcId;\n error: { code: number; message: string; data?: unknown };\n}\n\nexport type JsonRpcResponse = JsonRpcSuccessResponse | JsonRpcErrorResponse;\n\nexport type JsonRpcMessage =\n | JsonRpcRequest\n | JsonRpcNotification\n | JsonRpcResponse;\n\n// ─── 标准错误码 ─────────────────────────────────────────────────\n\nexport const PARSE_ERROR = -32700;\nexport const INVALID_REQUEST = -32600;\nexport const METHOD_NOT_FOUND = -32601;\nexport const INVALID_PARAMS = -32602;\nexport const INTERNAL_ERROR = -32603;\n\n// ─── 构造 ─────────────────────────────────────────────────────\n\nexport function createRequest(\n id: Exclude<JsonRpcId, null>,\n method: string,\n params?: unknown,\n): JsonRpcRequest {\n const req: JsonRpcRequest = { jsonrpc: '2.0', id, method };\n if (params !== undefined) req.params = params;\n return req;\n}\n\nexport function createNotification(method: string, params?: unknown): JsonRpcNotification {\n const n: JsonRpcNotification = { jsonrpc: '2.0', method };\n if (params !== undefined) n.params = params;\n return n;\n}\n\nexport function createSuccessResponse(id: JsonRpcId, result: unknown): JsonRpcSuccessResponse {\n return { jsonrpc: '2.0', id, result };\n}\n\nexport function createErrorResponse(\n id: JsonRpcId,\n code: number,\n message: string,\n data?: unknown,\n): JsonRpcErrorResponse {\n const err: JsonRpcErrorResponse = { jsonrpc: '2.0', id, error: { code, message } };\n if (data !== undefined) err.error.data = data;\n return err;\n}\n\n// ─── 序列化 ───────────────────────────────────────────────────\n\nexport function serialize(message: JsonRpcMessage): string {\n return JSON.stringify(message);\n}\n\n// ─── 解析 / 分类 ───────────────────────────────────────────────\n\nfunction hasOwn(o: unknown, k: string): boolean {\n return typeof o === 'object' && o !== null && Object.prototype.hasOwnProperty.call(o, k);\n}\n\n/**\n * 解析一段字符串为 JSON-RPC 消息,或返回 null(非 JSON / 非合法 JSON-RPC)。\n * 容错:不要求 result/error 二者互斥以外的强校验,未知字段保留。\n */\nexport function parseMessage(raw: string): JsonRpcMessage | null {\n let obj: unknown;\n try {\n obj = JSON.parse(raw);\n } catch {\n return null;\n }\n return classify(obj);\n}\n\n/** 对已解析的对象做 JSON-RPC 2.0 形状判定(不入站不 JSON.parse 的场景) */\nexport function classify(obj: unknown): JsonRpcMessage | null {\n if (typeof obj !== 'object' || obj === null) return null;\n const o = obj as Record<string, unknown>;\n if (o.jsonrpc !== '2.0') return null;\n\n // 响应:有 result 或 error\n if (hasOwn(o, 'result') || hasOwn(o, 'error')) {\n return o as unknown as JsonRpcResponse;\n }\n // 请求 / 通知:有 method\n if (hasOwn(o, 'method') && typeof o.method === 'string') {\n // 有 id(非 null)即请求;通知无 id 字段\n if (hasOwn(o, 'id') && o.id !== null) return o as unknown as JsonRpcRequest;\n if (!hasOwn(o, 'id') || o.id === null) return o as unknown as JsonRpcNotification;\n }\n return null;\n}\n\nexport function isResponse(m: JsonRpcMessage): m is JsonRpcResponse {\n return 'result' in m || 'error' in m;\n}\n\nexport function isRequest(m: JsonRpcMessage): m is JsonRpcRequest {\n return !isResponse(m) && 'id' in m && (m as JsonRpcRequest).id !== null;\n}\n\nexport function isNotification(m: JsonRpcMessage): m is JsonRpcNotification {\n return !isResponse(m) && !('id' in m && (m as { id?: unknown }).id !== null);\n}\n\nexport function isErrorResponse(m: JsonRpcMessage): m is JsonRpcErrorResponse {\n return isResponse(m) && 'error' in m;\n}\n","/**\n * protocol.ts - MCP 协议子集消息构造 / 校验(纯函数)\n *\n * v1 范围:initialize / notifications/initialized / tools/list / tools/call /\n * ping / notifications/cancelled / notifications/tools/list_changed。\n * resources / prompts / sampling 留待后续版本。\n *\n * 设计原则:本模块只产 / 解 MCP 消息形状,不分配 JSON-RPC id(id 由会话层\n * McpClient 分配并经 jsonrpc.createRequest 注入),保证纯函数可单测。\n */\n\nimport {\n createRequest,\n createNotification,\n type JsonRpcRequest,\n type JsonRpcNotification,\n isErrorResponse,\n} from './jsonrpc';\n\n// ─── 协议版本 ─────────────────────────────────────────────────\n\n/** 客户端宣告版本(最新稳定) */\nexport const MCP_PROTOCOL_VERSION = '2025-06-18';\n/** 协议基线;server 声明版本 < 此值则视为不兼容 */\nexport const MCP_BASELINE_VERSION = '2024-11-05';\n\n// ─── 能力 / 信息 ─────────────────────────────────────────────\n\nexport interface McpClientInfo {\n name: string;\n version: string;\n}\n\nexport interface McpServerInfo {\n name: string;\n version: string;\n}\n\nexport interface McpServerCapabilities {\n tools?: { listChanged?: boolean };\n resources?: Record<string, unknown> | {};\n prompts?: Record<string, unknown> | {};\n logging?: Record<string, unknown> | {};\n [key: string]: unknown;\n}\n\n// ─── 工具形状 ─────────────────────────────────────────────────\n\nexport interface McpToolInfo {\n name: string;\n description?: string;\n /** JSON Schema,直接对接 agent Tool.parameters */\n inputSchema?: unknown;\n annotations?: unknown;\n}\n\nexport interface McpContentBlock {\n type: string;\n text?: string;\n data?: string;\n mimeType?: string;\n /** 规范中 resource 块的载荷在嵌套字段 */\n resource?: { uri: string; text?: string; blob?: string; mimeType?: string };\n}\n\nexport interface McpToolCallResult {\n content: McpContentBlock[];\n isError?: boolean;\n}\n\n// ─── initialize ───────────────────────────────────────────────\n\nexport interface McpInitializeResult {\n protocolVersion: string;\n serverInfo: McpServerInfo;\n capabilities: McpServerCapabilities;\n}\n\n/**\n * 协议版本协商:client 发送 clientVersion,server 返回其版本。\n * - server 版本 === clientVersion → ok,使用之\n * - server 版本 >= baseline → ok,使用 server 版本(降级)\n * - 否则不兼容\n */\nexport function negotiateProtocol(\n clientVersion: string,\n serverVersion: string,\n): { ok: boolean; version?: string } {\n if (!serverVersion || typeof serverVersion !== 'string') return { ok: false };\n if (serverVersion === clientVersion) return { ok: true, version: serverVersion };\n // 字符串序不足以判断版本先后,这里仅做基线存在性校验:只要 >= baseline 即接受\n if (serverVersion >= MCP_BASELINE_VERSION) return { ok: true, version: serverVersion };\n return { ok: false };\n}\n\nexport function createInitializeRequest(\n id: number | string,\n client: McpClientInfo,\n capabilities?: Record<string, unknown>,\n): JsonRpcRequest {\n return createRequest(id, 'initialize', buildInitializeParams(client, capabilities));\n}\n\n/** 构造 initialize 请求 params(协议版本 + 能力 + 客户端信息) */\nexport function buildInitializeParams(\n client: McpClientInfo,\n capabilities?: Record<string, unknown>,\n): Record<string, unknown> {\n return {\n protocolVersion: MCP_PROTOCOL_VERSION,\n capabilities: capabilities ?? {},\n clientInfo: client,\n };\n}\n\nexport function createInitializedNotification(): JsonRpcNotification {\n return createNotification('notifications/initialized');\n}\n\n/** 解析 initialize 响应 result;容错:缺省字段给出合理默认 */\nexport function parseInitializeResult(result: unknown): McpInitializeResult {\n const r = (result ?? {}) as Record<string, unknown>;\n const serverInfo = (r.serverInfo ?? { name: 'unknown', version: '0.0.0' }) as McpServerInfo;\n const capabilities = (r.capabilities ?? {}) as McpServerCapabilities;\n const protocolVersion = typeof r.protocolVersion === 'string' ? r.protocolVersion : '';\n return { protocolVersion, serverInfo, capabilities };\n}\n\n// ─── tools/list ──────────────────────────────────────────────\n\nexport function createListToolsRequest(id: number | string, cursor?: string): JsonRpcRequest {\n const params: Record<string, unknown> = {};\n if (cursor) params.cursor = cursor;\n return createRequest(id, 'tools/list', Object.keys(params).length ? params : undefined);\n}\n\nexport interface McpToolListResult {\n tools: McpToolInfo[];\n nextCursor?: string;\n}\n\nexport function parseToolListResponse(result: unknown): McpToolListResult {\n const r = (result ?? {}) as Record<string, unknown>;\n const rawTools = Array.isArray(r.tools) ? (r.tools as unknown[]) : [];\n const tools: McpToolInfo[] = [];\n for (const t of rawTools) {\n const tt = t as Record<string, unknown>;\n if (!tt || typeof tt.name !== 'string') continue; // 跳过非法工具\n tools.push({\n name: tt.name,\n description: typeof tt.description === 'string' ? tt.description : undefined,\n inputSchema: tt.inputSchema,\n annotations: tt.annotations,\n });\n }\n const nextCursor = typeof r.nextCursor === 'string' ? r.nextCursor : undefined;\n return { tools, nextCursor };\n}\n\n// ─── tools/call ───────────────────────────────────────────────\n\nexport function createCallToolRequest(\n id: number | string,\n name: string,\n args: unknown,\n): JsonRpcRequest {\n return createRequest(id, 'tools/call', { name, arguments: args ?? {} });\n}\n\n/**\n * 解析 tools/call 响应。容错:\n * - content 缺失 → 空数组\n * - 未知 type / 未知字段保留(由 adapter 层降级映射)\n * - JSON-RPC error 响应 → 转为 isError + 错误文本\n */\nexport function parseToolCallResult(result: unknown): McpToolCallResult {\n if (result && typeof result === 'object' && 'error' in result) {\n // 调用方传入的是整个 JSON-RPC error 对象(不应发生,但兜底)\n const err = (result as { error: { message?: string } }).error;\n return { content: [{ type: 'text', text: err?.message ?? 'MCP call error' }], isError: true };\n }\n const r = (result ?? {}) as Record<string, unknown>;\n const rawContent = Array.isArray(r.content) ? (r.content as unknown[]) : [];\n const content: McpContentBlock[] = [];\n for (const c of rawContent) {\n const cc = c as Record<string, unknown>;\n if (!cc || typeof cc.type !== 'string') {\n content.push({ type: 'text', text: '[unsupported content]' });\n continue;\n }\n content.push({\n type: cc.type,\n text: typeof cc.text === 'string' ? cc.text : undefined,\n data: typeof cc.data === 'string' ? cc.data : undefined,\n mimeType: typeof cc.mimeType === 'string' ? cc.mimeType : undefined,\n resource: cc.resource as McpContentBlock['resource'],\n });\n }\n if (content.length === 0) content.push({ type: 'text', text: '[empty result]' });\n // isError 仅在 true 时显式置位,否则 undefined(与 agent \"details.error 缺省 = 成功\" 约定一致)\n const isError = r.isError === true ? true : undefined;\n return { content, isError };\n}\n\n/** 把 JSON-RPC error 响应转为 MCP 工具调用结果(isError) */\nexport function errorResponseToCallResult(message: string): McpToolCallResult {\n return { content: [{ type: 'text', text: message }], isError: true };\n}\n\n// ─── ping ─────────────────────────────────────────────────────\n\nexport function createPingRequest(id: number | string): JsonRpcRequest {\n return createRequest(id, 'ping', {});\n}\n\n// ─── notifications ────────────────────────────────────────────\n\n/** 取消通知:告知 server 某请求已被取消(协作型 server 可停止计算) */\nexport function createCancelledNotification(\n requestId: number | string,\n reason?: string,\n): JsonRpcNotification {\n const params: Record<string, unknown> = { requestId };\n if (reason) params.reason = reason;\n return createNotification('notifications/cancelled', params);\n}\n\n/** 工具列表变更通知:订阅后 server 主动告知客户端重新拉取 */\nexport function createListChangedNotification(): JsonRpcNotification {\n return createNotification('notifications/tools/list_changed');\n}\n\nexport function isListChangedNotification(m: { method?: string }): boolean {\n return m.method === 'notifications/tools/list_changed';\n}\n\n// ─── 服务端方向:resources / prompts(M3,可选)──────────────\n// host 在 options 提供 resources / prompts 时才 advertise 对应 capability 并\n// 处理 resources/list | resources/read | prompts/list | prompts/get;\n// 未提供时 capability 缺省,方法回 -32601(method not found)。\n\nexport interface McpResource {\n uri: string;\n name?: string;\n description?: string;\n mimeType?: string;\n /** 内嵌文本(read 时返回 text 块) */\n text?: string;\n /** 内嵌二进制(base64;read 时返回 blob 块) */\n blob?: string;\n}\n\nexport interface McpPromptArgument {\n name: string;\n description?: string;\n required?: boolean;\n}\n\nexport interface McpPromptMessage {\n role: 'user' | 'assistant';\n content:\n | { type: 'text'; text: string }\n | { type: 'image'; data: string; mimeType?: string }\n | { type: 'resource'; resource: { uri: string; text?: string; blob?: string; mimeType?: string } };\n}\n\nexport interface McpPrompt {\n name: string;\n description?: string;\n arguments?: McpPromptArgument[];\n /** 静态消息(get 时返回);或由 host 外部动态构造 */\n messages?: McpPromptMessage[];\n}\n\n// ─── 服务端:入站请求 params 解析(纯函数,容错)──────────────\n\nexport function parseInitializeParams(params: unknown): {\n protocolVersion?: string;\n clientInfo?: McpClientInfo;\n capabilities?: Record<string, unknown>;\n} {\n const p = (params ?? {}) as Record<string, unknown>;\n return {\n protocolVersion: typeof p.protocolVersion === 'string' ? p.protocolVersion : undefined,\n clientInfo: p.clientInfo as McpClientInfo | undefined,\n capabilities: p.capabilities as Record<string, unknown> | undefined,\n };\n}\n\nexport function parseToolCallParams(params: unknown): { name?: string; arguments?: unknown } {\n const p = (params ?? {}) as Record<string, unknown>;\n return {\n name: typeof p.name === 'string' ? p.name : undefined,\n arguments: p.arguments,\n };\n}\n\nexport function parseListToolsParams(params: unknown): { cursor?: string } {\n const p = (params ?? {}) as Record<string, unknown>;\n return { cursor: typeof p.cursor === 'string' ? p.cursor : undefined };\n}\n\nexport function parseResourceReadParams(params: unknown): { uri?: string } {\n const p = (params ?? {}) as Record<string, unknown>;\n return { uri: typeof p.uri === 'string' ? p.uri : undefined };\n}\n\nexport function parsePromptGetParams(params: unknown): { name?: string; arguments?: Record<string, unknown> } {\n const p = (params ?? {}) as Record<string, unknown>;\n return {\n name: typeof p.name === 'string' ? p.name : undefined,\n arguments: p.arguments as Record<string, unknown> | undefined,\n };\n}\n\n// ─── 服务端:响应 result 构造(纯函数;host 用 createSuccessResponse 包装)──\n\nexport interface McpServerInfoLike {\n name: string;\n version: string;\n}\n\n/** 服务端 initialize 响应 result */\nexport function createInitializeResult(\n serverInfo: McpServerInfoLike,\n capabilities: McpServerCapabilities,\n): unknown {\n return {\n protocolVersion: MCP_PROTOCOL_VERSION,\n capabilities,\n serverInfo,\n };\n}\n\n/** 服务端 tools/list 响应 result */\nexport function buildToolsListResult(\n tools: Array<{ name: string; description?: string; inputSchema?: unknown }>,\n nextCursor?: string,\n): unknown {\n const list = tools.map((t) => {\n const out: Record<string, unknown> = { name: t.name };\n if (t.description !== undefined) out.description = t.description;\n out.inputSchema = t.inputSchema ?? { type: 'object', properties: {} };\n return out;\n });\n const r: Record<string, unknown> = { tools: list };\n if (nextCursor) r.nextCursor = nextCursor;\n return r;\n}\n\n/** 服务端 tools/call 响应 result */\nexport function buildToolCallResult(content: McpContentBlock[], isError?: boolean): unknown {\n const r: Record<string, unknown> = { content: content.length ? content : [{ type: 'text', text: '[empty result]' }] };\n if (isError) r.isError = true;\n return r;\n}\n\n/** 服务端 resources/list 响应 result */\nexport function buildResourcesListResult(resources: McpResource[], nextCursor?: string): unknown {\n const list = resources.map((r0) => {\n const out: Record<string, unknown> = { uri: r0.uri };\n if (r0.name !== undefined) out.name = r0.name;\n if (r0.description !== undefined) out.description = r0.description;\n if (r0.mimeType !== undefined) out.mimeType = r0.mimeType;\n return out;\n });\n const r: Record<string, unknown> = { resources: list };\n if (nextCursor) r.nextCursor = nextCursor;\n return r;\n}\n\n/** 服务端 resources/read 响应 result(按 uri 查找;未命中返回 null 交由 host 报错) */\nexport function buildResourceReadResult(resource: McpResource): unknown {\n const contents: Record<string, unknown> = { uri: resource.uri };\n if (resource.mimeType !== undefined) contents.mimeType = resource.mimeType;\n if (resource.text !== undefined) contents.text = resource.text;\n else if (resource.blob !== undefined) contents.blob = resource.blob;\n return { contents: [contents] };\n}\n\n/** 服务端 prompts/list 响应 result */\nexport function buildPromptsListResult(prompts: McpPrompt[], nextCursor?: string): unknown {\n const list = prompts.map((p0) => {\n const out: Record<string, unknown> = { name: p0.name };\n if (p0.description !== undefined) out.description = p0.description;\n if (p0.arguments !== undefined) out.arguments = p0.arguments;\n return out;\n });\n const r: Record<string, unknown> = { prompts: list };\n if (nextCursor) r.nextCursor = nextCursor;\n return r;\n}\n\n/** 服务端 prompts/get 响应 result */\nexport function buildPromptGetResult(messages: McpPromptMessage[]): unknown {\n return { messages: messages ?? [] };\n}\n\n// ─── sampling(server ↔ client LLM 补全请求,2025-06-18)──────────\n// server 经 sampling/createMessage 请求 client 用其 LLM 生成补全;双向:\n// - 客户端方向:外部 server 发起 → 本库 McpClient 应答(onSampling 钩子)\n// - 服务端方向:McpServerHost 发起 → 外部 client 应答(host.sampleLLM,\n// 经传输层出站通道;stdio-runner 自动接线请求/响应关联)\n\nexport interface McpSamplingContentBlock {\n type: 'text' | 'image';\n text?: string; // type=text\n data?: string; // type=image (base64)\n mimeType?: string; // type=image\n}\n\nexport interface McpSamplingMessage {\n role: 'user' | 'assistant';\n content: McpSamplingContentBlock | McpSamplingContentBlock[];\n}\n\nexport interface McpModelPreferences {\n hints?: Array<'cost' | 'speed' | 'intelligence' | 'quality'>;\n costPriority?: number;\n speedPriority?: number;\n intelligencePriority?: number;\n qualityPriority?: number;\n [key: string]: unknown;\n}\n\nexport interface McpCreateMessageParams {\n messages: McpSamplingMessage[];\n modelPreferences?: McpModelPreferences;\n systemPrompt?: string;\n includeContext?: 'none' | 'thisServer' | 'allServers';\n maxTokens?: number;\n stopSequences?: string[];\n metadata?: Record<string, unknown>;\n}\n\nexport interface McpCreateMessageResult {\n role: 'assistant';\n content: McpSamplingContentBlock;\n model: string;\n stopReason?: 'endTurn' | 'stopSequence' | 'maxTokens' | 'other';\n stopSequence?: string;\n usage?: { inputTokens?: number; outputTokens?: number; totalTokens?: number };\n}\n\n/** 构造 sampling/createMessage 请求(服务端方向发起;id 由调用方分配) */\nexport function createSamplingRequest(\n id: number | string,\n params: McpCreateMessageParams,\n): JsonRpcRequest {\n return createRequest(id, 'sampling/createMessage', params);\n}\n\n/** 解析入站 sampling/createMessage 请求 params(客户端方向应答用);容错:缺 messages 返回空数组 */\nexport function parseCreateMessageParams(payload: unknown): McpCreateMessageParams {\n const p = (payload ?? {}) as Record<string, unknown>;\n const messages = Array.isArray(p.messages) ? (p.messages as McpSamplingMessage[]) : [];\n const out: McpCreateMessageParams = { messages };\n if (p.systemPrompt !== undefined) out.systemPrompt = p.systemPrompt as string;\n if (p.includeContext !== undefined) out.includeContext = p.includeContext as McpCreateMessageParams['includeContext'];\n if (p.maxTokens !== undefined) out.maxTokens = p.maxTokens as number;\n if (p.modelPreferences !== undefined) out.modelPreferences = p.modelPreferences as McpModelPreferences;\n if (p.stopSequences !== undefined) out.stopSequences = p.stopSequences as string[];\n if (p.metadata !== undefined) out.metadata = p.metadata as Record<string, unknown>;\n return out;\n}\n\n/** 构造 sampling/createMessage 响应 result(客户端方向应答用) */\nexport function buildCreateMessageResult(result: McpCreateMessageResult): unknown {\n const out: Record<string, unknown> = {\n role: 'assistant',\n content: result.content,\n model: result.model,\n };\n if (result.stopReason !== undefined) out.stopReason = result.stopReason;\n if (result.stopSequence !== undefined) out.stopSequence = result.stopSequence;\n if (result.usage !== undefined) out.usage = result.usage;\n return out;\n}\n\n/** 解析 sampling/createMessage 响应 result(服务端方向发起后解析应答);容错:缺省字段给默认 */\nexport function parseCreateMessageResult(payload: unknown): McpCreateMessageResult {\n const r = (payload ?? {}) as Record<string, unknown>;\n const content = (r.content ?? { type: 'text', text: '' }) as McpSamplingContentBlock;\n return {\n role: 'assistant',\n content: typeof content.type === 'string' ? content : { type: 'text', text: '' },\n model: typeof r.model === 'string' ? r.model : 'unknown',\n stopReason: r.stopReason as McpCreateMessageResult['stopReason'],\n stopSequence: typeof r.stopSequence === 'string' ? r.stopSequence : undefined,\n usage: r.usage as McpCreateMessageResult['usage'],\n };\n}\n\nexport { isErrorResponse };\n","/**\n * server/host.ts - MCP 服务端宿主(Node only,但消息分发逻辑为纯 async)\n *\n * 把 aipack 原生 Tool[] / resources / prompts 反向暴露为标准 MCP Server,\n * 供外部 MCP 客户端(Claude Desktop、Cursor 等)调用。\n *\n * 与 multi-agent/MCPBridge 的关系:泛化而非复制——MCPBridge 保持不动\n * (避免 breaking),本模块提供面向任意 Tool[] 的通用实现;MCPBridge 后续可迁移。\n *\n * 设计:\n * - 传输层无关:只产 / 解 JSON-RPC 消息,由 stdio-entry / http 入口驱动\n * - 入站三类消息:响应(不应收到,忽略)、通知(initialized/cancelled,no-op)、\n * 请求(dispatch:initialize / tools/* / resources/* / prompts/* / ping)\n * - 工具调用经 authorize 钩子裁决(stdio 本地默认放行;可注入 PermissionPolicy 包装)\n * - agent ToolResult.content → MCP content blocks(text/image 1:1;thinking/toolCall\n * 降级为文本摘要),details.error 存在 → isError\n * - 未知方法回 -32601;非法 params 内部抛错回 -32603\n */\n\nimport type {\n Tool,\n ToolResult,\n ContentBlock,\n TextContent,\n ImageContent,\n} from '@aipack-ai/agent';\nimport * as jsonrpc from '../client/jsonrpc';\nimport {\n createInitializeResult,\n buildToolsListResult,\n buildToolCallResult,\n buildResourcesListResult,\n buildResourceReadResult,\n buildPromptsListResult,\n buildPromptGetResult,\n parseToolCallParams,\n parseResourceReadParams,\n parsePromptGetParams,\n parseCreateMessageResult,\n createListChangedNotification,\n type McpServerCapabilities,\n type McpContentBlock,\n type McpResource,\n type McpPrompt,\n type McpServerInfoLike,\n type McpCreateMessageParams,\n type McpCreateMessageResult,\n} from '../client/protocol';\n\n// ─── 反向 content 映射(agent ContentBlock → MCP content block)──────────\n\n/**\n * agent ContentBlock → MCP McpContentBlock。\n * - text → { type:'text', text }\n * - image → { type:'image', data, mimeType }(缺 mimeType 降级文本)\n * - thinking → { type:'text', text }(MCP 无 thinking 概念,透传为文本)\n * - toolCall → { type:'text', text: JSON }(摘要)\n */\nexport function mapAgentContentToMcp(blocks: ContentBlock[]): McpContentBlock[] {\n const out: McpContentBlock[] = [];\n for (const b of blocks) {\n out.push(mapOneAgentBlock(b));\n }\n return out.length ? out : [{ type: 'text', text: '[empty result]' }];\n}\n\nfunction mapOneAgentBlock(b: ContentBlock): McpContentBlock {\n if (b.type === 'text') {\n const t = b as TextContent;\n return { type: 'text', text: t.text };\n }\n if (b.type === 'image') {\n const img = b as ImageContent;\n if (typeof img.data === 'string' && typeof img.mimeType === 'string') {\n return { type: 'image', data: img.data, mimeType: img.mimeType };\n }\n return { type: 'text', text: '[image: missing data/mimeType]' };\n }\n // thinking / toolCall:降级为文本摘要\n return { type: 'text', text: JSON.stringify(b) };\n}\n\n/** agent ToolResult → MCP tools/call 结果(isError 由 details.error 推导) */\nexport function toolResultToMcpCallResult(result: ToolResult): { content: McpContentBlock[]; isError?: boolean } {\n const isError = isToolResultError(result);\n return { content: mapAgentContentToMcp(result.content ?? []), isError: isError ? true : undefined };\n}\n\nfunction isToolResultError(result: ToolResult): boolean {\n const d = result.details;\n if (d && typeof d === 'object' && 'error' in (d as Record<string, unknown>)) {\n const e = (d as Record<string, unknown>).error;\n return !!e || typeof e === 'string';\n }\n return false;\n}\n\n// ─── 选项 ─────────────────────────────────────────────────────\n\nexport interface McpAuthorizeCall {\n /** 工具名 */\n toolName: string;\n /** 工具声明的权限能力 */\n permissions: readonly string[];\n /** 经 prepareArguments 处理后的参数 */\n args: unknown;\n}\n\n/**\n * 授权钩子:返回 true 放行、false 拒绝(→ isError 结果)。\n * stdio 本地默认放行(对齐计划\"本地拉起默认放行\");http 场景可注入\n * 包装 PermissionPolicy 的 authorize(check → allow/confirm 视为 true,deny/pending 视为 false)。\n */\nexport type McpAuthorizeFn = (call: McpAuthorizeCall) => Promise<boolean>;\n\nexport interface McpServerHostOptions {\n /** serverInfo.name */\n name: string;\n /** 默认 '0.1.0' */\n version?: string;\n /** 暴露的工具集合(静态数组或动态解析器,支持运行时热变更) */\n tools: Tool[] | (() => Tool[] | Promise<Tool[]>);\n /** 可选 resources(提供则 advertise resources capability 并处理 resources/* ) */\n resources?: McpResource[] | (() => McpResource[] | Promise<McpResource[]>);\n /** 可选 prompts(提供则 advertise prompts capability 并处理 prompts/* ) */\n prompts?: McpPrompt[] | (() => McpPrompt[] | Promise<McpPrompt[]>);\n /** 工具调用授权钩子;缺省放行 */\n authorize?: McpAuthorizeFn;\n /** 单次工具调用超时(默认不设,交由工具自身/runtime) */\n toolTimeoutMs?: number;\n /**\n * 启用 sampling 能力:advertise `sampling` capability,并提供 `sampleLLM()`\n * 供工具经传输层出站通道向外部 client 请求 LLM 补全。出站通道由传输层\n * (stdio-runner)经 `setOutboundRequest` 注入;未注入时 `sampleLLM` 抛错。\n */\n sampling?: boolean;\n /**\n * 直接注入出站请求通道(高级用例;stdio-runner 会自动注入,通常无需手填)。\n * 提供时同样会 advertise sampling 能力。\n */\n onOutboundRequest?: (method: string, params?: unknown) => Promise<unknown>;\n /** 服务端主动发出的通知(如 tools/list_changed)落点;stdio-entry 用以写 stdout */\n onNotification?: (msg: jsonrpc.JsonRpcNotification) => void;\n}\n\n// ─── McpServerHost ─────────────────────────────────────────────\n\n/**\n * MCP 服务端宿主。传输层无关——只产 / 解 JSON-RPC 消息。\n *\n * 用法(程序化):\n * const host = createMcpServerHost({ name: 'my-agent', tools: [...] });\n * const resp = await host.handleRequest(parsedRequest);\n *\n * 独立进程入口见 `./stdio-entry.ts`。\n */\nexport class McpServerHost {\n private serverInfo: McpServerInfoLike;\n private toolsResolver: () => Tool[] | Promise<Tool[]>;\n private resourcesResolver?: () => McpResource[] | Promise<McpResource[]>;\n private promptsResolver?: () => McpPrompt[] | Promise<McpPrompt[]>;\n private authorize?: McpAuthorizeFn;\n private toolTimeoutMs?: number;\n private onNotification?: (msg: jsonrpc.JsonRpcNotification) => void;\n private samplingEnabled: boolean;\n private outboundRequest?: (method: string, params?: unknown) => Promise<unknown>;\n private capabilities: McpServerCapabilities;\n\n constructor(options: McpServerHostOptions) {\n this.serverInfo = { name: options.name, version: options.version ?? '0.1.0' };\n this.toolsResolver = typeof options.tools === 'function'\n ? options.tools as () => Tool[] | Promise<Tool[]>\n : () => options.tools as Tool[];\n if (options.resources) {\n this.resourcesResolver = typeof options.resources === 'function'\n ? options.resources as () => McpResource[] | Promise<McpResource[]>\n : () => options.resources as McpResource[];\n }\n if (options.prompts) {\n this.promptsResolver = typeof options.prompts === 'function'\n ? options.prompts as () => McpPrompt[] | Promise<McpPrompt[]>\n : () => options.prompts as McpPrompt[];\n }\n this.authorize = options.authorize;\n this.toolTimeoutMs = options.toolTimeoutMs;\n this.onNotification = options.onNotification;\n this.outboundRequest = options.onOutboundRequest;\n this.samplingEnabled = options.sampling === true || !!options.onOutboundRequest;\n this.capabilities = this.computeCapabilities();\n }\n\n getServerInfo(): McpServerInfoLike {\n return { ...this.serverInfo };\n }\n\n getCapabilities(): McpServerCapabilities {\n return { ...this.capabilities };\n }\n\n private computeCapabilities(): McpServerCapabilities {\n const caps: Record<string, unknown> = { tools: {} };\n if (this.resourcesResolver) caps.resources = {};\n if (this.promptsResolver) caps.prompts = {};\n if (this.samplingEnabled) caps.sampling = {};\n return caps as McpServerCapabilities;\n }\n\n /** 主动通知客户端工具列表已变更 */\n notifyToolsListChanged(): void {\n this.onNotification?.(createListChangedNotification());\n }\n\n /**\n * 注入出站请求通道(由传输层如 stdio-runner 调用):写入 JSON-RPC 请求\n * 并关联响应。注入后 `sampleLLM` 可向外部 client 请求 LLM 补全。\n */\n setOutboundRequest(fn: (method: string, params?: unknown) => Promise<unknown>): void {\n this.outboundRequest = fn;\n if (!this.samplingEnabled) {\n this.samplingEnabled = true;\n this.capabilities = this.computeCapabilities();\n }\n }\n\n /**\n * 经出站通道向外部 client 请求 LLM 补全(sampling/createMessage)。\n * 需传输层(stdio-runner)已注入出站通道;未注入则抛错。\n */\n async sampleLLM(params: McpCreateMessageParams): Promise<McpCreateMessageResult> {\n if (!this.outboundRequest) {\n throw new Error('sampling unavailable: outbound request channel not attached');\n }\n const raw = await this.outboundRequest('sampling/createMessage', params);\n return parseCreateMessageResult(raw);\n }\n\n /**\n * 处理一条入站 JSON-RPC 消息。\n * - 请求 → 返回响应(JsonRpcResponse)\n * - 通知 → 返回 null(不回写)\n * - 响应 / 非法消息 → 返回 null\n */\n async handleRequest(input: unknown): Promise<jsonrpc.JsonRpcMessage | null> {\n const msg = jsonrpc.classify(input);\n if (!msg) return null;\n\n if (jsonrpc.isResponse(msg)) return null; // 服务端不处理客户端响应\n\n if (jsonrpc.isNotification(msg)) {\n // notifications/initialized / notifications/cancelled:no-op\n return null;\n }\n\n if (!jsonrpc.isRequest(msg)) return null;\n return this.onRequest(msg as jsonrpc.JsonRpcRequest);\n }\n\n private async onRequest(req: jsonrpc.JsonRpcRequest): Promise<jsonrpc.JsonRpcMessage> {\n try {\n switch (req.method) {\n case 'initialize':\n return jsonrpc.createSuccessResponse(\n req.id,\n createInitializeResult(this.serverInfo, this.capabilities),\n );\n case 'notifications/initialized':\n return jsonrpc.createSuccessResponse(req.id, {});\n case 'tools/list':\n return jsonrpc.createSuccessResponse(\n req.id,\n buildToolsListResult(await this.toToolInfos(await this.toolsResolver())),\n );\n case 'tools/call':\n return jsonrpc.createSuccessResponse(req.id, await this.handleToolCall(req));\n case 'ping':\n return jsonrpc.createSuccessResponse(req.id, {});\n case 'resources/list':\n if (!this.resourcesResolver) break;\n return jsonrpc.createSuccessResponse(\n req.id,\n buildResourcesListResult(await this.resourcesResolver()),\n );\n case 'resources/read': {\n if (!this.resourcesResolver) break;\n const { uri } = parseResourceReadParams(req.params);\n if (!uri) return jsonrpc.createErrorResponse(req.id, jsonrpc.INVALID_PARAMS, 'resources/read requires uri');\n const found = (await this.resourcesResolver()).find((r) => r.uri === uri);\n if (!found) return jsonrpc.createErrorResponse(req.id, jsonrpc.INVALID_PARAMS, `resource not found: ${uri}`);\n return jsonrpc.createSuccessResponse(req.id, buildResourceReadResult(found));\n }\n case 'prompts/list':\n if (!this.promptsResolver) break;\n return jsonrpc.createSuccessResponse(\n req.id,\n buildPromptsListResult(await this.promptsResolver()),\n );\n case 'prompts/get': {\n if (!this.promptsResolver) break;\n const { name } = parsePromptGetParams(req.params);\n if (!name) return jsonrpc.createErrorResponse(req.id, jsonrpc.INVALID_PARAMS, 'prompts/get requires name');\n const found = (await this.promptsResolver()).find((p) => p.name === name);\n if (!found) return jsonrpc.createErrorResponse(req.id, jsonrpc.INVALID_PARAMS, `prompt not found: ${name}`);\n return jsonrpc.createSuccessResponse(req.id, buildPromptGetResult(found.messages ?? []));\n }\n default:\n break;\n }\n return jsonrpc.createErrorResponse(\n req.id,\n jsonrpc.METHOD_NOT_FOUND,\n `method not found: ${req.method}`,\n );\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n return jsonrpc.createErrorResponse(req.id, jsonrpc.INTERNAL_ERROR, message);\n }\n }\n\n private async handleToolCall(req: jsonrpc.JsonRpcRequest): Promise<unknown> {\n const { name, arguments: args } = parseToolCallParams(req.params);\n if (!name) {\n return buildToolCallResult(\n [{ type: 'text', text: 'tools/call requires name' }],\n true,\n );\n }\n const tools = await this.toolsResolver();\n const tool = tools.find((t) => t.name === name);\n if (!tool) {\n return buildToolCallResult(\n [{ type: 'text', text: `unknown tool: ${name}` }],\n true,\n );\n }\n\n const prepared = tool.prepareArguments ? tool.prepareArguments(args) : args;\n\n // 授权(stdio 本地默认放行)\n if (this.authorize) {\n const allowed = await this.authorize({\n toolName: tool.name,\n permissions: tool.permissions ?? [],\n args: prepared,\n });\n if (!allowed) {\n return buildToolCallResult(\n [{ type: 'text', text: `permission denied: ${tool.name}` }],\n true,\n );\n }\n }\n\n let result: ToolResult;\n try {\n result = await this.callWithTimeout(tool, prepared);\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n return buildToolCallResult(\n [{ type: 'text', text: `tool execution failed: ${message}` }],\n true,\n );\n }\n const mapped = toolResultToMcpCallResult(result);\n return buildToolCallResult(mapped.content, mapped.isError);\n }\n\n private callWithTimeout(tool: Tool, args: unknown): Promise<ToolResult> {\n if (!this.toolTimeoutMs) return tool.execute('mcp', args);\n return new Promise<ToolResult>((resolve, reject) => {\n const ac = new AbortController();\n const timer = setTimeout(() => {\n ac.abort();\n reject(new Error(`tools/call timeout: ${tool.name} (${this.toolTimeoutMs}ms)`));\n }, this.toolTimeoutMs);\n tool.execute('mcp', args, ac.signal).then(\n (r) => { clearTimeout(timer); resolve(r); },\n (e) => { clearTimeout(timer); reject(e); },\n );\n });\n }\n\n private toToolInfos(tools: Tool[]): Array<{ name: string; description?: string; inputSchema?: unknown }> {\n return tools.map((t) => ({\n name: t.name,\n description: t.description,\n inputSchema: t.parameters,\n }));\n }\n}\n\n/** 工厂 */\nexport function createMcpServerHost(options: McpServerHostOptions): McpServerHost {\n return new McpServerHost(options);\n}\n","/**\n * extensions/mcp-bridge.ts - MCPBridge Extension\n *\n * 将 AgentGraph 暴露为 MCP (Model Context Protocol) 工具,\n * 使外部 MCP 客户端可以直接调用多 Agent 编排图。\n *\n * 设计原则:不依赖外部 MCP SDK,仅输出符合 MCP 规范的 JSON 结构,\n * 由宿主环境(如 aipack CLI)负责实际的 MCP 传输层。\n */\n\nimport type { AgentGraph, MCPBridgeOpts, MultiAgentResult } from '../core/types';\nimport type { Tool, ToolResult, ContentBlock } from '@aipack-ai/agent';\nimport { createMcpServerHost } from '@aipack-ai/mcp';\nimport type { McpServerHost } from '@aipack-ai/mcp';\n\n// ─── MCP 工具定义 ────────────────────────────────────────────────\n\n/** MCP 工具参数定义 */\nexport interface MCPToolParameter {\n name: string;\n description: string;\n type: 'string' | 'number' | 'boolean' | 'object' | 'array';\n required?: boolean;\n}\n\n/** MCP 工具定义 */\nexport interface MCPToolDefinition {\n /** 工具名 */\n name: string;\n /** 工具描述 */\n description: string;\n /** 参数 schema */\n parameters: MCPToolParameter[];\n}\n\n/** MCP 工具调用请求 */\nexport interface MCPToolCallRequest {\n /** 工具名 */\n name: string;\n /** 参数 */\n arguments: Record<string, unknown>;\n}\n\n/** MCP 工具调用结果 */\nexport interface MCPToolCallResult {\n /** 是否错误 */\n isError?: boolean;\n /** 结果内容列表 */\n content: Array<{\n type: 'text' | 'image' | 'resource';\n text?: string;\n data?: string;\n mimeType?: string;\n }>;\n}\n\n// ─── MCPBridge ───────────────────────────────────────────────────\n\n/**\n * MCPBridge:将 AgentGraph 注册为 MCP 工具\n *\n * 用法:\n * ```typescript\n * const bridge = new MCPBridge(graph, { toolPrefix: 'ma_' });\n *\n * // 获取工具列表(供 MCP Server 注册)\n * const tools = bridge.listTools();\n *\n * // 处理工具调用\n * const result = await bridge.handleCall({ name: 'ma_run', arguments: { input: '...' } });\n *\n * // M3:经标准 stdio MCP Server 暴露(补齐传输层,供 Claude Desktop 等拉起)\n * import { runStdioServer } from '@aipack-ai/mcp';\n * await runStdioServer(bridge.toMcpServerHost());\n * ```\n *\n * M3 起,run/status 核心逻辑在 handleCall(legacy)与 asTools(统一路径)间共享,\n * 避免与 packages/mcp 的协议实现重复。\n */\nexport class MCPBridge {\n private graph: AgentGraph;\n private opts: Required<MCPBridgeOpts>;\n\n constructor(graph: AgentGraph, opts?: MCPBridgeOpts) {\n this.graph = graph;\n this.opts = {\n serverName: opts?.serverName ?? 'aipack-multi-agent',\n serverVersion: opts?.serverVersion ?? '1.0.0',\n toolPrefix: opts?.toolPrefix ?? '',\n };\n }\n\n /** 获取 MCP Server 信息 */\n getServerInfo() {\n return {\n name: this.opts.serverName,\n version: this.opts.serverVersion,\n };\n }\n\n /** 列出所有可用 MCP 工具(legacy 形状:MCPToolDefinition[]) */\n listTools(): MCPToolDefinition[] {\n const prefix = this.opts.toolPrefix;\n\n return [\n {\n name: `${prefix}run`,\n description: '运行多Agent编排图,传入用户输入,返回执行结果',\n parameters: [\n {\n name: 'input',\n description: '用户输入文本',\n type: 'string',\n required: true,\n },\n ],\n },\n {\n name: `${prefix}status`,\n description: '获取当前图执行状态',\n parameters: [],\n },\n ];\n }\n\n // ─── 核心逻辑(handleCall 与 asTools 共享,单一来源)──────────────\n\n /** run 工具核心:执行图并序列化为 MCP 形状结果 */\n private async runTool(input: unknown): Promise<MCPToolCallResult> {\n const inputText = input as string | undefined;\n if (!inputText) {\n return {\n isError: true,\n content: [{ type: 'text', text: '缺少必需参数: input' }],\n };\n }\n\n const result = await this.graph.run(inputText);\n return {\n content: [\n {\n type: 'text',\n text: JSON.stringify({\n success: result.success,\n content: result.content,\n lastAgentId: result.lastAgentId,\n stepsCompleted: result.stepsCompleted,\n stopReason: result.stopReason,\n totalUsage: result.totalUsage,\n }, null, 2),\n },\n ],\n };\n }\n\n /** status 工具核心:图执行状态序列化为 MCP 形状结果 */\n private statusTool(): MCPToolCallResult {\n const state = this.graph.getState();\n return {\n content: [\n {\n type: 'text',\n text: JSON.stringify({\n currentAgentId: state.currentAgentId,\n stepsCompleted: state.stepsCompleted,\n finished: state.finished,\n error: state.error,\n nodeStates: Object.fromEntries(state.nodeStates),\n }, null, 2),\n },\n ],\n };\n }\n\n /** 处理 MCP 工具调用(legacy API,行为保持不变) */\n async handleCall(request: MCPToolCallRequest): Promise<MCPToolCallResult> {\n const prefix = this.opts.toolPrefix;\n const runToolName = `${prefix}run`;\n const statusToolName = `${prefix}status`;\n\n try {\n if (request.name === runToolName) {\n return await this.runTool(request.arguments.input);\n }\n if (request.name === statusToolName) {\n return this.statusTool();\n }\n return {\n isError: true,\n content: [{ type: 'text', text: `未知工具: ${request.name}` }],\n };\n } catch (err) {\n return {\n isError: true,\n content: [\n {\n type: 'text',\n text: `执行错误: ${err instanceof Error ? err.message : String(err)}`,\n },\n ],\n };\n }\n }\n\n // ─── M3 统一:暴露为 agent 原生 Tool[],接入 McpServerHost / stdio 传输 ──\n\n /**\n * 将 AgentGraph 暴露为 agent 原生 `Tool[]`(JSON Schema 参数 + execute)。\n * 可直接喂给 `@aipack-ai/mcp` 的 `createMcpServerHost({ tools })`,\n * 再经 `runStdioServer` 拉起为标准 stdio MCP Server——补齐 MCPBridge\n * 原本缺失的传输层(\"由宿主环境负责实际的 MCP 传输\" 这一缺口)。\n *\n * 工具 `${prefix}run` / `${prefix}status` 与 legacy `listTools()`/`handleCall()`\n * 共享 `runTool` / `statusTool` 核心,语义一致。\n */\n asTools(): Tool[] {\n const prefix = this.opts.toolPrefix;\n return [\n {\n name: `${prefix}run`,\n description: '运行多Agent编排图,传入用户输入,返回执行结果',\n parameters: {\n type: 'object',\n properties: { input: { type: 'string', description: '用户输入文本' } },\n required: ['input'],\n },\n permissions: [],\n execute: async (_id: string, args: unknown): Promise<ToolResult> => {\n const input = (args as { input?: string } | null)?.input;\n return toToolResult(await this.runTool(input));\n },\n },\n {\n name: `${prefix}status`,\n description: '获取当前图执行状态',\n parameters: { type: 'object', properties: {} },\n permissions: [],\n execute: async (): Promise<ToolResult> => toToolResult(this.statusTool()),\n },\n ];\n }\n\n /**\n * 构建一个 `McpServerHost`(来自 `@aipack-ai/mcp`),把本 AgentGraph 作为\n * 标准 MCP Server 暴露。配合 `runStdioServer(host)` 即可经 stdin/stdout\n * 服务外部 MCP 客户端(Claude Desktop / Cursor)。\n *\n * 与 legacy `handleCall()` 共享 `runTool` / `statusTool` 核心,保证语义一致。\n */\n toMcpServerHost(): McpServerHost {\n return createMcpServerHost({\n name: this.opts.serverName,\n version: this.opts.serverVersion,\n tools: this.asTools(),\n });\n }\n}\n\n/** MCPToolCallResult → agent ToolResult(isError → details.error,对齐 mcp 包约定) */\nfunction toToolResult(r: MCPToolCallResult): ToolResult {\n const isError = r.isError === true;\n return {\n content: r.content as ContentBlock[],\n details: isError ? { error: r.content[0]?.text ?? 'error' } : undefined,\n };\n}\n\n// ─── createMCPBridge 工厂函数 ────────────────────────────────────\n\n/** 创建 MCPBridge */\nexport function createMCPBridge(graph: AgentGraph, opts?: MCPBridgeOpts): MCPBridge {\n return new MCPBridge(graph, opts);\n}\n\n/**\n * 便捷工厂:从 AgentGraph 直接构建一个 `McpServerHost`(@aipack-ai/mcp),\n * 供 `runStdioServer(host)` 拉起为标准 stdio MCP Server。\n *\n * ```typescript\n * import { runStdioServer } from '@aipack-ai/mcp';\n * const host = createMultiAgentMcpServerHost(graph, { serverName: 'my-graph' });\n * await runStdioServer(host);\n * ```\n */\nexport function createMultiAgentMcpServerHost(graph: AgentGraph, opts?: MCPBridgeOpts): McpServerHost {\n return new MCPBridge(graph, opts).toMcpServerHost();\n}\n","/**\n * extensions/debug.ts - 可视化调试扩展\n *\n * 提供:\n * 1. DOT 格式图结构导出(可用 Graphviz 渲染)\n * 2. 执行 Trace 记录(GraphTrace)\n * 3. 执行过程日志\n */\n\nimport type {\n AgentGraph,\n AgentNode,\n AgentEdge,\n GraphTrace,\n TraceStep,\n MultiAgentEvent,\n NodeExecutionState,\n} from '../core/types';\n\n// ─── GraphDebugger ───────────────────────────────────────────────\n\n/**\n * GraphDebugger:图可视化调试工具\n *\n * 用法:\n * ```typescript\n * const debugger_ = new GraphDebugger(graph);\n *\n * // 导出 DOT 格式\n * const dot = debugger_.toDOT();\n *\n * // 运行并记录 trace\n * const trace = await debugger_.trace('用户输入');\n *\n * // 导出 trace 为 JSON\n * const json = debugger_.traceToJSON(trace);\n * ```\n */\nexport class GraphDebugger {\n private graph: AgentGraph;\n private nodes: Map<string, AgentNode> = new Map();\n private edges: AgentEdge[] = [];\n private entryId?: string;\n\n constructor(graph: AgentGraph, nodes?: AgentNode[], edges?: AgentEdge[], entryId?: string) {\n this.graph = graph;\n if (nodes) {\n for (const node of nodes) {\n this.nodes.set(node.id, node);\n }\n }\n if (edges) {\n this.edges = edges;\n }\n this.entryId = entryId;\n }\n\n /** 设置图元数据(供无法直接访问内部结构的场景使用) */\n setGraphMeta(nodes: AgentNode[], edges: AgentEdge[], entryId?: string): void {\n this.nodes.clear();\n for (const node of nodes) {\n this.nodes.set(node.id, node);\n }\n this.edges = edges;\n this.entryId = entryId;\n }\n\n /** 导出为 DOT 格式 */\n toDOT(): string {\n const lines: string[] = [];\n lines.push('digraph AgentGraph {');\n lines.push(' rankdir=LR;');\n lines.push(' node [shape=box, style=filled, fillcolor=\"#e8f4fd\", fontname=\"Arial\"];');\n lines.push(' edge [fontname=\"Arial\", fontsize=10];');\n lines.push('');\n\n // 节点\n for (const [id, node] of this.nodes) {\n const isEntry = id === this.entryId;\n const fillColor = isEntry ? '#4CAF50' : '#e8f4fd';\n const fontColor = isEntry ? 'white' : 'black';\n const label = `${node.name}\\\\n(${id})`;\n lines.push(` \"${id}\" [label=\"${label}\", fillcolor=\"${fillColor}\", fontcolor=\"${fontColor}\"];`);\n }\n\n lines.push('');\n\n // 边\n for (const edge of this.edges) {\n const hasCondition = !!edge.condition;\n const style = hasCondition ? 'dashed' : 'solid';\n const label = hasCondition ? '条件' : '';\n lines.push(` \"${edge.from}\" -> \"${edge.to}\" [style=${style}, label=\"${label}\"];`);\n }\n\n lines.push('}');\n return lines.join('\\n');\n }\n\n /** 执行图并记录 Trace */\n async trace(input: string): Promise<GraphTrace> {\n const traceId = `trace-${Date.now()}`;\n const graphStartTime = Date.now();\n const steps: TraceStep[] = [];\n let stepIndex = 0;\n\n // 收集事件\n for await (const event of this.graph.stream(input)) {\n if (event.type === 'agent_start') {\n stepIndex++;\n steps.push({\n step: stepIndex,\n agentId: event.agentId,\n agentName: event.agentName,\n startTime: Date.now(),\n duration: 0,\n input: '',\n output: '',\n state: 'running',\n });\n } else if (event.type === 'agent_result') {\n // 找最后一个匹配的 running step(同一 agent 可能执行多次)\n const step = this.findLastRunning(steps, event.agentId);\n if (step) {\n step.duration = Date.now() - step.startTime;\n step.output = this.truncate(event.result.content, 200);\n step.state = 'completed';\n } else {\n // 如果找不到 running step,回退到找最后一个同 agentId 的 step\n const fallback = this.findLastById(steps, event.agentId);\n if (fallback) {\n fallback.duration = Date.now() - fallback.startTime;\n fallback.output = this.truncate(event.result.content, 200);\n fallback.state = 'completed';\n }\n }\n } else if (event.type === 'agent_error') {\n const step = this.findLastRunning(steps, event.agentId);\n if (step) {\n step.duration = Date.now() - step.startTime;\n step.error = event.error;\n step.state = 'failed';\n }\n }\n }\n\n // 获取最终结果\n const state = this.graph.getState();\n const graphDuration = Date.now() - graphStartTime;\n\n return {\n traceId,\n startTime: graphStartTime,\n duration: graphDuration,\n steps,\n result: {\n success: !state.error,\n content: state.error ?? '',\n stopReason: state.error ? 'error' : 'completed',\n stepsCompleted: state.stepsCompleted,\n },\n };\n }\n\n /** 将 Trace 转为 JSON 字符串 */\n traceToJSON(trace: GraphTrace): string {\n return JSON.stringify(trace, null, 2);\n }\n\n /** 将 Trace 转为可读的执行日志 */\n traceToLog(trace: GraphTrace): string {\n const lines: string[] = [];\n lines.push(`=== Graph Trace: ${trace.traceId} ===`);\n lines.push(`Duration: ${trace.duration}ms`);\n lines.push('');\n\n for (const step of trace.steps) {\n const status = step.state === 'completed' ? 'OK' : step.state === 'failed' ? 'FAIL' : step.state;\n lines.push(`[${step.step}] ${step.agentName} (${step.agentId}) - ${status} (${step.duration}ms)`);\n if (step.input) lines.push(` Input: ${this.truncate(step.input, 100)}`);\n if (step.output) lines.push(` Output: ${this.truncate(step.output, 100)}`);\n if (step.error) lines.push(` Error: ${step.error}`);\n lines.push('');\n }\n\n lines.push(`Result: ${trace.result.success ? 'SUCCESS' : 'FAILED'} (${trace.result.stopReason})`);\n return lines.join('\\n');\n }\n\n private truncate(text: string, maxLength: number): string {\n if (text.length <= maxLength) return text;\n return text.slice(0, maxLength) + '...';\n }\n\n /** 找最后一个匹配 agentId 且状态为 running 的 step */\n private findLastRunning(steps: TraceStep[], agentId: string): TraceStep | undefined {\n for (let i = steps.length - 1; i >= 0; i--) {\n if (steps[i].agentId === agentId && steps[i].state === 'running') {\n return steps[i];\n }\n }\n return undefined;\n }\n\n /** 找最后一个匹配 agentId 的 step(不管状态) */\n private findLastById(steps: TraceStep[], agentId: string): TraceStep | undefined {\n for (let i = steps.length - 1; i >= 0; i--) {\n if (steps[i].agentId === agentId) {\n return steps[i];\n }\n }\n return undefined;\n }\n}\n\n// ─── createDebugger 工厂函数 ─────────────────────────────────────\n\n/** 创建 GraphDebugger */\nexport function createDebugger(graph: AgentGraph): GraphDebugger {\n return new GraphDebugger(graph);\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../core/context.ts","../../agent/core/types.ts","../../agent/core/tapable.ts","../../agent/core/request.ts","../../agent/core/context-resource.ts","../../agent/core/task-graph.ts","../../agent/core/extension.ts","../../agent/core/result.ts","../../agent/core/session.ts","../../agent/request/index.ts","../../agent/context-resource/index.ts","../../agent/ai/index.ts","../../agent/ai/errors.ts","../../agent/ai/overflow.ts","../../agent/transformer/index.ts","../../agent/runtime/index.ts","../core/event-stream.ts","../core/executor.ts","../core/graph.ts","../patterns/pipeline.ts","../patterns/router.ts","../core/supervisor-executor.ts","../patterns/supervisor.ts","../core/debate-executor.ts","../patterns/debate.ts","../core/map-reduce-executor.ts","../patterns/map-reduce.ts","../../mcp/src/client/jsonrpc.ts","../../mcp/src/client/protocol.ts","../../mcp/src/server/host.ts","../extensions/mcp-bridge.ts","../extensions/debug.ts"],"sourcesContent":["/**\n * core/context.ts - SharedContext 实现\n *\n * 提供 EventBus、ToolRegistry 和 SharedContext 的默认实现。\n */\n\nimport type { Tool, Request } from '@aipack-ai/agent';\nimport type { EventBus, ToolRegistry, SharedContext, EventListener } from './types';\n\n// ─── SimpleEventBus ──────────────────────────────────────────────\n\n/** 简单同步事件总线实现 */\nexport class SimpleEventBus implements EventBus {\n private listeners = new Map<string, Set<EventListener>>();\n\n on(event: string, listener: EventListener): this {\n let set = this.listeners.get(event);\n if (!set) {\n set = new Set();\n this.listeners.set(event, set);\n }\n set.add(listener);\n return this;\n }\n\n off(event: string, listener: EventListener): this {\n this.listeners.get(event)?.delete(listener);\n return this;\n }\n\n emit(event: string, data?: unknown): this {\n const set = this.listeners.get(event);\n if (set) {\n for (const listener of set) {\n try {\n listener(data);\n } catch {\n // 防止监听器异常中断事件传播\n }\n }\n }\n return this;\n }\n}\n\n// ─── SimpleToolRegistry ─────────────────────────────────────────\n\n/** 简单工具注册表实现 */\nexport class SimpleToolRegistry implements ToolRegistry {\n private tools = new Map<string, Tool>();\n\n register(tool: Tool): this {\n this.tools.set(tool.name, tool);\n return this;\n }\n\n registerAll(tools: Tool[]): this {\n for (const tool of tools) {\n this.tools.set(tool.name, tool);\n }\n return this;\n }\n\n get(name: string): Tool | undefined {\n return this.tools.get(name);\n }\n\n getAll(): Tool[] {\n return Array.from(this.tools.values());\n }\n\n has(name: string): boolean {\n return this.tools.has(name);\n }\n}\n\n// ─── createSharedContext ────────────────────────────────────────\n\n/** 创建默认 SharedContext */\nexport function createSharedContext(init?: Partial<SharedContext>): SharedContext {\n return {\n blackboard: init?.blackboard ?? new Map(),\n bus: init?.bus ?? new SimpleEventBus(),\n toolRegistry: init?.toolRegistry ?? new SimpleToolRegistry(),\n meta: init?.meta ?? {},\n };\n}\n\n// ─── storeOriginalInput: 统一写入原始输入 ──────────────────────\n\n/**\n * 将原始用户输入写入 blackboard['__original_input__']。\n * 所有执行器(Graph/Supervisor/Debate/MapReduce)在 run/stream 入口统一调用,\n * 保证 Router 等模式的 passOriginalInput 语义可用。\n */\nexport function storeOriginalInput(ctx: SharedContext, input: string | Request): void {\n const inputText = typeof input === 'string' ? input : input.message;\n ctx.blackboard.set('__original_input__', inputText);\n}\n","/**\n * packages/core/types.ts - 核心类型定义\n *\n * 这是整个框架的类型基础,不依赖任何外部实现。\n * 所有消息、内容块、模型、工具等类型都在此定义。\n */\n\n// ─── 内容块类型 ───────────────────────────────────────────────────\n\nexport interface TextContent {\n type: 'text';\n text: string;\n}\n\nexport interface ImageContent {\n type: 'image';\n data: string; // base64 或 URL\n mimeType: string;\n}\n\nexport interface ToolCallContent {\n type: 'toolCall';\n id: string;\n name: string;\n arguments: unknown;\n}\n\nexport interface ThinkingContent {\n type: 'thinking';\n text: string;\n}\n\nexport type ContentBlock =\n | TextContent\n | ImageContent\n | ToolCallContent\n | ThinkingContent;\n\n// ─── 消息类型 ─────────────────────────────────────────────────────\n\nexport interface BaseMessage {\n role: string;\n content: string | ContentBlock[];\n timestamp: number;\n [key: string]: unknown;\n}\n\nexport interface UserMessage extends BaseMessage {\n role: 'user';\n}\n\nexport interface AssistantMessage extends BaseMessage {\n role: 'assistant';\n model?: string;\n provider?: string;\n stopReason?: string;\n usage?: Usage;\n errorMessage?: string;\n responseId?: string;\n}\n\nexport interface ToolResultMessage extends BaseMessage {\n role: 'toolResult';\n toolCallId: string;\n toolName: string;\n isError: boolean;\n}\n\nexport interface SystemMessage extends BaseMessage {\n role: 'system';\n}\n\nexport type Message = UserMessage | AssistantMessage | ToolResultMessage | SystemMessage;\n\n// ─── Token 用量 ───────────────────────────────────────────────────\n\n/**\n * 用量与费用。与 aipack/ai 的 Usage 结构对齐:\n * cacheRead/cacheWrite/reasoning 为可选字段,旧消费者无需感知。\n */\nexport interface Usage {\n input: number;\n output: number;\n total: number;\n /** 命中缓存读取的 token 数(不计入 input) */\n cacheRead?: number;\n /** 写入缓存的 token 数 */\n cacheWrite?: number;\n /** 推理 token 数(completion 的子集) */\n reasoning?: number;\n /** 还原后的原始 token 总数(input + output + cacheRead + cacheWrite) */\n totalTokens?: number;\n}\n\n// ─── 模型定义 ─────────────────────────────────────────────────────\n\nexport interface Model {\n id: string;\n name: string;\n provider: string;\n contextWindow: number;\n maxTokens: number;\n reasoning: boolean;\n [key: string]: unknown;\n}\n\n// ─── 工具定义 ─────────────────────────────────────────────────────\n\nexport interface ToolResult {\n content: ContentBlock[];\n details: unknown;\n usage?: Usage;\n}\n\nexport interface Tool {\n name: string;\n description: string;\n parameters: unknown; // JSON Schema 或 TypeBox schema\n /**\n * 所需权限能力声明(如 'shell:exec' / 'fs:write' / 'memory:write' / 'network:fetch')。\n * 供框架级 PermissionPolicy 裁决使用;未声明视为安全工具。\n */\n permissions?: string[];\n execute: (\n toolCallId: string,\n args: unknown,\n signal?: AbortSignal,\n ) => Promise<ToolResult>;\n prepareArguments?: (args: unknown) => unknown;\n}\n\n// ─── 上下文 ───────────────────────────────────────────────────────\n\nexport interface Context {\n systemPrompt: string;\n messages: Message[];\n tools?: Tool[];\n}\n\n// ─── 流式事件 ─────────────────────────────────────────────────────\n\nexport interface StreamOptions {\n signal?: AbortSignal;\n reasoning?: string;\n sessionId?: string;\n /** 重试回调:provider 内 retry() 真正退避重试时调用(可观测/埋点用) */\n onRetryAttempt?: (info: { attempt: number; error: unknown; delayMs: number }) => void;\n}\n\nexport type StreamEvent =\n | { type: 'start'; partial: { content: ContentBlock[] } }\n | { type: 'text_delta'; delta: string }\n | { type: 'thinking_delta'; delta: string }\n | { type: 'tool_call_start'; id: string; name: string }\n | { type: 'tool_call_delta'; id: string; delta: string }\n | { type: 'tool_call_end'; id: string }\n | { type: 'done'; message: AssistantMessage }\n | { type: 'error'; message: AssistantMessage };\n\nexport type StreamResult = AsyncIterable<StreamEvent>;\n\n/**\n * 流式函数类型 - 模型提供者需实现此接口\n *\n * 是一个可替换的核心能力。\n * 用户通过提供不同的 streamFn 来接入不同的 LLM 提供商。\n */\nexport type StreamFn = (\n model: Model,\n context: Context,\n options?: StreamOptions,\n) => StreamResult;\n\n// ─── Agent 状态 ───────────────────────────────────────────────────\n\nexport type ThinkingLevel = 'off' | 'minimal' | 'low' | 'medium' | 'high' | 'max';\n\nexport interface AgentState {\n systemPrompt: string;\n model: Model;\n thinkingLevel: ThinkingLevel;\n tools: Tool[];\n messages: Message[];\n isStreaming: boolean;\n streamingMessage?: Message;\n pendingToolCalls: Set<string>;\n errorMessage?: string;\n}\n\n// ─── 工具函数 ─────────────────────────────────────────────────────\n\nexport function extractText(content: string | ContentBlock[]): string {\n if (typeof content === 'string') return content;\n return content\n .filter((c): c is TextContent => c.type === 'text')\n .map(c => c.text)\n .join('');\n}\n\nexport function extractToolCalls(content: string | ContentBlock[]): ToolCallContent[] {\n if (typeof content === 'string') return [];\n return content.filter((c): c is ToolCallContent => c.type === 'toolCall');\n}\n\nexport function createTextContent(text: string): TextContent {\n return { type: 'text', text };\n}\n\nexport function createEmptyUsage(): Usage {\n return { input: 0, output: 0, total: 0 };\n}\n","/**\n * Tapable - 事件钩子系统\n *\n * 提供同步与异步钩子,允许 Extension 在 Runtime 生命周期的关键节点注入逻辑。\n */\n\n// ─── 钩子类型 ─────────────────────────────────────────────────────\n\nexport type TapType = 'sync' | 'async' | 'promise';\n\nexport interface Tap {\n /** 钩子名称(用于调试与去重) */\n name: string;\n /** 钩子类型 */\n type: TapType;\n /** 回调函数 */\n fn: (...args: any[]) => any;\n /** 执行阶段:before / during / after */\n stage?: number;\n}\n\n// ─── SyncHook ─────────────────────────────────────────────────────\n\nexport class SyncHook<TArgs extends any[] = any[]> {\n private taps: Tap[] = [];\n\n constructor(private readonly name: string) {}\n\n tap(name: string, fn: (...args: TArgs) => void, stage?: number): void {\n this.taps.push({ name, type: 'sync', fn, stage: stage ?? 0 });\n this.taps.sort((a, b) => (a.stage ?? 0) - (b.stage ?? 0));\n }\n\n call(...args: TArgs): void {\n for (const tap of this.taps) {\n try {\n tap.fn(...args);\n } catch (err) {\n // 单个 tap 失败不影响其他 tap\n }\n }\n }\n\n isUsed(): boolean {\n return this.taps.length > 0;\n }\n\n clear(): void {\n this.taps = [];\n }\n}\n\n// ─── AsyncSeriesHook ──────────────────────────────────────────────\n\nexport class AsyncSeriesHook<TArgs extends any[] = any[]> {\n private taps: Tap[] = [];\n\n constructor(private readonly name: string) {}\n\n tapPromise(name: string, fn: (...args: TArgs) => Promise<void>, stage?: number): void {\n this.taps.push({ name, type: 'promise', fn, stage: stage ?? 0 });\n this.taps.sort((a, b) => (a.stage ?? 0) - (b.stage ?? 0));\n }\n\n async promise(...args: TArgs): Promise<void> {\n for (const tap of this.taps) {\n try {\n await tap.fn(...args);\n } catch (err) {\n // 单个 tap 失败不影响其他 tap\n }\n }\n }\n\n isUsed(): boolean {\n return this.taps.length > 0;\n }\n\n clear(): void {\n this.taps = [];\n }\n}\n\n// ─── AsyncSeriesWaterfallHook ─────────────────────────────────────\n\nexport class AsyncSeriesWaterfallHook<T = any> {\n private taps: Tap[] = [];\n\n constructor(private readonly name: string) {}\n\n tapPromise(name: string, fn: (value: T, ...rest: any[]) => Promise<T>, stage?: number): void {\n this.taps.push({ name, type: 'promise', fn, stage: stage ?? 0 });\n this.taps.sort((a, b) => (a.stage ?? 0) - (b.stage ?? 0));\n }\n\n async promise(value: T, ...rest: any[]): Promise<T> {\n let current = value;\n for (const tap of this.taps) {\n try {\n current = await tap.fn(current, ...rest);\n } catch (err) {\n // 失败时保持当前值不变\n }\n }\n return current;\n }\n\n isUsed(): boolean {\n return this.taps.length > 0;\n }\n\n clear(): void {\n this.taps = [];\n }\n}\n\n// ─── HookMap ──────────────────────────────────────────────────────\n\nexport class HookMap<THook> {\n private map = new Map<string, THook>();\n\n constructor(private readonly factory: () => THook) {}\n\n for(key: string): THook {\n let hook = this.map.get(key);\n if (!hook) {\n hook = this.factory();\n this.map.set(key, hook);\n }\n return hook;\n }\n\n has(key: string): boolean {\n return this.map.has(key);\n }\n\n get(key: string): THook | undefined {\n return this.map.get(key);\n }\n\n keys(): string[] {\n return Array.from(this.map.keys());\n }\n}\n","/**\n * Request - 请求入口\n *\n * 代表一次 Agent 运行的入口请求,包含用户输入、会话标识与运行选项。\n */\n\n// ─── 请求类型 ─────────────────────────────────────────────────────\n\nexport type RequestType = 'message' | 'stream' | 'continue' | 'replay';\n\n// ─── 请求接口 ─────────────────────────────────────────────────────\n\nexport interface Request {\n /** 用户输入消息 */\n readonly message: string;\n /** 请求类型 */\n readonly type: RequestType;\n /** 通道标识 */\n readonly channel?: string;\n /** 聊天 ID */\n readonly chatId?: string;\n /** 发送者 ID */\n readonly senderId?: string;\n /**\n * 会话标识。同一 Runtime 可服务多个会话(SessionManager / 多租户):\n * 未指定时回退到 Runtime 的默认会话 key(createRuntime 的 sessionKey)。\n * 不同 sessionKey 的请求消息历史相互隔离、串行队列独立。\n */\n readonly sessionKey?: string;\n /** 媒体附件 */\n readonly media?: string[];\n /** 是否临时会话(不持久化) */\n readonly ephemeral?: boolean;\n /** 指定模型 */\n readonly model?: string;\n /** 指定模型预设 */\n readonly modelPreset?: string;\n /** 额外元数据 */\n readonly metadata?: Record<string, unknown>;\n}\n\n// ─── 请求构建器 ───────────────────────────────────────────────────\n\nexport class RequestBuilder {\n private _message: string = '';\n private _type: RequestType = 'message';\n private _channel?: string;\n private _chatId?: string;\n private _senderId?: string;\n private _media?: string[];\n private _ephemeral?: boolean;\n private _model?: string;\n private _modelPreset?: string;\n private _sessionKey?: string;\n private _metadata: Record<string, unknown> = {};\n\n message(msg: string): this {\n this._message = msg;\n return this;\n }\n\n type(t: RequestType): this {\n this._type = t;\n return this;\n }\n\n channel(ch: string): this {\n this._channel = ch;\n return this;\n }\n\n chatId(id: string): this {\n this._chatId = id;\n return this;\n }\n\n senderId(id: string): this {\n this._senderId = id;\n return this;\n }\n\n media(m: string[]): this {\n this._media = m;\n return this;\n }\n\n ephemeral(e: boolean): this {\n this._ephemeral = e;\n return this;\n }\n\n model(m: string): this {\n this._model = m;\n return this;\n }\n\n modelPreset(p: string): this {\n this._modelPreset = p;\n return this;\n }\n\n metadata(key: string, value: unknown): this {\n this._metadata[key] = value;\n return this;\n }\n\n /** 指定会话 key(多会话运行时按此路由到对应会话) */\n sessionKey(key: string): this {\n this._sessionKey = key;\n return this;\n }\n\n build(): Request {\n return {\n message: this._message,\n type: this._type,\n channel: this._channel,\n chatId: this._chatId,\n senderId: this._senderId,\n sessionKey: this._sessionKey,\n media: this._media,\n ephemeral: this._ephemeral,\n model: this._model,\n modelPreset: this._modelPreset,\n metadata: this._metadata,\n };\n }\n}\n\nexport function createRequest(message: string, options?: Partial<Request>): Request {\n return {\n message,\n type: 'message',\n ...options,\n };\n}\n","/**\n * ContextResource - 上下文资源\n *\n * 代表上下文中的单个资源单元(消息、工具调用、工具结果、状态快照等)。\n * 每个 Resource 拥有唯一标识,并可声明对其他 Resource 的依赖。\n */\n\n// ─── 资源类型 ─────────────────────────────────────────────────────\n\nexport type ResourceType =\n | 'user_message'\n | 'assistant_message'\n | 'tool_call'\n | 'tool_result'\n | 'system_message'\n | 'state_snapshot'\n | 'compaction_summary'\n | 'custom';\n\nexport type ResourceRole = 'user' | 'assistant' | 'toolResult' | 'system' | string;\n\n// ─── 资源接口 ─────────────────────────────────────────────────────\n\nexport interface ContextResource {\n /** 唯一标识 */\n readonly id: string;\n /** 资源类型 */\n readonly type: ResourceType;\n /** 消息角色 */\n readonly role: ResourceRole;\n /** 资源内容(消息体或工具数据) */\n readonly content: unknown;\n /** 时间戳 */\n readonly timestamp: number;\n /** 依赖的其他资源 ID(如 tool_result 依赖 tool_call) */\n readonly dependencies: string[];\n /** 资源元数据 */\n readonly meta: Record<string, unknown>;\n /** 是否为关键资源(压缩时不可移除) */\n readonly pinned: boolean;\n}\n\n// ─── 资源构建器 ───────────────────────────────────────────────────\n\nexport class ContextResourceBuilder {\n private _id: string;\n private _type: ResourceType = 'custom';\n private _role: ResourceRole = 'user';\n private _content: unknown = '';\n private _timestamp: number = Date.now();\n private _dependencies: string[] = [];\n private _meta: Record<string, unknown> = {};\n private _pinned: boolean = false;\n\n constructor(id?: string) {\n this._id = id || `res_${Date.now()}_${Math.random().toString(36).slice(2, 8)}`;\n }\n\n id(id: string): this {\n this._id = id;\n return this;\n }\n\n type(t: ResourceType): this {\n this._type = t;\n return this;\n }\n\n role(r: ResourceRole): this {\n this._role = r;\n return this;\n }\n\n content(c: unknown): this {\n this._content = c;\n return this;\n }\n\n timestamp(ts: number): this {\n this._timestamp = ts;\n return this;\n }\n\n dependsOn(...ids: string[]): this {\n this._dependencies.push(...ids);\n return this;\n }\n\n meta(key: string, value: unknown): this {\n this._meta[key] = value;\n return this;\n }\n\n pinned(p: boolean = true): this {\n this._pinned = p;\n return this;\n }\n\n build(): ContextResource {\n return {\n id: this._id,\n type: this._type,\n role: this._role,\n content: this._content,\n timestamp: this._timestamp,\n dependencies: this._dependencies,\n meta: this._meta,\n pinned: this._pinned,\n };\n }\n}\n\n// ─── 工厂函数 ─────────────────────────────────────────────────────\n\nexport function createMessageResource(\n role: ResourceRole,\n content: unknown,\n options?: Partial<ContextResource>,\n): ContextResource {\n const type: ResourceType =\n role === 'user' ? 'user_message'\n : role === 'assistant' ? 'assistant_message'\n : role === 'system' ? 'system_message'\n : 'custom';\n\n return new ContextResourceBuilder()\n .type(type)\n .role(role)\n .content(content)\n .timestamp(options?.timestamp ?? Date.now())\n .build();\n}\n\nexport function createToolCallResource(\n toolCallId: string,\n toolName: string,\n args: unknown,\n options?: Partial<ContextResource>,\n): ContextResource {\n return new ContextResourceBuilder()\n .id(toolCallId)\n .type('tool_call')\n .role('assistant')\n .content({ toolName, args })\n .meta('toolName', toolName)\n .meta('toolCallId', toolCallId)\n .timestamp(options?.timestamp ?? Date.now())\n .build();\n}\n\nexport function createToolResultResource(\n toolCallId: string,\n toolName: string,\n result: unknown,\n isError: boolean,\n dependsOn: string,\n options?: Partial<ContextResource>,\n): ContextResource {\n return new ContextResourceBuilder()\n .id(`${toolCallId}_result`)\n .type('tool_result')\n .role('toolResult')\n .content(result)\n .dependsOn(dependsOn)\n .meta('toolName', toolName)\n .meta('toolCallId', toolCallId)\n .meta('isError', isError)\n .timestamp(options?.timestamp ?? Date.now())\n .build();\n}\n","/**\n * TaskGraph - 任务依赖图\n *\n * 管理所有 ContextResource 之间的依赖关系,支持拓扑排序与可达性分析。\n * Runtime 在每次编译时会构建 TaskGraph,Transformer 基于图结构操作资源。\n */\n\nimport type { ContextResource, ResourceType } from './context-resource';\n\n// ─── 图节点 ───────────────────────────────────────────────────────\n\nexport interface GraphNode {\n resource: ContextResource;\n dependents: Set<string>; // 依赖此节点的节点\n dependencies: Set<string>; // 此节点依赖的节点\n}\n\n// ─── TaskGraph 接口 ───────────────────────────────────────────────\n\nexport interface TaskGraph {\n /** 添加资源到图中 */\n add(resource: ContextResource): void;\n /** 批量添加资源 */\n addAll(resources: ContextResource[]): void;\n /** 获取指定 ID 的资源 */\n resolve(id: string): ContextResource | undefined;\n /** 获取指定 ID 的节点 */\n getNode(id: string): GraphNode | undefined;\n /** 移除资源(同时清理依赖关系) */\n remove(id: string): boolean;\n /** 获取所有资源 */\n getAll(): ContextResource[];\n /** 按类型过滤资源 */\n getByType(type: ResourceType): ContextResource[];\n /** 拓扑排序 */\n topologicalSort(): ContextResource[];\n /** 检查从 from 到 to 是否可达 */\n isReachable(from: string, to: string): boolean;\n /** 获取所有叶子节点(无依赖的节点) */\n getLeaves(): ContextResource[];\n /** 获取根节点(无被依赖的节点) */\n getRoots(): ContextResource[];\n /** 获取图的大小 */\n readonly size: number;\n /** 清空图 */\n clear(): void;\n}\n\n// ─── TaskGraph 实现 ───────────────────────────────────────────────\n\nexport class TaskGraphImpl implements TaskGraph {\n private nodes = new Map<string, GraphNode>();\n private _size = 0;\n\n get size(): number {\n return this._size;\n }\n\n add(resource: ContextResource): void {\n // 如果已存在,先移除旧节点\n if (this.nodes.has(resource.id)) {\n this.remove(resource.id);\n }\n\n const node: GraphNode = {\n resource,\n dependents: new Set(),\n dependencies: new Set(),\n };\n\n // 建立依赖关系\n for (const depId of resource.dependencies) {\n node.dependencies.add(depId);\n const depNode = this.nodes.get(depId);\n if (depNode) {\n depNode.dependents.add(resource.id);\n }\n }\n\n this.nodes.set(resource.id, node);\n this._size++;\n }\n\n addAll(resources: ContextResource[]): void {\n // 先添加所有节点(不带依赖),再补充依赖关系\n for (const res of resources) {\n if (!this.nodes.has(res.id)) {\n this.nodes.set(res.id, {\n resource: res,\n dependents: new Set(),\n dependencies: new Set(),\n });\n this._size++;\n }\n }\n // 补充依赖关系\n for (const res of resources) {\n const node = this.nodes.get(res.id)!;\n for (const depId of res.dependencies) {\n node.dependencies.add(depId);\n const depNode = this.nodes.get(depId);\n if (depNode) {\n depNode.dependents.add(res.id);\n }\n }\n }\n }\n\n resolve(id: string): ContextResource | undefined {\n return this.nodes.get(id)?.resource;\n }\n\n getNode(id: string): GraphNode | undefined {\n return this.nodes.get(id);\n }\n\n remove(id: string): boolean {\n const node = this.nodes.get(id);\n if (!node) return false;\n\n // 清理依赖关系\n for (const depId of node.dependencies) {\n const depNode = this.nodes.get(depId);\n depNode?.dependents.delete(id);\n }\n for (const dependentId of node.dependents) {\n const dependentNode = this.nodes.get(dependentId);\n dependentNode?.dependencies.delete(id);\n }\n\n this.nodes.delete(id);\n this._size--;\n return true;\n }\n\n getAll(): ContextResource[] {\n return Array.from(this.nodes.values()).map(n => n.resource);\n }\n\n getByType(type: ResourceType): ContextResource[] {\n return this.getAll().filter(r => r.type === type);\n }\n\n topologicalSort(): ContextResource[] {\n const result: ContextResource[] = [];\n const visited = new Set<string>();\n const visiting = new Set<string>();\n\n const visit = (id: string): void => {\n if (visited.has(id)) return;\n if (visiting.has(id)) return; // 环检测:跳过\n\n visiting.add(id);\n const node = this.nodes.get(id);\n if (node) {\n for (const depId of node.dependencies) {\n visit(depId);\n }\n result.push(node.resource);\n }\n visiting.delete(id);\n visited.add(id);\n };\n\n for (const id of this.nodes.keys()) {\n visit(id);\n }\n\n return result;\n }\n\n isReachable(from: string, to: string): boolean {\n if (from === to) return true;\n const visited = new Set<string>();\n const queue = [from];\n\n while (queue.length > 0) {\n const current = queue.shift()!;\n if (visited.has(current)) continue;\n visited.add(current);\n\n const node = this.nodes.get(current);\n if (!node) continue;\n\n for (const depId of node.dependencies) {\n if (depId === to) return true;\n if (!visited.has(depId)) {\n queue.push(depId);\n }\n }\n }\n\n return false;\n }\n\n getLeaves(): ContextResource[] {\n return Array.from(this.nodes.values())\n .filter(n => n.dependencies.size === 0)\n .map(n => n.resource);\n }\n\n getRoots(): ContextResource[] {\n return Array.from(this.nodes.values())\n .filter(n => n.dependents.size === 0)\n .map(n => n.resource);\n }\n\n clear(): void {\n this.nodes.clear();\n this._size = 0;\n }\n}\n\n// ─── 图构建器 ─────────────────────────────────────────────────────\n\nexport class TaskGraphBuilder {\n private resources: ContextResource[] = [];\n\n add(resource: ContextResource): this {\n this.resources.push(resource);\n return this;\n }\n\n addAll(resources: ContextResource[]): this {\n this.resources.push(...resources);\n return this;\n }\n\n build(): TaskGraph {\n const graph = new TaskGraphImpl();\n graph.addAll(this.resources);\n return graph;\n }\n}\n\nexport function createTaskGraph(): TaskGraph {\n return new TaskGraphImpl();\n}\n","/**\n * Extension - 扩展插件系统\n *\n * Extension 通过 Tapable 钩子在 Runtime 生命周期的关键节点注入逻辑,\n * 无需修改 Runtime 核心,实现开闭原则。\n */\n\nimport { AsyncSeriesHook, AsyncSeriesWaterfallHook } from './tapable';\nimport type { Request } from './request';\nimport type { Result } from './result';\nimport type { Context } from './types';\nimport type { ContextResource } from './context-resource';\nimport type { BeforeToolCallDecision, AfterToolCallDecision } from './tool-hooks';\nimport type { Runtime } from './runtime';\n\n// ─── Runtime 钩子集合 ─────────────────────────────────────────────\n\nexport interface RuntimeHooks {\n /** Runtime 初始化前 */\n beforeInitialize: AsyncSeriesHook<[Request]>;\n /** Runtime 初始化后 */\n afterInitialize: AsyncSeriesHook<[Request]>;\n /** 请求处理前(可修改请求) */\n beforeRun: AsyncSeriesWaterfallHook<Request>;\n /** 资源构建后、转换前(可修改资源) */\n beforeTransform: AsyncSeriesWaterfallHook<ContextResource[]>;\n /**\n * 资源转换后、模型调用前(可修改资源)\n */\n afterTransform: AsyncSeriesWaterfallHook<ContextResource[]>;\n /**\n * 模型调用前(waterfall,可修改最终发给模型的 Context:\n * systemPrompt / messages / tools)。\n * 典型用途:插件注入 system prompt 片段或动态附加工具(如 skills 目录注入)。\n * 每次模型调用触发一次;systemPrompt 以 Runtime 持有的基准值为起点,改动不累积。\n */\n beforeModelCall: AsyncSeriesWaterfallHook<Context>;\n /** 模型调用后、结果构建前 */\n beforeEmit: AsyncSeriesHook<[Result]>;\n /** 结果构建后 */\n afterEmit: AsyncSeriesHook<[Result]>;\n /**\n * 运行结束。\n * 第二参数为最终 Request(可选,向后兼容)。\n * 单会话模式下会话标识由 Runtime 持有;多会话场景请创建独立 Runtime 实例。\n */\n done: AsyncSeriesHook<[Result, Request?]>;\n /** 运行失败 */\n failed: AsyncSeriesHook<[Error, Request]>;\n /**\n * 工具执行前(参数校验后)。流转 BeforeToolCallDecision:\n * 任一 tap 设 block 则该工具不执行(生成拒绝结果);\n * 设 terminate 则终止整个 run(本轮工具结束后停止 runLoop);\n * 可改写 args。第二参数为 ToolCallContext。\n */\n beforeToolCall: AsyncSeriesWaterfallHook<BeforeToolCallDecision>;\n /**\n * 工具执行后、最终事件发出前。流转 AfterToolCallDecision:\n * 可改写 result(waterfall),设 terminate 终止整个 run。\n * 第二参数为 ToolCallContext。\n */\n afterToolCall: AsyncSeriesWaterfallHook<AfterToolCallDecision>;\n}\n\n// ─── Extension 接口 ───────────────────────────────────────────────\n\nexport interface Extension {\n /** 扩展名称 */\n readonly name: string;\n /**\n * 应用扩展到 Runtime\n * 通过 hooks.tap 注册回调\n */\n apply(hooks: RuntimeHooks, context: ExtensionContext): void;\n}\n\n// ─── 扩展上下文 ───────────────────────────────────────────────────\n\nexport interface ExtensionContext {\n /** Runtime 配置 */\n readonly config: Record<string, unknown>;\n /** 工作区路径 */\n readonly workspace: string;\n /** 会话标识 */\n readonly sessionKey: string;\n /** 共享状态(Extension 间通信) */\n readonly shared: Map<string, unknown>;\n /**\n * 所属 Runtime 引用(可选)。\n * 供插件在 apply 阶段注册工具等(如 SkillsExtension 注册内置 skill 工具)。\n * 由 AgentRuntime.create 注入;自建 ExtensionContext 时可缺省。\n */\n readonly runtime?: Runtime;\n}\n\n// ─── Extension 管理器 ─────────────────────────────────────────────\n\nexport class ExtensionManager {\n private extensions: Extension[] = [];\n private hooks: RuntimeHooks;\n\n constructor() {\n this.hooks = this.createHooks();\n }\n\n private createHooks(): RuntimeHooks {\n return {\n beforeInitialize: new AsyncSeriesHook('beforeInitialize'),\n afterInitialize: new AsyncSeriesHook('afterInitialize'),\n beforeRun: new AsyncSeriesWaterfallHook('beforeRun'),\n beforeTransform: new AsyncSeriesWaterfallHook('beforeTransform'),\n afterTransform: new AsyncSeriesWaterfallHook('afterTransform'),\n beforeModelCall: new AsyncSeriesWaterfallHook('beforeModelCall'),\n beforeEmit: new AsyncSeriesHook('beforeEmit'),\n afterEmit: new AsyncSeriesHook('afterEmit'),\n done: new AsyncSeriesHook('done'),\n failed: new AsyncSeriesHook('failed'),\n beforeToolCall: new AsyncSeriesWaterfallHook('beforeToolCall'),\n afterToolCall: new AsyncSeriesWaterfallHook('afterToolCall'),\n };\n }\n\n /** 注册扩展 */\n register(extension: Extension): this {\n this.extensions.push(extension);\n return this;\n }\n\n /** 批量注册扩展 */\n registerAll(extensions: Extension[]): this {\n for (const ext of extensions) {\n this.register(ext);\n }\n return this;\n }\n\n /** 应用所有扩展到钩子 */\n applyAll(context: ExtensionContext): void {\n for (const ext of this.extensions) {\n try {\n ext.apply(this.hooks, context);\n } catch (err) {\n // 单个 Extension 失败不影响其他 Extension,但需可观测\n console.warn(`[Extension] \"${ext.name}\" apply 失败:`, (err as Error)?.message ?? err);\n }\n }\n }\n\n /** 获取钩子集合 */\n getHooks(): RuntimeHooks {\n return this.hooks;\n }\n\n /** 移除扩展 */\n unregister(name: string): boolean {\n const idx = this.extensions.findIndex(e => e.name === name);\n if (idx === -1) return false;\n this.extensions.splice(idx, 1);\n return true;\n }\n\n /** 获取所有已注册的扩展 */\n getExtensions(): Extension[] {\n return [...this.extensions];\n }\n\n /** 清空所有扩展 */\n clear(): void {\n this.extensions = [];\n }\n}\n\n// ─── 抽象基类 ─────────────────────────────────────────────────────\n\nexport abstract class BaseExtension implements Extension {\n abstract readonly name: string;\n\n apply(hooks: RuntimeHooks, context: ExtensionContext): void {\n this.setup(hooks, context);\n }\n\n protected abstract setup(hooks: RuntimeHooks, context: ExtensionContext): void;\n}\n","/**\n * Result - 运行结果\n *\n * Result 代表 Agent 一次运行的最终产物,\n * 包含输出内容、使用的工具、元数据、以及资源快照。\n */\n\nimport type { ContextResource } from './context-resource';\n\n// ─── 结果接口 ─────────────────────────────────────────────────────\n\nexport interface Result {\n /** 输出内容(最终回复文本) */\n readonly content: string;\n /** 使用的工具列表 */\n readonly toolsUsed: string[];\n /** Token 用量统计 */\n readonly usage: Record<string, number>;\n /** 停止原因 */\n readonly stopReason: string;\n /** 元数据 */\n readonly metadata: Record<string, unknown>;\n /** 错误信息(运行失败时) */\n readonly error?: string;\n /** 是否成功 */\n readonly success: boolean;\n /** 资源快照(运行结束时的上下文资源) */\n readonly resources?: ContextResource[];\n}\n\n// ─── 结果构建器 ───────────────────────────────────────────────────\n\nexport class ResultBuilder {\n private _content: string = '';\n private _toolsUsed: string[] = [];\n private _usage: Record<string, number> = {};\n private _stopReason: string = 'completed';\n private _metadata: Record<string, unknown> = {};\n private _error?: string;\n private _success: boolean = true;\n private _resources?: ContextResource[];\n\n content(c: string): this {\n this._content = c;\n return this;\n }\n\n toolsUsed(tools: string[]): this {\n this._toolsUsed = tools;\n return this;\n }\n\n addTool(tool: string): this {\n if (!this._toolsUsed.includes(tool)) {\n this._toolsUsed.push(tool);\n }\n return this;\n }\n\n usage(u: Record<string, number>): this {\n this._usage = u;\n return this;\n }\n\n stopReason(r: string): this {\n this._stopReason = r;\n return this;\n }\n\n metadata(key: string, value: unknown): this;\n metadata(map: Record<string, unknown>): this;\n metadata(keyOrMap: string | Record<string, unknown>, value?: unknown): this {\n if (typeof keyOrMap === 'string') {\n this._metadata[keyOrMap] = value;\n } else {\n this._metadata = { ...this._metadata, ...keyOrMap };\n }\n return this;\n }\n\n error(e?: string): this {\n if (e !== undefined) {\n this._error = e;\n this._success = false;\n this._stopReason = 'error';\n }\n return this;\n }\n\n resources(res: ContextResource[]): this {\n this._resources = res;\n return this;\n }\n\n build(): Result {\n return {\n content: this._content,\n toolsUsed: this._toolsUsed,\n usage: this._usage,\n stopReason: this._stopReason,\n metadata: this._metadata,\n error: this._error,\n success: this._success,\n resources: this._resources,\n };\n }\n}\n\n// ─── 流式事件接口 ─────────────────────────────────────────────────\n\nexport interface ResultChunk {\n /** 块类型 */\n type: 'text' | 'tool_start' | 'tool_end' | 'thinking' | 'error' | 'done';\n /** 内容 */\n content?: string;\n /** 工具名称(tool 类型) */\n toolName?: string;\n /** 工具调用 ID */\n toolCallId?: string;\n /** 是否错误 */\n isError?: boolean;\n /** done 类型:最终 Result 摘要(usage / stopReason / toolsUsed 等,供调用方统计展示) */\n result?: Result;\n}\n\n// ─── 工厂函数 ─────────────────────────────────────────────────────\n\nexport function createResult(content: string, options?: Partial<Result>): Result {\n return {\n content,\n toolsUsed: options?.toolsUsed ?? [],\n usage: options?.usage ?? {},\n stopReason: options?.stopReason ?? 'completed',\n metadata: options?.metadata ?? {},\n error: options?.error,\n success: options?.success ?? !options?.error,\n resources: options?.resources,\n };\n}\n\nexport function createErrorResult(error: string): Result {\n return new ResultBuilder()\n .error(error)\n .build();\n}\n","/**\n * packages/core/session.ts - 会话持久化契约层\n *\n * 定义会话存储的数据格式与适配器接口。\n * 实现(memory/file)位于 packages/session/,遵循单向依赖:session → core。\n *\n * 设计要点:\n * - 线性结构:messages 平铺 + 元数据(模型、用量),不做树形分支(YAGNI)\n * - version 字段预留兼容,未来结构升级可平滑迁移\n * - 存储接口仿 src/storage 的 adapter 模式,但不依赖 src/\n */\n\nimport type { Message, Usage } from './types';\n\n/** 当前会话数据格式版本 */\nexport const SESSION_VERSION = 1;\n\n/** 会话模型信息(最后使用的模型) */\nexport interface SessionModel {\n provider: string;\n modelId: string;\n}\n\n/** 持久化会话数据(线性结构) */\nexport interface StoredSession {\n key: string;\n version: number;\n messages: Message[];\n model: SessionModel | null;\n usage: Usage;\n createdAt: string;\n updatedAt: string;\n}\n\n/** 跨进程锁句柄:调用方需在 finally 中 release() */\nexport interface StorageLock {\n release(): Promise<void>;\n}\n\n/** 会话存储适配器接口 */\nexport interface SessionStorage {\n load(key: string): Promise<StoredSession | null>;\n save(key: string, session: StoredSession): Promise<void>;\n delete(key: string): Promise<boolean>;\n list(): Promise<string[]>;\n /**\n * 跨进程互斥锁(可选):fn 执行期间独占该 key 的\"读-改-写\",\n * 防止多进程并发写同一会话导致 last-write-wins 丢消息。\n * 单进程存储(如内存实现)可省略;Runtime 在非 ephemeral 请求下自动调用。\n */\n withLock?<T>(key: string, fn: () => Promise<T>): Promise<T>;\n /** 手动锁(可选,供流式等无法用回调包住的场景):finally 中 release() */\n acquireLock?(key: string): Promise<StorageLock>;\n}\n\n/** 文件存储选项 */\nexport interface FileSessionStorageOptions {\n /** 存储根目录,默认 <pwd>/.aipack/sessions */\n baseDir?: string;\n /** 过期时间(毫秒),超过 updatedAt 的会话在加载/列举时清理 */\n maxAge?: number;\n /** 持久化消息条数上限(保留最新 N 条,0 表示不限,默认 0) */\n maxStoredMessages?: number;\n /** 获取跨进程锁的最大等待时间(毫秒,默认 30000)。超时抛错 */\n lockWaitMs?: number;\n /** 锁文件视为\"陈旧\"的阈值(毫秒,默认 300000)。\n * 持有锁的进程崩溃后留下的锁文件在超过该时长后会被接管 */\n lockStaleMs?: number;\n /** 锁获取重试的基础间隔(毫秒,默认 25,指数退避至 500) */\n lockRetryMs?: number;\n}\n\n/** 内存存储选项 */\nexport interface MemorySessionStorageOptions {\n /** 过期时间(毫秒),超过 updatedAt 的会话在加载时清理 */\n maxAge?: number;\n}\n","/**\n * packages/request - 请求入口\n *\n * 独立实现,不依赖 src/。\n * 负责请求的解析、验证与标准化。\n */\n\nimport { RequestBuilder, createRequest } from '../core';\nimport type { Request, RequestType } from '../core';\n\n// ─── 请求验证 ─────────────────────────────────────────────────────\n\nexport interface ValidationResult {\n valid: boolean;\n errors: string[];\n}\n\nexport function validateRequest(request: Request): ValidationResult {\n const errors: string[] = [];\n\n if (!request.message || request.message.trim().length === 0) {\n errors.push('message 不能为空');\n }\n\n if (request.message.length > 100000) {\n errors.push('message 长度超过限制(100000 字符)');\n }\n\n return { valid: errors.length === 0, errors };\n}\n\n// ─── 请求标准化 ───────────────────────────────────────────────────\n\nexport function normalizeRequest(request: Request): Request {\n return createRequest(request.message, {\n type: request.type,\n channel: request.channel || 'cli',\n chatId: request.chatId || 'direct',\n senderId: request.senderId || 'user',\n sessionKey: request.sessionKey,\n media: request.media?.filter(Boolean) || [],\n ephemeral: request.ephemeral ?? false,\n model: request.model || undefined,\n modelPreset: request.modelPreset || undefined,\n metadata: request.metadata || {},\n });\n}\n\n// ─── 请求工厂 ─────────────────────────────────────────────────────\n\n// 渠道相关工厂(CLI / Webhook / 飞书 / SDK)不属于框架:\n// 各渠道由使用方基于 createRequest 自行拼装,例如:\n// createRequest(msg, { sessionKey: `webhook:${chatId}`, channel: 'webhook', chatId, senderId })\n\nexport { RequestBuilder, createRequest } from '../core';\nexport type { Request, RequestType } from '../core';\n","/**\n * packages/context-resource - 上下文资源适配层\n *\n * 将 core 的 Message 体系转换为 ContextResource。\n */\n\nimport type {\n Message,\n UserMessage,\n AssistantMessage,\n ToolResultMessage,\n SystemMessage,\n ContentBlock,\n Usage,\n} from '../core';\nimport {\n ContextResourceBuilder,\n createToolResultResource,\n} from '../core';\nimport type { ContextResource, ResourceType, ResourceRole } from '../core';\nimport { extractToolCalls, extractText } from '../core';\n\n// ─── Message -> ContextResource ───────────────────────────────────\n\nexport function messageToResource(msg: Message, index: number): ContextResource {\n const id = `msg_${index}`;\n const timestamp = msg.timestamp ?? Date.now();\n\n switch (msg.role) {\n case 'user': {\n return new ContextResourceBuilder()\n .id(id)\n .type('user_message')\n .role('user')\n .content(msg.content)\n .timestamp(timestamp)\n .build();\n }\n\n case 'assistant': {\n const assistant = msg as AssistantMessage;\n const builder = new ContextResourceBuilder()\n .id(id)\n .type('assistant_message')\n .role('assistant')\n .content(assistant.content)\n .timestamp(timestamp)\n .meta('model', assistant.model)\n .meta('provider', assistant.provider)\n .meta('stopReason', assistant.stopReason);\n\n if (assistant.usage) {\n builder.meta('usage', assistant.usage);\n }\n\n const toolCalls = extractToolCalls(assistant.content);\n for (const tc of toolCalls) {\n builder.dependsOn(tc.id);\n }\n\n return builder.build();\n }\n\n case 'toolResult': {\n const toolMsg = msg as ToolResultMessage;\n return createToolResultResource(\n toolMsg.toolCallId,\n toolMsg.toolName,\n toolMsg.content,\n toolMsg.isError,\n toolMsg.toolCallId,\n { timestamp },\n );\n }\n\n case 'system': {\n return new ContextResourceBuilder()\n .id(id)\n .type('system_message')\n .role('system')\n .content(msg.content)\n .timestamp(timestamp)\n .pinned()\n .build();\n }\n\n default: {\n const customMsg = msg as Message & { role: string };\n const roleStr: string = customMsg.role;\n const customType: ResourceType =\n roleStr === 'compactionSummary' ? 'compaction_summary'\n : roleStr === 'stateSnapshot' ? 'state_snapshot'\n : 'custom';\n\n const builder = new ContextResourceBuilder()\n .id(id)\n .type(customType)\n .role(roleStr as ResourceRole)\n .content(customMsg)\n .timestamp(timestamp);\n // 摘要与状态快照为关键资源:截断类转换器不可移除(pinned)\n if (customType === 'compaction_summary' || customType === 'state_snapshot') {\n builder.pinned();\n }\n return builder.build();\n }\n }\n}\n\nexport function messagesToResources(messages: Message[]): ContextResource[] {\n return messages.map((msg, index) => messageToResource(msg, index));\n}\n\n// ─── ContextResource -> Message ───────────────────────────────────\n\nexport function resourceToMessage(resource: ContextResource): Message {\n switch (resource.type) {\n case 'user_message':\n return {\n role: 'user',\n content: resource.content as string | ContentBlock[],\n timestamp: resource.timestamp,\n } as UserMessage;\n\n case 'assistant_message': {\n const meta = resource.meta;\n const content = resource.content;\n // 标准转换:resource.content 存的是 ContentBlock[],需重建完整 AssistantMessage\n if (Array.isArray(content)) {\n return {\n role: 'assistant',\n content: content as ContentBlock[],\n stopReason: meta.stopReason as string | undefined,\n usage: meta.usage as Usage | undefined,\n model: meta.model as string | undefined,\n provider: meta.provider as string | undefined,\n timestamp: resource.timestamp,\n } as AssistantMessage;\n }\n // 兼容:content 本身就是完整消息(自定义转换器可能直接存消息)\n return content as AssistantMessage;\n }\n\n case 'tool_result': {\n const meta = resource.meta;\n return {\n role: 'toolResult',\n toolCallId: meta.toolCallId as string,\n toolName: meta.toolName as string,\n content: resource.content as ContentBlock[],\n isError: meta.isError as boolean,\n timestamp: resource.timestamp,\n } as ToolResultMessage;\n }\n\n case 'system_message':\n return {\n role: 'system',\n content: resource.content as string,\n timestamp: resource.timestamp,\n } as SystemMessage;\n\n case 'state_snapshot': {\n // StateSnapshotTransformer 直接构造的资源(不经 messageToResource),\n // 其 content 为快照文本字符串。此处包装为合法 Message\n // (role='stateSnapshot'),由 runtime.buildContext 统一转为 user 消息\n // 发往 provider。此前 default 分支 `return resource.content as Message`\n // 会把字符串当 Message 返回,导致消息数组混入字符串、buildContext 崩溃。\n const text =\n typeof resource.content === 'string'\n ? resource.content\n : extractText(resource.content as ContentBlock[]);\n return {\n role: 'stateSnapshot',\n content: text,\n timestamp: resource.timestamp,\n } as unknown as Message;\n }\n\n default:\n return resource.content as Message;\n }\n}\n\nexport function resourcesToMessages(resources: ContextResource[]): Message[] {\n return resources.map(resourceToMessage);\n}\n\n// ─── 工具函数 ─────────────────────────────────────────────────────\n\nexport function extractToolCallsFromResource(resource: ContextResource): string[] {\n if (resource.type !== 'assistant_message') return [];\n const content = resource.content as ContentBlock[];\n if (!Array.isArray(content)) return [];\n return extractToolCalls(content).map(tc => tc.id);\n}\n\nexport function extractTextFromResource(resource: ContextResource): string {\n const content = resource.content;\n if (typeof content === 'string') return content;\n if (Array.isArray(content)) return extractText(content);\n return '';\n}\n","// ─── 重新导出 TypeBox ───────────────────────────────────────────\nexport { Type, type Static, type TSchema } from '@sinclair/typebox';\n\n// ─── 类型 ────────────────────────────────────────────────────────\nexport type {\n Api,\n ContentBlock,\n TextContent,\n ImageContent,\n ToolCallContent,\n ThinkingContent,\n Usage,\n Model,\n UserMessage,\n AssistantMessage,\n ToolResultMessage,\n Message,\n Tool,\n Context,\n StreamEvent,\n StreamStartEvent,\n TextStartEvent,\n TextDeltaEvent,\n TextEndEvent,\n ThinkingStartEvent,\n ThinkingDeltaEvent,\n ThinkingEndEvent,\n ToolCallStartEvent,\n ToolCallDeltaEvent,\n ToolCallEndEvent,\n DoneEvent,\n ErrorEvent,\n StreamResult,\n SimpleStreamOptions,\n StreamOptions,\n ReasoningLevel,\n Provider,\n ResolvedAuth,\n ModelsOptions,\n CredentialStore,\n ImagesModel,\n ImagesProvider,\n ImageInputBlock,\n ImageOutputBlock,\n AssistantImages,\n ImagesGenerateOptions,\n} from './types';\n\n// ─── 函数 ───────────────────────────────────────────────────\nexport { hasApi, createEmptyUsage, createEmptyAssistantMessage } from './types';\n\n// ─── Models 类 ──────────────────────────────────────────────────────\nexport { Models, createModels } from './models';\n\n// ─── 图片生成 ────────────────────────────────────────────\nexport { ImagesModels, createImagesModels } from './images';\n\n// ─── 内置提供者 ──────────────────────────────────────────\nexport {\n builtinModels,\n builtinProviders,\n builtinImagesModels,\n getBuiltinModel,\n getBuiltinModels,\n getBuiltinProviders,\n} from './providers-all';\n\n// ─── 目录 ─────────────────────────────────────────────────────\nexport { BUILTIN_MODELS, BUILTIN_IMAGES_MODELS, BUILTIN_PROVIDERS, getEnvApiKey, hasProviderConfigured } from './catalog';\n\n// ─── 流式实现(供适配器直接复用) ──────────────────────────────\nexport { streamOpenAI } from './stream-openai';\nexport { streamAnthropic } from './stream-anthropic';\n\n// ─── 统一凭证解析 ─────────────────────────────────────────────\nexport {\n envKeyName,\n resolveApiKey,\n resolveApiKeyFromEnv,\n EnvCredentialStore,\n createEnvCredentialStore,\n} from './credentials';\n\n// ─── 上下文溢出检测 ────────────────────────────────────────────\nexport { isContextOverflow } from './overflow';\n\n// ─── 统一错误分类 ──────────────────────────────────────────────\nexport {\n AgentError,\n AgentErrorCategory,\n isAgentError,\n isRetryableCategory,\n classifyHttpStatus,\n classifyErrorMessage,\n classifyError,\n isContextOverflowError,\n categoryLabel,\n formatCategoryError,\n formatHttpError,\n} from './errors';\nexport type { AgentErrorOptions } from './errors';\n","/**\n * AgentError - 统一错误分类体系\n *\n * AI 调用链(stream 层 / retry 层 / 上层消费者)共享同一套错误分类:\n * - retryable 网络抖动 / 5xx 瞬时错误(可重试)\n * - rate-limit 429 限流(可重试,配合退避)\n * - timeout 超时(半开连接 / idle 断流)\n * - auth 认证失败(401/403 / 缺少 API key / key 无效)\n * - context-overflow 上下文超限(413 / context length 错误)\n * - invalid-request 请求非法(其余 4xx)\n * - unknown 未分类\n *\n * 用途:\n * 1. retry 决策(isRetryableError 优先读取 category,替代消息模式匹配)\n * 2. 上层差异化处理(如 auth 错误提示用户换 key、context-overflow 触发压缩)\n * 3. errorMessage 带 [category] 前缀,人可直接阅读\n */\n\n// ─── 分类常量 ──────────────────────────────────────────────────────\n\nexport const AgentErrorCategory = {\n RETRYABLE: 'retryable',\n TIMEOUT: 'timeout',\n AUTH: 'auth',\n CONTEXT_OVERFLOW: 'context-overflow',\n RATE_LIMIT: 'rate-limit',\n INVALID_REQUEST: 'invalid-request',\n UNKNOWN: 'unknown',\n} as const;\n\nexport type AgentErrorCategory =\n (typeof AgentErrorCategory)[keyof typeof AgentErrorCategory];\n\n// ─── AgentError 类 ─────────────────────────────────────────────────\n\nexport interface AgentErrorOptions {\n /** 错误分类(缺省 unknown) */\n category?: AgentErrorCategory;\n /** HTTP 状态码(如有) */\n status?: number;\n /** 是否可重试(缺省按分类推导:retryable / rate-limit 可重试) */\n retryable?: boolean;\n /** 原始错误(如 fetch Response / 底层 Error) */\n cause?: unknown;\n}\n\nconst RETRYABLE_CATEGORIES: ReadonlySet<AgentErrorCategory> = new Set([\n AgentErrorCategory.RETRYABLE,\n AgentErrorCategory.RATE_LIMIT,\n]);\n\n/** 该分类默认是否可重试 */\nexport function isRetryableCategory(category: AgentErrorCategory): boolean {\n return RETRYABLE_CATEGORIES.has(category);\n}\n\nexport class AgentError extends Error {\n readonly category: AgentErrorCategory;\n readonly status?: number;\n readonly retryable: boolean;\n /** 原始错误(ES2022 cause,Node 18 起 Error 构造支持 options.cause) */\n override readonly cause?: unknown;\n\n constructor(message: string, options: AgentErrorOptions = {}) {\n super(message);\n this.name = 'AgentError';\n this.category = options.category ?? AgentErrorCategory.UNKNOWN;\n this.status = options.status;\n this.retryable = options.retryable ?? isRetryableCategory(this.category);\n // 不依赖 ES2022 Error 构造 options.cause(低 target 转译可能丢失),显式赋值\n this.cause = options.cause;\n }\n}\n\n/** 类型守卫:兼容跨包/跨 realm 复制的 AgentError 对象 */\nexport function isAgentError(error: unknown): error is AgentError {\n if (error instanceof AgentError) return true;\n return (\n !!error &&\n typeof error === 'object' &&\n (error as { name?: unknown }).name === 'AgentError' &&\n typeof (error as { category?: unknown }).category === 'string'\n );\n}\n\n// ─── HTTP 状态码分类 ───────────────────────────────────────────────\n\nexport function classifyHttpStatus(status: number): AgentErrorCategory {\n if (status === 401 || status === 403) return AgentErrorCategory.AUTH;\n if (status === 429) return AgentErrorCategory.RATE_LIMIT;\n if (status === 413) return AgentErrorCategory.CONTEXT_OVERFLOW;\n if (status >= 500 && status < 600) return AgentErrorCategory.RETRYABLE;\n if (status >= 400 && status < 500) return AgentErrorCategory.INVALID_REQUEST;\n return AgentErrorCategory.UNKNOWN;\n}\n\n// ─── 错误消息分类(覆盖无 HTTP 状态码的场景)────────────────────────\n\nconst CONTEXT_OVERFLOW_PATTERNS = [\n 'context length',\n 'context window',\n 'context overflow',\n 'context too long',\n 'maximum context',\n 'too many tokens',\n 'token limit',\n 'prompt is too long',\n 'input is too long',\n 'exceeds the model',\n];\n\nconst RATE_LIMIT_PATTERNS = [\n 'rate limit',\n 'too many requests',\n 'ratelimit',\n];\n\nconst AUTH_PATTERNS = [\n 'unauthorized',\n 'authentication',\n 'invalid api key',\n 'incorrect api key',\n 'api key invalid',\n 'permission denied',\n 'forbidden',\n '401',\n '403',\n];\n\nconst TIMEOUT_PATTERNS = [\n 'timeout',\n 'timed out',\n 'etimedout',\n];\n\nexport function classifyErrorMessage(message: string): AgentErrorCategory {\n const lower = message.toLowerCase();\n if (CONTEXT_OVERFLOW_PATTERNS.some((p) => lower.includes(p))) {\n return AgentErrorCategory.CONTEXT_OVERFLOW;\n }\n if (RATE_LIMIT_PATTERNS.some((p) => lower.includes(p))) {\n return AgentErrorCategory.RATE_LIMIT;\n }\n if (AUTH_PATTERNS.some((p) => lower.includes(p))) {\n return AgentErrorCategory.AUTH;\n }\n if (TIMEOUT_PATTERNS.some((p) => lower.includes(p))) {\n return AgentErrorCategory.TIMEOUT;\n }\n return AgentErrorCategory.UNKNOWN;\n}\n\n// ─── 分类组合 ──────────────────────────────────────────────────────\n\n/**\n * 从任意错误对象推导分类:\n * AgentError 优先;有 status 按状态码;否则按消息模式。\n */\nexport function classifyError(error: unknown): AgentErrorCategory {\n if (isAgentError(error)) return error.category;\n const status = (error as { status?: unknown } | null)?.status;\n if (typeof status === 'number') return classifyHttpStatus(status);\n const msg = (error as Error | null)?.message ?? String(error ?? '');\n return classifyErrorMessage(msg);\n}\n\n/** 是否属于\"上下文超限\"(供压缩/截断策略复用) */\nexport function isContextOverflowError(error: unknown): boolean {\n return classifyError(error) === AgentErrorCategory.CONTEXT_OVERFLOW;\n}\n\n// ─── 格式化 ────────────────────────────────────────────────────────\n\n/** 分类标签(如 [auth]),unknown 分类返回空串 */\nexport function categoryLabel(category: AgentErrorCategory): string {\n return category === AgentErrorCategory.UNKNOWN ? '' : `[${category}] `;\n}\n\n/**\n * 构造带分类前缀的 errorMessage:\n * [auth] API error 401: Invalid API key\n * [rate-limit] API error 429: Too many requests\n * [timeout] Stream idle timeout after 60000ms\n */\nexport function formatCategoryError(\n category: AgentErrorCategory,\n message: string,\n): string {\n return `${categoryLabel(category)}${message}`;\n}\n\n/**\n * 基于 HTTP 状态码构造分类错误消息:\n * apiErrorLabel 形如 \"API error\" / \"Anthropic API error\"\n */\nexport function formatHttpError(\n status: number,\n message: string,\n apiErrorLabel = 'API error',\n): string {\n const category = classifyHttpStatus(status);\n return formatCategoryError(category, `${apiErrorLabel} ${status}: ${message}`);\n}\n","/**\n * 上下文溢出检测\n *\n * 通过匹配各提供商的错误消息模式,检测 API 返回是否因输入超出上下文窗口导致。\n * 支持五种溢出/可恢复截断模式:\n * 1. 显式溢出:provider 返回错误消息\n * 2. 静默溢出:provider 接受请求但 usage.input > contextWindow\n * 3. 截断溢出(输入侧):provider 截断输入后无输出空间(output=0)\n * 4. 截断溢出(输出侧,thinking 耗尽):stopReason=\"length\" 且模型只有 thinking\n * 块、没有实际 text/tool_call 产出(reasoning 模型常见,maxTokens 预算被 thinking\n * 吃光导致用户侧零产出,必须恢复,否则只能手动点「继续」)\n * 5. 截断溢出(输出侧,output 接近上限):stopReason=\"length\" 且 usage.output 占\n * 满 maxTokens(传入),视为本回合预算耗尽,需要外部继续\n */\n\n// ─── 溢出模式 ──────────────────────────────────────────────────────\n\nconst OVERFLOW_PATTERNS: RegExp[] = [\n // 本框架 formatCategoryError 产出的分类前缀(errors.ts),\n // 覆盖消息体不含已知关键词但已带分类前缀的场景\n /^\\[context-overflow\\]/i,\n // Anthropic\n /prompt is too long/i,\n /request_too_large/i,\n // Amazon Bedrock\n /input is too long for requested model/i,\n // OpenAI & 兼容\n /exceeds the context window/i,\n /exceeds (?:the )?(?:model'?s )?maximum context length(?: of [\\d,]+ tokens?|\\s*\\([\\d,]+\\))/i,\n /input token count.*exceeds the maximum/i,\n // xAI Grok\n /maximum prompt length is \\d+/i,\n // Groq\n /reduce the length of the messages/i,\n // OpenRouter\n /maximum context length is \\d+ tokens/i,\n /exceeds (?:the )?maximum allowed input length of [\\d,]+ tokens?/i,\n // Together AI\n /input \\(\\d+ tokens\\) is longer than the model'?s context length \\(\\d+ tokens\\)/i,\n // GitHub Copilot\n /exceeds the limit of \\d+/i,\n // llama.cpp\n /exceeds the available context size/i,\n // LM Studio\n /greater than the context length/i,\n // MiniMax\n /context window exceeds limit/i,\n // Kimi\n /exceeded model token limit/i,\n // Mistral\n /too large for model with \\d+ maximum context length/i,\n // DS4\n /prompt has [\\d,]+ tokens?, but the configured context size is [\\d,]+ tokens?/i,\n // z.ai\n /model_context_window_exceeded/i,\n // Ollama\n /prompt too long; exceeded (?:max )?context length/i,\n // DashScope / Qwen\n /range of input length should be/i,\n // 通用回退\n /context[_ ]length[_ ]exceeded/i,\n /too many tokens/i,\n /token limit exceeded/i,\n // Cerebras: 400/413 无 body\n /^4(?:00|13)\\s*(?:status code)?\\s*\\(no body\\)/i,\n];\n\n// ─── 非溢出的排除模式 ─────────────────────────────────────────────\n\nconst NON_OVERFLOW_PATTERNS: RegExp[] = [\n /^(Throttling error|Service unavailable):/i,\n /rate limit/i,\n /too many requests/i,\n];\n\n// ─── 导出函数 ──────────────────────────────────────────────────────\n\ntype MinimalBlock =\n | { type: 'text'; text?: string }\n | { type: 'toolCall'; id?: string }\n | { type: 'thinking'; thinking?: string; text?: string }\n | { type: string };\n\n/**\n * 溢出检测所需的消息最小形状。\n * 兼容 core(stopReason/usage 可缺省)与 ai(必填)两套 AssistantMessage 定义。\n */\nexport interface OverflowProbeMessage {\n stopReason?: string;\n errorMessage?: string;\n usage?: {\n input: number;\n output: number;\n cacheRead?: number;\n reasoning?: number;\n };\n /** assistant message 的 content block(可缺省);用于检测「只有 thinking 没有有效产出」 */\n content?: string | MinimalBlock[];\n /** 传给 overflow 检测的上限:模型本轮的 max_output_tokens;用于识别 output 被打满的 length 截断 */\n maxTokens?: number;\n}\n\n/**\n * 判断一条 assistant message 是否为上下文溢出错误。\n *\n * @param message - 要检查的 assistant message\n * @param contextWindow - 可选的上下文窗口大小,用于检测静默溢出(如 z.ai)\n */\nexport function isContextOverflow(\n message: OverflowProbeMessage,\n contextWindow?: number,\n): boolean {\n // 情况 1:检查错误消息模式(显式溢出)\n if (message.stopReason === 'error' && message.errorMessage) {\n const errMsg: string = message.errorMessage;\n const isNonOverflow = NON_OVERFLOW_PATTERNS.some((p) => p.test(errMsg));\n if (!isNonOverflow && OVERFLOW_PATTERNS.some((p) => p.test(errMsg))) {\n return true;\n }\n }\n\n // 情况 2:静默溢出(z.ai 风格)— 成功但 usage 超出上下文\n if (contextWindow && message.stopReason === 'stop' && message.usage) {\n const inputTokens = message.usage.input + (message.usage.cacheRead ?? 0);\n if (inputTokens > contextWindow) {\n return true;\n }\n }\n\n // 情况 3:截断溢出(输入侧)— 截断输入后无输出空间\n if (\n contextWindow &&\n message.stopReason === 'length' &&\n message.usage &&\n message.usage.output === 0\n ) {\n const inputTokens = message.usage.input + (message.usage.cacheRead ?? 0);\n if (inputTokens >= contextWindow * 0.99) {\n return true;\n }\n }\n\n // 情况 4:截断溢出(输出侧 thinking 耗尽)\n // reasoning 模型 maxTokens 预算被 thinking 吃光:stopReason=\"length\" 且 content\n // 里没有任何非空 text、也没有 tool_call(可能只有 thinking 块)。\n // 典型场景:deepseek-v4-flash maxTokens=8192,output=8192 全是 reasoning,\n // 用户视角「模型什么都没回复就停了」,必须视为可恢复溢出。\n if (message.stopReason === 'length' && message.content) {\n const blocks = Array.isArray(message.content) ? message.content : null;\n if (blocks) {\n const hasMeaningfulText = blocks.some(\n (b) =>\n b.type === 'text' &&\n typeof (b as any).text === 'string' &&\n (b as any).text.trim().length > 0,\n );\n const hasToolCall = blocks.some((b) => b.type === 'toolCall');\n const hasThinking = blocks.some((b) => b.type === 'thinking');\n // 没有有效文本、没有工具调用、但至少有 thinking → 典型 reasoning 耗尽\n if (!hasMeaningfulText && !hasToolCall && hasThinking) {\n return true;\n }\n }\n }\n\n // 情况 5:截断溢出(输出侧打满)\n // stopReason=\"length\" 且 usage.output ≥ 0.95 × maxTokens → 本轮 output token\n // 预算被打满,后续内容会被截断,需要恢复流程(压缩 / 继续)。\n if (\n message.maxTokens &&\n message.maxTokens > 0 &&\n message.stopReason === 'length' &&\n message.usage\n ) {\n if (message.usage.output >= Math.floor(message.maxTokens * 0.95)) {\n return true;\n }\n }\n\n return false;\n}\n\n/**\n * 获取溢出模式列表(用于测试)\n */\nexport function getOverflowPatterns(): RegExp[] {\n return [...OVERFLOW_PATTERNS];\n}\n","/**\n * packages/transformer - 上下文转换器\n *\n * 独立实现的 ContextTransformer,不依赖 src/。\n * 提供工具配对修复、状态快照注入、消息截断等内置转换器。\n * 用户可通过 BaseTransformer 实现自定义转换器(如上下文压缩)。\n */\n\nimport { BaseTransformer } from '../core';\nimport type { ContextResource, TransformContext } from '../core';\nimport type { Message, ToolCallContent, ContentBlock } from '../core';\nimport { extractToolCalls } from '../core';\nimport { messagesToResources, resourcesToMessages } from '../context-resource';\n\n// ─── token 估算 ───────────────────────────────────────────────────\n\n/**\n * 粗略 token 估算:约 4 字符/token(对中英文混合近似可用)。\n * 不引入 tokenizer 依赖;若需要精确计数,使用方可注入自定义转换器替换。\n */\nfunction estimateTokens(text: string): number {\n if (!text) return 0;\n return Math.ceil(text.length / 4);\n}\n\n/** 估算单个资源的 token 数(序列化内容后计数) */\nfunction estimateResourceTokens(resource: ContextResource): number {\n const content = resource.content;\n if (typeof content === 'string') return estimateTokens(content);\n try {\n return estimateTokens(JSON.stringify(content ?? ''));\n } catch {\n return 0;\n }\n}\n\n/** 序列化资源内容为可读文本,用于 token 估算 */\nfunction resourceText(resource: ContextResource): string {\n const content = resource.content;\n if (typeof content === 'string') return content;\n try {\n return JSON.stringify(content ?? '');\n } catch {\n return '';\n }\n}\n\n// ─── 工具配对转换器 ───────────────────────────────────────────────\n\n/**\n * 确保上下文中 tool_call 与 tool_result 的配对完整性。\n * 移除孤立的工具调用或工具结果消息。\n *\n * 建议放在 transformers 数组最后(兜底修复)。\n * 必须晚于 TruncationTransformer:截断会丢弃旧资源,可能打破配对\n * (例如丢掉 toolCall 但保留 toolResult,或反之),需要本转换器作为\n * 最终兜底重新修复,否则破坏后的消息序列会导致下一次模型调用 400。\n */\nexport class ToolPairingTransformer extends BaseTransformer {\n readonly name = 'tool-pairing';\n\n protected async run(\n resources: ContextResource[],\n _context: TransformContext,\n ): Promise<ContextResource[]> {\n const messages = resourcesToMessages(resources);\n const paired = ensureToolPairing(messages);\n return messagesToResources(paired);\n }\n}\n\n/**\n * 确保 tool_call 与 tool_result 配对完整\n */\nexport function ensureToolPairing(messages: Message[]): Message[] {\n const toolCallIds = new Set<string>();\n const toolResultIds = new Set<string>();\n\n // 收集所有 tool_call ID\n for (const msg of messages) {\n if (msg.role === 'assistant') {\n const content = msg.content;\n if (Array.isArray(content)) {\n for (const tc of extractToolCalls(content)) {\n toolCallIds.add(tc.id);\n }\n }\n }\n if (msg.role === 'toolResult') {\n toolResultIds.add((msg as any).toolCallId);\n }\n }\n\n // 找出孤立的 tool_call(无对应 result)和孤立的 tool_result(无对应 call)\n const orphanedCalls = new Set<string>();\n const orphanedResults = new Set<string>();\n\n for (const id of toolCallIds) {\n if (!toolResultIds.has(id)) orphanedCalls.add(id);\n }\n for (const id of toolResultIds) {\n if (!toolCallIds.has(id)) orphanedResults.add(id);\n }\n\n if (orphanedCalls.size === 0 && orphanedResults.size === 0) {\n return messages;\n }\n\n // 过滤消息\n const result: Message[] = [];\n for (const msg of messages) {\n if (msg.role === 'assistant') {\n const content = msg.content;\n if (Array.isArray(content)) {\n // 移除孤立的 tool_call\n const filteredContent = content.filter(block => {\n if (block.type === 'toolCall') {\n return !orphanedCalls.has((block as ToolCallContent).id);\n }\n return true;\n });\n // 如果所有内容都被移除,跳过这条消息\n if (filteredContent.length === 0 && content.length > 0) continue;\n result.push({ ...msg, content: filteredContent });\n } else {\n result.push(msg);\n }\n } else if (msg.role === 'toolResult') {\n // 移除孤立的 tool_result\n if (!orphanedResults.has((msg as any).toolCallId)) {\n result.push(msg);\n }\n } else {\n result.push(msg);\n }\n }\n\n return result;\n}\n\n// ─── 状态快照注入转换器 ───────────────────────────────────────────\n\n/**\n * 在上下文开头注入状态快照。\n */\nexport class StateSnapshotTransformer extends BaseTransformer {\n readonly name = 'state-snapshot';\n\n constructor(private getStateSnapshot: () => string | null) {\n super();\n }\n\n protected async run(\n resources: ContextResource[],\n _context: TransformContext,\n ): Promise<ContextResource[]> {\n const snapshot = this.getStateSnapshot();\n if (!snapshot) return resources;\n\n const snapshotResource: ContextResource = {\n id: `snapshot_${Date.now()}`,\n type: 'state_snapshot',\n role: 'system',\n content: snapshot,\n timestamp: Date.now(),\n dependencies: [],\n meta: { injected: true },\n pinned: true,\n };\n\n return [snapshotResource, ...resources];\n }\n}\n\n// ─── 消息截断转换器 ───────────────────────────────────────────────\n\n/**\n * 当资源总数超过限制时,移除最旧的非关键资源。\n *\n * 截断按\"配对组\"丢弃:丢弃一个带 toolCall 的 assistant 资源时,会一并丢弃\n * 对应的 toolResult 资源,避免留下孤立结果(孤立结果虽会被 ToolPairingTransformer\n * 兜底清理,但会浪费保留预算)。\n */\nexport class TruncationTransformer extends BaseTransformer {\n readonly name = 'truncation';\n\n constructor(private maxResources: number = 200) {\n super();\n }\n\n protected async run(\n resources: ContextResource[],\n _context: TransformContext,\n ): Promise<ContextResource[]> {\n if (resources.length <= this.maxResources) return resources;\n\n const pinned = resources.filter(r => r.pinned);\n const unpinned = resources.filter(r => !r.pinned);\n const keepCount = this.maxResources - pinned.length;\n\n if (keepCount <= 0) return pinned;\n\n // 保留最新的 keepCount 个,但需按\"配对组\"整体丢弃头部。\n // 从尾部回溯收集要保留的资源,遇到 assistant(toolCall) 时把对应的\n // toolResult 也纳入保留集合(即便它位于 keepCount 边界之外)。\n const keep = new Set<number>();\n const toolCallIdsInRange = new Set<string>();\n\n for (let i = unpinned.length - 1; i >= 0 && keep.size < keepCount; i--) {\n const res = unpinned[i];\n keep.add(i);\n if (res.type === 'assistant_message') {\n for (const dep of res.dependencies) toolCallIdsInRange.add(dep);\n }\n if (res.type === 'tool_result') {\n const tcId = (res.meta as { toolCallId?: string } | undefined)?.toolCallId;\n if (tcId) toolCallIdsInRange.add(tcId);\n }\n }\n\n // 二次扫描:把与已保留 toolCall 配对的 toolResult(或反之)一并保留,\n // 防止截断打破配对。\n for (let i = 0; i < unpinned.length; i++) {\n if (keep.has(i)) continue;\n const res = unpinned[i];\n if (res.type === 'tool_result') {\n const tcId = (res.meta as { toolCallId?: string } | undefined)?.toolCallId;\n if (tcId && toolCallIdsInRange.has(tcId)) keep.add(i);\n }\n }\n\n const kept = unpinned.filter((_, i) => keep.has(i));\n return [...pinned, ...kept].sort((a, b) => a.timestamp - b.timestamp);\n }\n}\n\n// ─── Token 预算截断转换器 ─────────────────────────────────────────\n\n/**\n * 按模型 contextWindow 的 token 预算截断上下文。\n *\n * 条数截断(TruncationTransformer)无法防止 token 溢出:200 条消息可能远超\n * 模型上下文窗口。本转换器按 token 估算从最旧的非关键\n * 资源开始丢弃,直到总 token 低于预算(默认 contextWindow * 0.8,预留输出空间)。\n */\nexport class TokenBudgetTransformer extends BaseTransformer {\n readonly name = 'token-budget';\n\n constructor(private ratio: number = 0.8) {\n super();\n }\n\n protected async run(\n resources: ContextResource[],\n context: TransformContext,\n ): Promise<ContextResource[]> {\n const contextWindow = context.runtime.contextWindow;\n if (!contextWindow || contextWindow <= 0) return resources;\n\n const ratio = context.runtime.contextBudgetRatio ?? this.ratio ?? 0.8;\n const budget = Math.floor(contextWindow * ratio);\n\n const pinned = resources.filter(r => r.pinned);\n const unpinned = resources.filter(r => !r.pinned); // 按时间顺序:旧在前\n\n let total = pinned.reduce((sum, r) => sum + estimateResourceTokens(r), 0)\n + unpinned.reduce((sum, r) => sum + estimateResourceTokens(r), 0);\n if (total <= budget) return resources;\n\n // 从头部(最旧)开始丢弃,直到总 token <= 预算。\n // 配对组感知:丢弃 assistant(toolCall) 时记录其 toolCallId,\n // 后续对应的 toolResult 也一并丢弃。\n const droppedToolCallIds = new Set<string>();\n let i = 0;\n while (i < unpinned.length && total > budget) {\n const res = unpinned[i];\n total -= estimateResourceTokens(res);\n if (res.type === 'assistant_message') {\n for (const dep of res.dependencies) droppedToolCallIds.add(dep);\n }\n i++;\n }\n\n // 保留未丢弃部分,并移除与已丢弃 toolCall 配对的 toolResult\n const kept = unpinned.slice(i).filter(res => {\n if (res.type === 'tool_result') {\n const tcId = (res.meta as { toolCallId?: string } | undefined)?.toolCallId;\n if (tcId && droppedToolCallIds.has(tcId)) return false;\n }\n return true;\n });\n\n return [...pinned, ...kept].sort((a, b) => a.timestamp - b.timestamp);\n }\n}\n\n// ─── 系统消息清理转换器 ───────────────────────────────────────────\n\n/**\n * 移除重复的系统消息,只保留最后一条。\n */\nexport class SystemMessageCleanerTransformer extends BaseTransformer {\n readonly name = 'system-message-cleaner';\n\n protected async run(\n resources: ContextResource[],\n _context: TransformContext,\n ): Promise<ContextResource[]> {\n const systemMessages = resources.filter(r => r.type === 'system_message');\n if (systemMessages.length <= 1) return resources;\n\n // 保留最后一条系统消息\n const lastSystem = systemMessages[systemMessages.length - 1];\n return resources.filter(r => r.type !== 'system_message' || r === lastSystem);\n }\n}\n\n// ─── 转换器工厂 ───────────────────────────────────────────────────\n\nexport function createDefaultTransformers(options?: {\n getStateSnapshot?: () => string | null;\n maxResources?: number;\n contextBudgetRatio?: number;\n}): import('../core').ContextTransformer[] {\n const transformers: import('../core').ContextTransformer[] = [\n new SystemMessageCleanerTransformer(),\n new TruncationTransformer(options?.maxResources ?? 200),\n new TokenBudgetTransformer(options?.contextBudgetRatio ?? 0.8),\n new ToolPairingTransformer(), // 放在最后,兜底修复配对\n ];\n\n if (options?.getStateSnapshot) {\n transformers.push(new StateSnapshotTransformer(options.getStateSnapshot));\n }\n\n return transformers;\n}\n","/**\n * packages/runtime - 运行时核心实现\n *\n * 独立实现的 Runtime,不依赖 src/。\n * Runtime 是整个 Agent 系统的核心调度器,\n * 负责协调对话循环、工具执行、上下文转换和插件钩子。\n */\n\nimport type {\n Runtime,\n Compilation,\n RuntimeOptions,\n CompactionOptions,\n Request,\n Result,\n ResultChunk,\n Extension,\n RuntimeHooks,\n ExtensionContext,\n ContextTransformer,\n TransformContext,\n ToolCallContext,\n BeforeToolCallDecision,\n AfterToolCallDecision,\n PermissionRequest,\n PermissionPolicy,\n ApprovalManager,\n} from '../core';\nimport {\n ExtensionManager,\n createTaskGraph,\n ResultBuilder,\n isErrorToolResult,\n} from '../core';\nimport type {\n Model,\n Tool,\n StreamFn,\n Message,\n UserMessage,\n AssistantMessage,\n ToolResultMessage,\n ContentBlock,\n ToolCallContent,\n ImageContent,\n Usage,\n Context,\n StreamOptions,\n StreamEvent,\n ThinkingLevel,\n ToolResult,\n} from '../core';\nimport {\n extractText,\n extractToolCalls,\n createTextContent,\n createEmptyUsage,\n SESSION_VERSION,\n} from '../core';\nimport type {\n SessionStorage,\n StoredSession,\n SessionModel,\n} from '../core';\nimport type { Telemetry, ErrorClass, CompactionTelemetryInfo } from '../telemetry';\nimport { validateRequest, normalizeRequest } from '../request';\nimport {\n messagesToResources,\n resourcesToMessages,\n} from '../context-resource';\nimport { classifyError, isAgentError, isContextOverflow } from '../ai';\nimport { ensureToolPairing } from '../transformer';\nimport { randomUUID } from 'node:crypto';\n\n// ─── traceId / spanId 生成(零新依赖)────────────────────────────\n\nfunction newTraceId(): string {\n return `${Date.now().toString(36)}-${randomUUID()}`;\n}\n\nfunction newSpanId(): string {\n return randomUUID();\n}\n\n/** 从流错误消息的 \"[category]\" 前缀解析错误分类(formatCategoryError 产出) */\nfunction errorClassFromMessage(message: string): string | undefined {\n const m = message.match(/^\\[([^\\]]+)\\]/);\n return m ? m[1] : undefined;\n}\n\n/** 工具结果状态分类:error(执行失败) / ok(正常)。blocked/skipped 不进入 onToolCall */\nfunction toolResultStatus(result: ToolResult): 'ok' | 'error' | 'blocked' | 'skipped' {\n if (result.details && typeof result.details === 'object' && 'error' in result.details) {\n return 'error';\n }\n const d = result.details as { blocked?: boolean; skipped?: boolean } | undefined;\n if (d?.blocked) return 'blocked';\n if (d?.skipped) return 'skipped';\n return 'ok';\n}\n\n/** 从重试错误对象提取 HTTP 状态码(AgentError 或 fetch Response) */\nfunction statusOfRetryError(error: unknown): number | undefined {\n if (isAgentError(error)) return error.status;\n const s = (error as { status?: unknown } | null)?.status;\n return typeof s === 'number' ? s : undefined;\n}\n\n// ─── 会话状态 ─────────────────────────────────────────────────────\n\ninterface SessionState {\n messages: Message[];\n isStreaming: boolean;\n abortController: AbortController | null;\n createdAt: string; // 会话首次创建时间,持久化时保留\n hydrated: boolean; // 是否已从存储恢复(串行化后无竞态)\n /** 串行队列:同一会话的 run/stream 依次执行,避免消息数组交错与 abort 覆盖 */\n queue: Promise<void>;\n /** 等待空闲的 resolver,isStreaming 变 false 时逐个唤醒 */\n idleResolvers: Array<() => void>;\n /** 是否持有执行锁(acquire 后 → release 前)。LRU 淘汰时保护刚入队未开始运行的会话 */\n lockHeld: boolean;\n}\n\n/** 内存会话状态表 LRU 上限(仅清理内存态,不删存储;超限淘汰最久未用) */\nconst DEFAULT_MAX_SESSIONS = 256;\n\nfunction createSessionState(): SessionState {\n return {\n messages: [],\n isStreaming: false,\n abortController: null,\n createdAt: new Date().toISOString(),\n hydrated: false,\n queue: Promise.resolve(),\n idleResolvers: [],\n lockHeld: false,\n };\n}\n\n// ─── 工具超时信号(Node 18 无 AbortSignal.any,手动桥接)─────────\n\nfunction withTimeoutSignal(\n parent: AbortSignal | undefined,\n ms: number,\n): { signal: AbortSignal; clear: () => void } {\n const controller = new AbortController();\n const timer = setTimeout(\n () => controller.abort(new Error(`Tool execution timeout after ${ms}ms`)),\n ms,\n );\n // 保存监听器引用,clear 时移除,避免 parent 长生命周期时未触发的 abort\n // 监听器累积({ once: true } 仅在触发后清理,不触发则常驻 parent 上)。\n let onAbort: (() => void) | undefined;\n if (parent) {\n if (parent.aborted) {\n controller.abort(parent.reason);\n } else {\n onAbort = () => controller.abort(parent.reason);\n parent.addEventListener('abort', onAbort, { once: true });\n }\n }\n return {\n signal: controller.signal,\n clear: () => {\n clearTimeout(timer);\n if (onAbort && parent) {\n parent.removeEventListener('abort', onAbort);\n onAbort = undefined;\n }\n },\n };\n}\n\n// ─── 媒体附件 → ImageContent ──────────────────────────────────────\n\nfunction buildImageContent(media: string): ImageContent {\n const dataMatch = media.match(/^data:([^;]+);base64,(.*)$/s);\n if (dataMatch) {\n return { type: 'image', mimeType: dataMatch[1], data: dataMatch[2] };\n }\n // 非 data URI 视为 URL(ImageContent.data 字段同时接受 base64 与 URL)\n return { type: 'image', mimeType: 'image/url', data: media };\n}\n\n// ─── 上下文溢出自动恢复 ────────────────────────────────────────────\n\n/** 单回合内溢出恢复重试上限(截断后仍溢出最多再试 2 次,防止死循环) */\nconst OVERFLOW_RECOVERY_LIMIT = 2;\n\n/** 粗略 token 估算(与 transformer 层同口径:约 4 字符/token) */\nfunction estimateMessageTokens(message: Message): number {\n const content = message.content;\n if (typeof content === 'string') return Math.ceil(content.length / 4);\n try {\n return Math.ceil(JSON.stringify(content ?? []).length / 4);\n } catch {\n return 0;\n }\n}\n\n/** 估算文本 token(与 estimateMessageTokens 同口径) */\nfunction estimateTextTokens(text: string): number {\n return Math.ceil(text.length / 4);\n}\n\n// ─── 内置摘要压缩 ─────────────────────────────────────────────────\n\n/**\n * 摘要请求输入预算:占 contextWindow 的比例。\n * 被压缩段序列化后超过该预算时不再发起摘要请求(请求本身必然超窗),\n * 直接降级硬截断,避免 doomed 调用。\n */\nconst COMPACTION_SUMMARY_BUDGET_RATIO = 0.6;\n\n/** 摘要请求单条消息的序列化字符上限(防单条巨型 toolResult 撑爆摘要请求) */\nconst COMPACTION_LINE_CLAMP = 4000;\n\n/** 默认摘要指令 */\nconst DEFAULT_COMPACTION_PROMPT = [\n '你是对话历史压缩器。请将以下对话历史压缩为一份信息密度高的摘要,供后续对话作为上下文参考。',\n '要求:',\n '1. 保留关键事实、决策、结论与未完成事项;',\n '2. 保留用户明确的偏好与约束;',\n '3. 保留重要工具调用的目的与结果要点(细节可省略);',\n '4. 丢弃寒暄、重复与无关细节;',\n '5. 直接输出摘要正文,不要任何前后缀说明。',\n].join('\\n');\n\n/** compactionSummary 消息发给 provider 时转换后的 user 消息前缀 */\nconst COMPACTION_USER_PREFIX = '[以下为此前对话历史的压缩摘要,作为上下文参考]';\n\n/** stateSnapshot 消息发给 provider 时转换后的 user 消息前缀 */\nconst STATE_SNAPSHOT_USER_PREFIX = '[以下为当前状态快照,作为上下文参考]';\n\n/** 序列化单条消息为摘要输入行;system 等无关角色返回空串 */\nfunction messageToSummaryLine(msg: Message): string {\n const clamp = (text: string): string =>\n text.length > COMPACTION_LINE_CLAMP\n ? `${text.slice(0, COMPACTION_LINE_CLAMP)}…(已截断)`\n : text;\n\n switch (msg.role) {\n case 'user': {\n const text = typeof msg.content === 'string' ? msg.content : extractText(msg.content);\n return `[用户] ${clamp(text)}`;\n }\n case 'assistant': {\n const parts: string[] = [];\n const content = msg.content;\n if (typeof content === 'string') {\n parts.push(content);\n } else {\n for (const block of content) {\n if (block.type === 'text') parts.push(block.text);\n else if (block.type === 'toolCall') {\n parts.push(`调用工具 ${block.name}(${JSON.stringify(block.arguments)})`);\n }\n }\n }\n return `[助手] ${clamp(parts.join(';'))}`;\n }\n case 'toolResult': {\n const m = msg as ToolResultMessage;\n const text = typeof m.content === 'string' ? m.content : extractText(m.content);\n return `[工具结果 ${m.toolName}] ${clamp(text)}`;\n }\n default: {\n // Message union 之外的扩展 role(compactionSummary / stateSnapshot 等)\n const role = (msg as { role: string }).role;\n // 已有的旧摘要/状态快照融入新摘要,避免反复压缩丢失早期信息\n if (role === 'compactionSummary' || role === 'stateSnapshot') {\n const text = typeof msg.content === 'string' ? msg.content : extractText(msg.content);\n return `[${role === 'compactionSummary' ? '历史摘要' : '状态快照'}] ${clamp(text)}`;\n }\n return '';\n }\n }\n}\n\n// ─── 工具执行结果(含 terminate 信号) ─────────────────────────────\n\n/**\n * 单次/一组工具执行的产出。除结果列表外,携带 terminate 信号:\n * beforeToolCall / afterToolCall 可请求终止整个 run,\n * runLoop 检测到后停止循环(本轮工具结果仍写入会话以保持配对完整)。\n */\ninterface ToolExecutionOutcome {\n results: ToolResult[];\n /** 是否请求终止整个 run */\n terminate: boolean;\n /** 终止原因(写入 Result.metadata.terminateReason) */\n terminateReason?: string;\n}\n\n/** 单个工具执行的产出(含 terminate 信号) */\ninterface SingleToolOutcome {\n result: ToolResult;\n terminate: boolean;\n terminateReason?: string;\n}\n\n// ─── AgentRuntime: Runtime 接口的独立实现 ─────────────────────────\n\nexport class AgentRuntime implements Runtime {\n private _config: Record<string, unknown>;\n private _extensions: ExtensionManager;\n private _hooks: RuntimeHooks;\n /** 上下文转换器列表,按数组顺序链式执行(上一个输出作为下一个输入) */\n private _transformers: ContextTransformer[];\n\n private _model: Model;\n private _streamFn: StreamFn;\n private _systemPrompt: string;\n private _thinkingLevel: ThinkingLevel;\n private _globalTools: Map<string, Tool> = new Map();\n\n /** 多会话状态表:key = sessionKey。模型/工具/扩展/转换器等资源跨会话共享 */\n private _sessions: Map<string, SessionState>;\n /** 默认会话 key(常量 'default';请求未指定 sessionKey 时路由到此会话) */\n private _sessionKey: string;\n /** 内存会话状态表 LRU 上限 */\n private _maxSessions: number;\n private _sessionStorage: SessionStorage | undefined;\n /** Extension 应用时的上下文(shared Map 供 ToolCallContext 引用) */\n private _extensionContext?: ExtensionContext;\n\n private _maxTurns: number;\n private _toolTimeoutMs: number;\n private _parallelToolCalls: boolean;\n private _contextBudgetRatio: number;\n /** 内置摘要压缩配置(未配置 = 保持旧行为,仅硬截断兜底) */\n private _compaction: CompactionOptions | undefined;\n private _telemetry: Telemetry | undefined;\n /** 框架级工具权限策略(未配置 → 放行,向后兼容) */\n private _permissionPolicy: PermissionPolicy | undefined;\n /** 审批管理器(pending 决策挂起等待外部批准;未配置 → pending 视为 deny) */\n private _approvals: ApprovalManager | undefined;\n /** 审批等待超时(毫秒) */\n private _approvalTimeoutMs: number;\n /** traceId 生成器(测试可注入确定性 id) */\n private _traceIdGenerator: (() => string) | undefined;\n\n private constructor(options: RuntimeOptions) {\n this._config = options.config ?? {};\n this._extensions = new ExtensionManager();\n this._hooks = this._extensions.getHooks();\n // 转换器按传入顺序链式执行(上一个输出作为下一个输入)\n this._transformers = [...(options.transformers ?? [])];\n\n this._model = options.model ?? {\n id: 'unknown',\n name: 'unknown',\n provider: 'unknown',\n contextWindow: 128000,\n maxTokens: 8192,\n reasoning: false,\n };\n\n this._streamFn = options.streamFn ?? (async function* () {\n throw new Error('streamFn 未设置,请通过 setStreamFn() 或 RuntimeOptions.streamFn 提供');\n });\n\n this._systemPrompt = options.systemPrompt ?? '';\n this._thinkingLevel = options.thinkingLevel ?? 'off';\n this._sessionStorage = options.sessionStorage;\n\n this._maxTurns = options.maxTurns ?? 50;\n this._toolTimeoutMs = options.toolTimeoutMs ?? 120_000;\n this._parallelToolCalls = options.parallelToolCalls ?? true;\n this._contextBudgetRatio = options.contextBudgetRatio ?? 0.8;\n this._compaction = options.compaction;\n this._telemetry = options.telemetry;\n this._permissionPolicy = options.permissionPolicy;\n this._approvals = options.approvals;\n this._approvalTimeoutMs = options.approvalTimeoutMs ?? 300_000;\n this._traceIdGenerator = options.traceIdGenerator;\n\n // 注册初始工具\n if (options.tools) {\n for (const tool of options.tools) {\n this._globalTools.set(tool.name, tool);\n }\n }\n\n this._sessionKey = 'default';\n this._maxSessions = options.maxSessions ?? DEFAULT_MAX_SESSIONS;\n // 默认会话预先入表,保证未指定 sessionKey 的请求路由到它\n this._sessions = new Map([[this._sessionKey, createSessionState()]]);\n }\n\n // ─── 静态工厂 ───────────────────────────────────────────────────\n\n static create(options: RuntimeOptions = {}): AgentRuntime {\n const runtime = new AgentRuntime(options);\n\n // 注册扩展\n if (options.extensions) {\n runtime._extensions.registerAll(options.extensions);\n }\n\n // 应用扩展到钩子\n const ctx: ExtensionContext = {\n config: runtime._config,\n workspace: options.workspace ?? process.cwd(),\n sessionKey: runtime._sessionKey,\n shared: new Map(),\n runtime,\n };\n runtime._extensionContext = ctx;\n runtime._extensions.applyAll(ctx);\n\n return runtime;\n }\n\n // ─── Runtime 接口实现 ───────────────────────────────────────────\n\n get config(): Record<string, unknown> {\n return this._config;\n }\n\n get extensions(): ExtensionManager {\n return this._extensions;\n }\n\n get hooks(): RuntimeHooks {\n return this._hooks;\n }\n\n // ─── 工具/模型/流管理 ───────────────────────────────────────────\n\n registerTool(tool: Tool): this {\n if (this._globalTools.has(tool.name)) {\n console.warn(`[Runtime] 工具 \"${tool.name}\" 已存在,将被覆盖`);\n }\n this._globalTools.set(tool.name, tool);\n return this;\n }\n\n registerTools(tools: Tool[]): this {\n for (const tool of tools) {\n this.registerTool(tool);\n }\n return this;\n }\n\n unregisterTool(name: string): boolean {\n return this._globalTools.delete(name);\n }\n\n setModel(model: Model): this {\n this._model = model;\n return this;\n }\n\n setSystemPrompt(prompt: string): this {\n this._systemPrompt = prompt;\n return this;\n }\n\n setThinkingLevel(level: ThinkingLevel): this {\n this._thinkingLevel = level;\n return this;\n }\n\n setStreamFn(fn: StreamFn): this {\n this._streamFn = fn;\n return this;\n }\n\n registerExtension(extension: Extension): this {\n this._extensions.register(extension);\n return this;\n }\n\n useTransformer(transformer: ContextTransformer): this {\n this._transformers.push(transformer);\n return this;\n }\n\n /** 获取指定会话的消息列表(默认会话;会话不存在返回空数组) */\n getMessages(sessionKey?: string): Message[] {\n const session = this._sessions.get(sessionKey ?? this._sessionKey);\n if (!session) return [];\n // 返回深拷贝,避免外部直接修改会话内部状态\n const messages = session.messages;\n try {\n return structuredClone(messages);\n } catch {\n return JSON.parse(JSON.stringify(messages));\n }\n }\n\n // ─── 核心运行逻辑 ───────────────────────────────────────────────\n\n /** 解析请求路由的会话 key:request.sessionKey ?? 默认会话 key */\n private resolveSessionKey(request: Request): string {\n return request.sessionKey ?? this._sessionKey;\n }\n\n /**\n * 获取(懒创建)会话状态。同一 Runtime 下不同 sessionKey 的消息历史、\n * 串行队列、abort 控制相互独立;共享模型/工具/扩展/转换器。\n * 超过 _maxSessions 时淘汰最久未用的非活动会话(仅清内存态,不删存储)。\n */\n private getSession(key: string): SessionState {\n let session = this._sessions.get(key);\n if (session) {\n // 刷新 LRU 顺序(Map 尾 = 最近使用)\n this._sessions.delete(key);\n this._sessions.set(key, session);\n return session;\n }\n session = createSessionState();\n this._sessions.set(key, session);\n this.evictIdleSessions();\n return session;\n }\n\n /** LRU 淘汰:仅淘汰非活动(未运行、未排队)的最久未用会话 */\n private evictIdleSessions(): void {\n if (this._sessions.size <= this._maxSessions) return;\n for (const [key, session] of this._sessions) {\n if (this._sessions.size <= this._maxSessions) break;\n // 运行中 / 已持有锁(入队待执行)不淘汰\n if (session.isStreaming || session.lockHeld) continue;\n this._sessions.delete(key);\n }\n }\n\n /** 当前活跃的会话 key 列表(含默认会话) */\n getSessionKeys(): string[] {\n return Array.from(this._sessions.keys());\n }\n\n /** 某会话是否存在(内存中) */\n hasSession(sessionKey: string): boolean {\n return this._sessions.has(sessionKey);\n }\n\n async run(request: Request): Promise<Result> {\n // 0. 校验请求\n const validation = validateRequest(request);\n if (!validation.valid) {\n const invalidResult = new ResultBuilder()\n .error(`请求校验失败: ${validation.errors.join('; ')}`)\n .build();\n // 校验失败也要可观测(errorClass='validation'),不进入排队\n await this.emitTelemetry('onRunEnd', {\n traceId: this.newTraceId(),\n sessionKey: this.resolveSessionKey(request),\n request,\n durationMs: 0,\n activeMs: 0,\n queuedMs: 0,\n turnCount: 0,\n result: invalidResult,\n success: false,\n errorClass: 'validation',\n tokens: { input: 0, output: 0 },\n });\n return invalidResult;\n }\n const finalRequest = normalizeRequest(request);\n const sessionKey = this.resolveSessionKey(finalRequest);\n const traceId = this.newTraceId();\n const queuedAt = Date.now();\n\n // 1. 入队前:onRunStart(配合 onRunEnd 求排队时长 queuedMs)\n await this.emitTelemetry('onRunStart', {\n traceId,\n sessionKey,\n request: finalRequest,\n queuedAt,\n });\n\n // 2. 串行化:同一会话的请求依次执行\n const session = this.getSession(sessionKey);\n const release = await this.acquire(session);\n const queuedMs = Date.now() - queuedAt;\n\n try {\n return await this.runWithStorageLock(finalRequest, sessionKey, () =>\n this._run(finalRequest, sessionKey, session, traceId, queuedMs),\n );\n } finally {\n release();\n }\n }\n\n async *stream(request: Request): AsyncGenerator<ResultChunk> {\n // 0. 校验请求\n const validation = validateRequest(request);\n if (!validation.valid) {\n const message = `请求校验失败: ${validation.errors.join('; ')}`;\n await this.emitTelemetry('onRunEnd', {\n traceId: this.newTraceId(),\n sessionKey: this.resolveSessionKey(request),\n request,\n durationMs: 0,\n activeMs: 0,\n queuedMs: 0,\n turnCount: 0,\n result: new ResultBuilder().error(message).build(),\n success: false,\n errorClass: 'validation',\n tokens: { input: 0, output: 0 },\n });\n yield { type: 'error', content: message };\n yield { type: 'done' };\n return;\n }\n const finalRequest = normalizeRequest(request);\n const sessionKey = this.resolveSessionKey(finalRequest);\n const traceId = this.newTraceId();\n const queuedAt = Date.now();\n\n await this.emitTelemetry('onRunStart', {\n traceId,\n sessionKey,\n request: finalRequest,\n queuedAt,\n });\n\n // 1. 串行化\n const session = this.getSession(sessionKey);\n const release = await this.acquire(session);\n const queuedMs = Date.now() - queuedAt;\n\n try {\n yield* this.streamWithStorageLock(finalRequest, sessionKey, () =>\n this._stream(finalRequest, sessionKey, session, traceId, queuedMs),\n );\n } finally {\n release();\n }\n }\n\n /**\n * 非 ephemeral 请求在\"读(load)-改(run)-写(save)\"全程持有存储级锁,\n * 防止多进程并发写同一会话导致 last-write-wins 丢消息。\n * ephemeral / 无锁支持 / 无存储时直接执行。\n */\n private async runWithStorageLock<T>(\n request: Request,\n sessionKey: string,\n fn: () => Promise<T>,\n ): Promise<T> {\n const storage = this._sessionStorage;\n if (request.ephemeral || !storage?.withLock) return fn();\n return storage.withLock(sessionKey, fn);\n }\n\n /** 流式版本:无法用回调包住生成器,改用手动锁(acquire/release) */\n private async *streamWithStorageLock(\n request: Request,\n sessionKey: string,\n gen: () => AsyncGenerator<ResultChunk>,\n ): AsyncGenerator<ResultChunk> {\n const storage = this._sessionStorage;\n if (request.ephemeral || !storage?.acquireLock) {\n yield* gen();\n return;\n }\n const lock = await storage.acquireLock(sessionKey);\n try {\n yield* gen();\n } finally {\n await lock.release();\n }\n }\n\n private async _run(\n request: Request,\n sessionKey: string,\n session: SessionState,\n traceId: string,\n queuedMs: number,\n ): Promise<Result> {\n const activeStartedAt = Date.now();\n\n // 1. 触发 beforeInitialize / afterInitialize\n await this._hooks.beforeInitialize.promise(request);\n await this._hooks.afterInitialize.promise(request);\n\n // 2. beforeRun(waterfall,可修改请求)\n const finalRequest = await this._hooks.beforeRun.promise(request);\n\n // 3. 会话持久化:从存储恢复历史消息(ephemeral 跳过)\n if (!finalRequest.ephemeral) {\n await this.hydrateSession(sessionKey, session);\n }\n\n // 4. 创建编译上下文\n const compilation = this.createCompilation(finalRequest, sessionKey, session, traceId);\n\n // 5. 添加用户消息(含媒体附件)\n compilation.messages.push(this.buildUserMessage(finalRequest));\n\n // 6. 运行对话循环\n try {\n await this.runLoop(compilation, finalRequest, session);\n\n // 7. 构建结果\n const result = this.buildResult(compilation);\n\n // 8. 触发 beforeEmit / afterEmit\n await this._hooks.beforeEmit.promise(result);\n await this._hooks.afterEmit.promise(result);\n\n // 9. 触发 done(携带最终 Request,供钩子按会话配对)\n await this._hooks.done.promise(result, finalRequest);\n\n compilation.completed = true;\n await this.emitRunEnd(finalRequest, sessionKey, compilation, result, queuedMs, activeStartedAt);\n return result;\n } catch (err) {\n const error = err as Error;\n // 非中止错误打印栈,便于线上排障(此前 catch 全部静默转 Result.error,丢栈)\n if (error?.name !== 'AbortError') {\n console.error('[Runtime] 运行失败:', error?.stack ?? error);\n }\n await this._hooks.failed.promise(error, finalRequest);\n\n const result = new ResultBuilder()\n .error(error.message)\n .build();\n await this.emitRunEnd(finalRequest, sessionKey, compilation, result, queuedMs, activeStartedAt);\n return result;\n } finally {\n // 10. 结束前最终保存会话(ephemeral 不持久化;失败不影响运行结果)\n await this.persistSessionSafe(finalRequest, sessionKey);\n }\n }\n\n private async *_stream(\n request: Request,\n sessionKey: string,\n session: SessionState,\n traceId: string,\n queuedMs: number,\n ): AsyncGenerator<ResultChunk> {\n const activeStartedAt = Date.now();\n\n // 1. 钩子\n await this._hooks.beforeInitialize.promise(request);\n await this._hooks.afterInitialize.promise(request);\n const finalRequest = await this._hooks.beforeRun.promise(request);\n\n // 2. 会话持久化:从存储恢复历史消息(ephemeral 跳过)\n if (!finalRequest.ephemeral) {\n await this.hydrateSession(sessionKey, session);\n }\n\n // 3. 创建编译上下文\n const compilation = this.createCompilation(finalRequest, sessionKey, session, traceId);\n\n // 4. 添加用户消息(含媒体附件)\n compilation.messages.push(this.buildUserMessage(finalRequest));\n\n // 5. 流式对话循环\n try {\n for await (const chunk of this.runLoopStream(compilation, finalRequest, session)) {\n yield chunk;\n }\n\n // 6. 构建并触发结果钩子\n const result = this.buildResult(compilation);\n await this._hooks.beforeEmit.promise(result);\n await this._hooks.afterEmit.promise(result);\n await this._hooks.done.promise(result, finalRequest);\n\n yield { type: 'done', result };\n await this.emitRunEnd(finalRequest, sessionKey, compilation, result, queuedMs, activeStartedAt);\n } catch (err) {\n const error = err as Error;\n if (error?.name !== 'AbortError') {\n console.error('[Runtime] 流式运行失败:', error?.stack ?? error);\n }\n await this._hooks.failed.promise(error, finalRequest);\n const result = new ResultBuilder().error(error.message).build();\n yield { type: 'error', content: error.message };\n yield { type: 'done', result };\n await this.emitRunEnd(finalRequest, sessionKey, compilation, result, queuedMs, activeStartedAt);\n } finally {\n await this.persistSessionSafe(finalRequest, sessionKey);\n }\n }\n\n createCompilation(request: Request, sessionKey?: string, session?: SessionState, traceId?: string): Compilation {\n return {\n request,\n graph: createTaskGraph(),\n resources: [],\n messages: (session ?? this.getSession(sessionKey ?? this._sessionKey)).messages,\n completed: false,\n traceId: traceId ?? this.newTraceId(),\n };\n }\n\n async close(): Promise<void> {\n // 等待所有会话的在途任务完成,再清理\n await Promise.allSettled(Array.from(this._sessions.values(), s => s.queue));\n\n for (const session of this._sessions.values()) {\n session.messages = [];\n session.hydrated = false;\n }\n this._sessions.clear();\n this._extensions.clear();\n this._transformers = [];\n }\n\n // ─── 对话循环(同步) ───────────────────────────────────────────\n\n private async runLoop(\n compilation: Compilation,\n request: Request,\n session: SessionState,\n ): Promise<void> {\n session.isStreaming = true;\n session.abortController = new AbortController();\n // 多会话路由:本次循环所属会话(请求携带的 sessionKey 优先)\n const sessionKey = this.resolveSessionKey(request);\n\n try {\n let maxTurns = this._maxTurns;\n let turnCount = 0; // step 长度:实际对话轮数(与 maxTurns 上限解耦)\n\n while (maxTurns-- > 0) {\n turnCount += 1;\n\n // 1. 链式转换上下文(原地替换,保持 session 引用)\n await this.transformMessages(compilation, sessionKey);\n\n // 1.5 阈值触发内置摘要压缩(估算 token 超窗口比例时,先摘要后截断兜底)\n await this.maybeCompactByThreshold(\n compilation, sessionKey, session.abortController!.signal,\n );\n\n // 2. 调用模型(streamModel 内部走统一埋点 streamModelEvents,\n // 含溢出自动恢复:检测 → 截断历史 → 同回合重试)\n const assistantMessage = await this.streamModel(\n compilation,\n session.abortController!.signal,\n sessionKey,\n );\n\n compilation.messages.push(assistantMessage);\n // 3.1 实时持久化:assistant 回复完成即落盘(运行中可查看最新会话)\n await this.persistSessionSafe(request, sessionKey);\n\n // 4. 检查工具调用\n const toolCalls = extractToolCalls(assistantMessage.content);\n\n if (toolCalls.length === 0) {\n break; // 无工具调用,结束循环\n }\n\n // 5. 执行工具(可选并行)\n const outcome = await this.executeToolCalls(\n compilation,\n toolCalls,\n session.abortController!.signal,\n );\n // 5.1 实时持久化:工具结果落盘\n await this.persistSessionSafe(request, sessionKey);\n // 5.2 beforeToolCall/afterToolCall 请求终止:停止循环\n if (outcome.terminate) {\n compilation.terminateReason = outcome.terminateReason ?? 'terminated';\n break;\n }\n }\n\n // 回合上限耗尽(循环条件失效而非 break 退出,maxTurns 已减至 -1):\n // 模型仍请求工具调用但被截断,标记供 buildResult 输出 'max_turns'\n if (maxTurns < 0) compilation.maxTurnsExhausted = true;\n compilation.turnCount = turnCount;\n } finally {\n this.markIdle(session);\n }\n }\n\n // ─── 对话循环(流式) ───────────────────────────────────────────\n\n private async *runLoopStream(\n compilation: Compilation,\n request: Request,\n session: SessionState,\n ): AsyncGenerator<ResultChunk> {\n session.isStreaming = true;\n session.abortController = new AbortController();\n // 多会话路由:本次流式循环所属会话\n const sessionKey = this.resolveSessionKey(request);\n\n try {\n let maxTurns = this._maxTurns;\n let turnCount = 0; // step 长度:实际对话轮数(与 maxTurns 上限解耦)\n\n while (maxTurns-- > 0) {\n turnCount += 1;\n\n // 1. 链式转换上下文(原地替换,保持 session 引用)\n await this.transformMessages(compilation, sessionKey);\n\n // 1.5 阈值触发内置摘要压缩(估算 token 超窗口比例时,先摘要后截断兜底)\n await this.maybeCompactByThreshold(\n compilation, sessionKey, session.abortController!.signal,\n );\n\n // 2. 流式调用模型(统一埋点 + 溢出自动恢复:可恢复的溢出错误\n // 吞掉 error chunk,截断历史后同回合重试)\n const turn = this.modelTurnWithRecovery(\n compilation,\n session.abortController!.signal,\n sessionKey,\n true, // stream 模式:同时统计首 token 延迟\n );\n let turnResult = await turn.next();\n while (!turnResult.done) {\n yield turnResult.value;\n turnResult = await turn.next();\n }\n const assistantMessage = turnResult.value;\n\n if (!assistantMessage) break;\n compilation.messages.push(assistantMessage);\n // 3.1 实时持久化:assistant 回复完成即落盘(运行中可查看最新会话)\n await this.persistSessionSafe(request, sessionKey);\n\n // 4. 检查工具调用\n const toolCalls = extractToolCalls(assistantMessage.content);\n\n if (toolCalls.length === 0) {\n break;\n }\n\n // 5. 执行工具\n for (const toolCall of toolCalls) {\n yield {\n type: 'tool_start',\n toolName: toolCall.name,\n toolCallId: toolCall.id,\n };\n }\n\n const outcome = await this.executeToolCalls(\n compilation,\n toolCalls,\n session.abortController!.signal,\n );\n // 5.1 实时持久化:工具结果落盘\n await this.persistSessionSafe(request, sessionKey);\n\n // 5.2 yield tool_end(block 的工具也产出事件,便于前端展示被拒调用)\n for (let i = 0; i < toolCalls.length; i++) {\n yield {\n type: 'tool_end',\n toolName: toolCalls[i].name,\n toolCallId: toolCalls[i].id,\n isError: this.isErrorResult(outcome.results[i]),\n };\n }\n\n // 5.3 beforeToolCall/afterToolCall 请求终止:tool_end 之后再停止循环\n if (outcome.terminate) {\n compilation.terminateReason = outcome.terminateReason ?? 'terminated';\n break;\n }\n }\n\n // 回合上限耗尽(循环条件失效而非 break 退出,maxTurns 已减至 -1):\n // 模型仍请求工具调用但被截断,标记供 buildResult 输出 'max_turns'\n if (maxTurns < 0) compilation.maxTurnsExhausted = true;\n compilation.turnCount = turnCount;\n } finally {\n this.markIdle(session);\n }\n }\n\n // ─── 工具执行 ───────────────────────────────────────────────────\n\n /** 同步循环:执行工具调用并将结果消息按原顺序追加 */\n private async executeToolCalls(\n compilation: Compilation,\n toolCalls: ToolCallContent[],\n signal: AbortSignal,\n ): Promise<ToolExecutionOutcome> {\n const outcome = await this.runTools(toolCalls, signal, compilation.request, compilation.traceId);\n for (let i = 0; i < toolCalls.length; i++) {\n compilation.messages.push(\n this.buildToolResultMessage(toolCalls[i], outcome.results[i]),\n );\n }\n return outcome;\n }\n\n /**\n * 执行一组工具调用:parallelToolCalls 为 true 时并行,否则串行。\n * 返回 ToolExecutionOutcome:任一工具请求 terminate 即终止整个 run;\n * 串行模式下 terminate 后剩余工具生成 skipped 结果以保持配对完整。\n */\n private async runTools(\n toolCalls: ToolCallContent[],\n signal: AbortSignal,\n request: Request,\n traceId: string,\n ): Promise<ToolExecutionOutcome> {\n const execute = (tc: ToolCallContent) => this.executeTool(tc, signal, request, traceId);\n\n if (this._parallelToolCalls && toolCalls.length > 1) {\n // 并行:全部执行,聚合 terminate(取第一个命中的原因)\n const outcomes = await Promise.all(toolCalls.map(execute));\n const terminated = outcomes.find(o => o.terminate);\n return {\n results: outcomes.map(o => o.result),\n terminate: !!terminated,\n terminateReason: terminated?.terminateReason,\n };\n }\n\n // 串行:依次执行;遇 terminate 后剩余工具跳过执行(生成 skipped 结果保持配对)\n const results: ToolResult[] = [];\n let terminate = false;\n let terminateReason: string | undefined;\n for (const tc of toolCalls) {\n if (terminate) {\n results.push(this.makeSkippedResult(tc));\n continue;\n }\n const outcome = await execute(tc);\n results.push(outcome.result);\n if (outcome.terminate) {\n terminate = true;\n terminateReason = outcome.terminateReason;\n }\n }\n return { results, terminate, terminateReason };\n }\n\n private async executeTool(\n toolCall: ToolCallContent,\n signal: AbortSignal | undefined,\n request: Request,\n traceId: string,\n ): Promise<SingleToolOutcome> {\n const tool = this._globalTools.get(toolCall.name);\n\n if (!tool) {\n return {\n result: {\n content: [createTextContent(`Tool \"${toolCall.name}\" not found`)],\n details: { error: `Tool \"${toolCall.name}\" not found` },\n },\n terminate: false,\n };\n }\n\n // ─── 参数预处理(权限裁决与执行钩子均基于处理后的 args)───\n let args: unknown = toolCall.arguments;\n if (tool.prepareArguments) {\n args = tool.prepareArguments(toolCall.arguments);\n }\n\n // ─── PermissionPolicy:框架级安全底线,先于扩展钩子裁决 ───\n // 未配置策略 → 放行(向后兼容);deny / confirm 未批准 → blocked 结果;\n // pending → 挂起等待外部审批(超时 / run abort 均视为拒绝)\n if (this._permissionPolicy) {\n const permissionReq: PermissionRequest = {\n toolName: toolCall.name,\n permissions: tool.permissions ?? [],\n args,\n sessionKey: request.sessionKey ?? this._sessionKey,\n request,\n shared: this._extensionContext?.shared ?? new Map(),\n };\n const decision = await this._permissionPolicy.check(permissionReq);\n let allowed = decision === 'allow';\n if (decision === 'confirm') {\n allowed = this._permissionPolicy.confirm\n ? await this._permissionPolicy.confirm(permissionReq)\n : false;\n }\n if (decision === 'pending') {\n // 挂起等待外部审批(异步 Human-in-the-loop);\n // 未配置审批管理器 → 保守拒绝(与 confirm 未提供回调的行为一致)\n if (this._approvals) {\n const approval = this._approvals.create(permissionReq, {\n timeoutMs: this._approvalTimeoutMs,\n signal,\n });\n await this.emitTelemetry('onApprovalPending', {\n traceId,\n sessionKey: permissionReq.sessionKey,\n approvalId: approval.id,\n toolName: toolCall.name,\n permissions: permissionReq.permissions,\n args,\n expiresAt: approval.expiresAt,\n });\n const outcome = await this._approvals.wait(approval);\n allowed = outcome.status === 'approved';\n await this.emitTelemetry('onApprovalResolved', {\n traceId,\n sessionKey: permissionReq.sessionKey,\n approvalId: approval.id,\n toolName: toolCall.name,\n outcome: outcome.status,\n waitedMs: outcome.waitedMs,\n });\n } else {\n allowed = false;\n }\n }\n if (!allowed) {\n const reason = `permission denied by policy for tool \"${toolCall.name}\"`;\n await this.emitTelemetry('onPermissionDenied', {\n traceId,\n sessionKey: permissionReq.sessionKey,\n toolName: toolCall.name,\n permissions: permissionReq.permissions,\n args,\n reason,\n });\n return {\n result: this.makeBlockedResult(reason),\n terminate: false,\n };\n }\n }\n\n // ─── 工具超时信号:权限裁决(含审批挂起)完成后起表,\n // 审批等待不占用工具执行超时 ───\n const { signal: timedSignal, clear } = withTimeoutSignal(signal, this._toolTimeoutMs);\n try {\n // ─── beforeToolCall:参数校验后、执行前(可 block / terminate / 改写 args)───\n const beforeCtx = this.buildToolCallContext(toolCall, tool, args, request, timedSignal);\n const before: BeforeToolCallDecision = await this._hooks.beforeToolCall.promise(\n { block: false, terminate: false, args },\n beforeCtx,\n );\n\n if (before.terminate) {\n const reason = before.reason ?? 'terminated by beforeToolCall';\n return {\n result: this.makeBlockedResult(reason),\n terminate: true,\n terminateReason: reason,\n };\n }\n if (before.block) {\n const reason = before.reason ?? 'blocked by beforeToolCall';\n return {\n result: this.makeBlockedResult(reason),\n terminate: false,\n };\n }\n // 允许 beforeToolCall 改写参数\n args = before.args;\n\n // ─── 执行工具 ───\n const toolStartedAt = Date.now();\n let result: ToolResult;\n try {\n result = await tool.execute(toolCall.id, args, timedSignal);\n } catch (err) {\n const message = (err as Error)?.message ?? String(err);\n result = {\n content: [createTextContent(message)],\n details: { error: message },\n };\n }\n\n const status = toolResultStatus(result);\n await this.emitTelemetry('onToolCall', {\n traceId,\n spanId: newSpanId(),\n sessionKey: request.sessionKey ?? this._sessionKey,\n toolName: toolCall.name,\n args,\n durationMs: Date.now() - toolStartedAt,\n result,\n success: status === 'ok',\n status,\n errorClass:\n status === 'error'\n ? (errorClassFromMessage(String((result.details as { error?: unknown })?.error ?? '')) as ErrorClass | undefined) ?? 'tool_error'\n : undefined,\n });\n\n // ─── afterToolCall:执行后、事件发出前(可改写 result / terminate)───\n // 用更新后的 args 重建 ctx,让 afterToolCall 看到改写后的参数\n const afterCtx = this.buildToolCallContext(toolCall, tool, args, request, timedSignal);\n const after: AfterToolCallDecision = await this._hooks.afterToolCall.promise(\n { result, terminate: false },\n afterCtx,\n );\n\n return {\n result: after.result,\n terminate: after.terminate,\n terminateReason: after.terminate ? 'terminated by afterToolCall' : undefined,\n };\n } finally {\n clear();\n }\n }\n\n private isErrorResult(result: ToolResult): boolean {\n return !!(result.details && typeof result.details === 'object' && 'error' in result.details);\n }\n\n /** beforeToolCall 阻断/终止时生成拒绝结果(非执行错误,isError=false) */\n private makeBlockedResult(reason: string): ToolResult {\n return {\n content: [createTextContent(`[blocked] ${reason}`)],\n details: { blocked: true, reason },\n };\n }\n\n /** 串行模式下前序工具 terminate 后,剩余工具生成 skipped 结果保持配对 */\n private makeSkippedResult(toolCall: ToolCallContent): ToolResult {\n return {\n content: [createTextContent(`[skipped] run terminated by prior tool: ${toolCall.name}`)],\n details: { skipped: true, toolName: toolCall.name },\n };\n }\n\n /** 构建 ToolCallContext:beforeToolCall/afterToolCall 的调用上下文 */\n private buildToolCallContext(\n toolCall: ToolCallContent,\n tool: Tool,\n args: unknown,\n request: Request,\n signal: AbortSignal,\n ): ToolCallContext {\n return {\n toolCall,\n tool,\n args,\n sessionKey: request.sessionKey ?? this._sessionKey,\n request,\n shared: this._extensionContext?.shared ?? new Map(),\n signal,\n };\n }\n\n private buildToolResultMessage(\n toolCall: ToolCallContent,\n result: ToolResult,\n ): ToolResultMessage {\n return {\n role: 'toolResult',\n content: result.content,\n toolCallId: toolCall.id,\n toolName: toolCall.name,\n isError: this.isErrorResult(result),\n timestamp: Date.now(),\n };\n }\n\n private buildUserMessage(request: Request): UserMessage {\n if (request.media && request.media.length > 0) {\n const blocks: ContentBlock[] = [\n createTextContent(request.message),\n ...request.media.filter(Boolean).map(buildImageContent),\n ];\n return {\n role: 'user',\n content: blocks,\n timestamp: Date.now(),\n };\n }\n return {\n role: 'user',\n content: request.message,\n timestamp: Date.now(),\n };\n }\n\n // ─── 内部方法 ───────────────────────────────────────────────────\n\n /**\n * 获取同一会话的执行锁:返回 release 函数,调用后释放。\n * 同一 sessionKey 的 run/stream 会串行执行,避免消息数组交错、\n * abortController 互相覆盖、hydrate 竞态。\n */\n private async acquire(session: SessionState): Promise<() => void> {\n let release!: () => void;\n const prev = session.queue;\n session.queue = new Promise<void>(resolve => {\n release = () => resolve();\n });\n await prev;\n session.lockHeld = true;\n return () => {\n session.lockHeld = false;\n release();\n };\n }\n\n /** 标记会话空闲并唤醒所有 waitForIdle 等待者 */\n private markIdle(session: SessionState): void {\n session.isStreaming = false;\n session.abortController = null;\n if (session.idleResolvers.length > 0) {\n const resolvers = session.idleResolvers.splice(0);\n for (const resolve of resolvers) resolve();\n }\n }\n\n // ─── 会话持久化 ─────────────────────────────────────────────────\n\n /** 从存储懒加载会话(串行化后无竞态,每个会话仅恢复一次) */\n private async hydrateSession(\n sessionKey: string,\n session: SessionState,\n ): Promise<void> {\n if (!this._sessionStorage) return;\n if (session.hydrated) return;\n session.hydrated = true;\n\n const stored = await this._sessionStorage.load(sessionKey);\n if (!stored) return;\n\n session.messages = stored.messages;\n session.createdAt = stored.createdAt;\n }\n\n /** 整体保存指定会话(ephemeral 跳过;失败不影响运行结果) */\n private async persistSession(\n sessionKey: string,\n session: SessionState,\n ): Promise<void> {\n if (!this._sessionStorage) return;\n\n const stored: StoredSession = {\n key: sessionKey,\n version: SESSION_VERSION,\n messages: session.messages,\n model: this.deriveModel(session.messages),\n usage: this.sumUsage(session.messages),\n createdAt: session.createdAt,\n updatedAt: new Date().toISOString(),\n };\n await this._sessionStorage.save(sessionKey, stored);\n }\n\n /**\n * 实时持久化指定会话:每轮 assistant 回复/工具结果完成后调用,\n * 让运行中的会话随时可被持久化数据观测到。ephemeral 跳过;\n * 存储失败仅告警,不影响对话循环继续。\n */\n private async persistSessionSafe(\n request: Request,\n sessionKey: string,\n ): Promise<void> {\n if (request.ephemeral || !this._sessionStorage) return;\n try {\n const session = this._sessions.get(sessionKey);\n if (!session) return; // 会话已被淘汰/删除,跳过\n await this.persistSession(sessionKey, session);\n } catch (err) {\n console.warn('[Runtime] 会话持久化失败:', (err as Error)?.message);\n }\n }\n\n /** 从消息中推导最后使用的模型 */\n private deriveModel(messages: Message[]): SessionModel | null {\n for (let i = messages.length - 1; i >= 0; i--) {\n const msg = messages[i];\n if (msg.role === 'assistant' && (msg as AssistantMessage).model) {\n return {\n provider: (msg as AssistantMessage).provider ?? this._model.provider,\n modelId: (msg as AssistantMessage).model as string,\n };\n }\n }\n return null;\n }\n\n /** 汇总所有 assistant 消息的 token 用量(含 cache) */\n private sumUsage(messages: Message[]): Usage {\n const usage = createEmptyUsage();\n for (const msg of messages) {\n if (msg.role === 'assistant') {\n const u = (msg as AssistantMessage).usage;\n if (u) {\n usage.input += u.input;\n usage.output += u.output;\n usage.total += u.total;\n usage.cacheRead = (usage.cacheRead ?? 0) + (u.cacheRead ?? 0);\n usage.cacheWrite = (usage.cacheWrite ?? 0) + (u.cacheWrite ?? 0);\n usage.reasoning = (usage.reasoning ?? 0) + (u.reasoning ?? 0);\n }\n }\n }\n return usage;\n }\n\n /** 链式执行上下文转换器(按数组顺序,上一个输出作为下一个输入) */\n private async transformMessages(\n compilation: Compilation,\n sessionKey: string,\n ): Promise<void> {\n if (this._transformers.length === 0) {\n return;\n }\n\n let resources = messagesToResources(compilation.messages);\n const context: TransformContext = {\n graph: compilation.graph,\n runtime: {\n sessionKey,\n turn: compilation.messages.length,\n contextWindow: this._model.contextWindow,\n maxTokens: this._model.maxTokens,\n contextBudgetRatio: this._contextBudgetRatio,\n },\n };\n\n for (const transformer of this._transformers) {\n try {\n resources = await transformer.transform(resources, context);\n } catch (err) {\n // 单个转换器失败时跳过,保持当前资源不变,但需可观测\n console.warn(\n `[Runtime] 转换器 \"${transformer.name}\" 失败,已跳过:`,\n (err as Error)?.message ?? err,\n );\n }\n }\n\n const messages = resourcesToMessages(resources);\n // 原地替换而非重新赋值:createCompilation 将 session.messages 按引用共享,\n // 重新赋值会导致后续 push 的 assistant/tool 消息脱离会话(持久化丢失)\n compilation.messages.splice(0, compilation.messages.length, ...messages);\n }\n\n private buildContext(messages: Message[]): Context {\n const tools = Array.from(this._globalTools.values());\n return {\n systemPrompt: this._systemPrompt,\n // compactionSummary / stateSnapshot 为内部扩展 role,provider 适配层\n // 仅支持 user/assistant/toolResult,发出前统一转为带标注的 user 消息\n messages: messages\n .filter(m => m.role !== 'system')\n .map(m => {\n const role = (m as { role: string }).role;\n if (role === 'compactionSummary') return this.compactionSummaryToUser(m);\n if (role === 'stateSnapshot') return this.stateSnapshotToUser(m);\n return m;\n }),\n tools: tools.length > 0 ? tools : undefined,\n };\n }\n\n /** compactionSummary 消息 → user 消息(所有 provider 均兼容 user role) */\n private compactionSummaryToUser(msg: Message): Message {\n const text = typeof msg.content === 'string' ? msg.content : extractText(msg.content);\n return {\n role: 'user',\n content: `${COMPACTION_USER_PREFIX}\\n${text}`,\n timestamp: msg.timestamp,\n } as Message;\n }\n\n /** stateSnapshot 消息 → user 消息(所有 provider 均兼容 user role) */\n private stateSnapshotToUser(msg: Message): Message {\n const text = typeof msg.content === 'string' ? msg.content : extractText(msg.content);\n return {\n role: 'user',\n content: `${STATE_SNAPSHOT_USER_PREFIX}\\n${text}`,\n timestamp: msg.timestamp,\n } as Message;\n }\n\n private async streamModel(\n compilation: Compilation,\n signal: AbortSignal,\n sessionKey: string,\n ): Promise<AssistantMessage> {\n // 含溢出自动恢复(modelTurnWithRecovery);非流式路径丢弃事件 chunk\n const turn = this.modelTurnWithRecovery(compilation, signal, sessionKey, false);\n let r = await turn.next();\n while (!r.done) r = await turn.next();\n return r.value ?? this.emptyAssistantMessage();\n }\n\n /** 空的 assistant 消息(流异常中断无 done/error 事件时的兜底,与旧 streamModel 行为一致) */\n private emptyAssistantMessage(): AssistantMessage {\n return {\n role: 'assistant',\n content: [],\n stopReason: 'stop',\n usage: createEmptyUsage(),\n model: this._model.id,\n provider: this._model.provider,\n timestamp: Date.now(),\n };\n }\n\n /**\n * 单回合模型调用 + 上下文溢出自动恢复闭环。\n *\n * 检测(isContextOverflow,统一传入 model.contextWindow / content / maxTokens,\n * 覆盖显式错误 / 静默溢出 / 输入截断溢出 / 输出 thinking 耗尽 / 输出打满 五模式)\n * → 丢弃失败的 assistant 消息 → 截断会话历史 → 同回合重试(不消耗回合数,\n * 上限 OVERFLOW_RECOVERY_LIMIT):\n *\n * - 显式错误 / 零产出截断溢出 / thinking 耗尽溢出 / 输出打满溢出:丢弃失败\n * 消息后重试;流式路径吞掉可恢复的 error chunk(消费者看不到瞬态错误),\n * 不可恢复时补发。\n * - 静默溢出(stop + 有完整产出):保留回复,仅压缩旧上下文供后续轮次。\n * - 恢复耗尽或单请求超窗(无可丢弃):返回最后一次错误消息,维持旧行为。\n *\n * 流式路径 yield 模型事件 chunk;非流式路径由 streamModel 消费(chunk 丢弃)。\n * 返回最终 assistant 消息;无 done/error 事件时返回 null。\n */\n private async *modelTurnWithRecovery(\n compilation: Compilation,\n signal: AbortSignal,\n sessionKey: string,\n stream: boolean,\n ): AsyncGenerator<ResultChunk, AssistantMessage | null> {\n const contextWindow = this._model.contextWindow;\n const maxTokens = this._model.maxTokens;\n let recoveries = 0;\n\n // 把 content / maxTokens 一并塞入 OverflowProbeMessage,供 isContextOverflow\n // 识别「只有 thinking 没有有效产出」和「output 打满 maxTokens」两种可恢复截断。\n const toProbe = (m: AssistantMessage) => ({\n stopReason: m.stopReason,\n errorMessage: m.errorMessage,\n usage: m.usage,\n content: m.content,\n maxTokens,\n });\n\n while (true) {\n let assistant: AssistantMessage | null = null;\n /** 被吞掉的可恢复溢出错误消息(等待恢复决策:重试则丢弃,不可恢复则补发 chunk) */\n let suppressed: AssistantMessage | null = null;\n\n for await (const event of this.streamModelEvents(compilation, signal, stream)) {\n if (event.type === 'error') {\n const msg = event.message;\n if (\n recoveries < OVERFLOW_RECOVERY_LIMIT &&\n isContextOverflow(toProbe(msg), contextWindow)\n ) {\n suppressed = msg; // 吞掉 error chunk,稍后恢复重试\n continue;\n }\n const chunk = this.streamEventToChunk(event);\n if (chunk) yield chunk;\n assistant = msg;\n } else {\n const chunk = this.streamEventToChunk(event);\n if (chunk) yield chunk;\n if (event.type === 'done') assistant = event.message;\n }\n }\n\n const final = assistant ?? suppressed;\n if (!final) return null; // 流异常中断(无 done/error 事件)\n\n if (isContextOverflow(toProbe(final), contextWindow)) {\n // failed:需要丢弃上轮并立即重试的场景\n // - stop=error 或 output=0:原有判定\n // - stop=length 但 content 里只有 thinking(零有效产出):reasoning 预算耗尽\n // 必须重跑(catalog 已给更高 maxTokens,但仍有可能碰到边界)\n // - stop=length 且 output 打满 maxTokens:回复被截断,丢弃并压缩后重试\n const output = final.usage?.output ?? 0;\n const blocks = Array.isArray(final.content) ? final.content : null;\n const hasMeaningfulText = blocks?.some(\n (b) => b.type === 'text' && 'text' in b && typeof b.text === 'string' && b.text.trim().length > 0,\n );\n const hasToolCall = blocks?.some((b) => b.type === 'toolCall');\n const thinkingOnly = blocks\n ? !hasMeaningfulText && !hasToolCall && blocks.some((b) => b.type === 'thinking')\n : false;\n const outputFull = maxTokens > 0 && output >= Math.floor(maxTokens * 0.95);\n\n const failed = final.stopReason === 'error' || output === 0 || thinkingOnly || outputFull;\n if (failed && recoveries < OVERFLOW_RECOVERY_LIMIT) {\n recoveries += 1;\n if (await this.recoverFromOverflow(compilation, recoveries, sessionKey, signal)) {\n const reason =\n thinkingOnly ? 'thinking 耗尽' : outputFull ? 'output 打满' : final.stopReason;\n console.warn(\n `[Runtime] 上下文溢出(${reason}),已压缩历史并同回合重试(${recoveries}/${OVERFLOW_RECOVERY_LIMIT})`,\n );\n await this.emitTelemetry('onRetry', {\n traceId: compilation.traceId,\n provider: this._model.provider,\n modelId: this._model.id,\n attempt: recoveries,\n errorClass: 'context-overflow',\n delayMs: 0,\n willRetry: true,\n });\n continue; // 同回合重试(不消耗回合数)\n }\n // 无可丢弃(单条请求即超窗):补发被吞的 error chunk 后原样返回\n if (suppressed) {\n yield { type: 'error', content: final.errorMessage || '模型调用出错' };\n }\n return final;\n }\n if (failed) return final; // 恢复次数耗尽,维持旧行为(错误消息落库)\n // 静默溢出(stop + 有完整产出):保留回复,仅压缩旧上下文供后续轮次\n await this.recoverFromOverflow(compilation, 1, sessionKey, signal);\n console.warn('[Runtime] 检测到静默上下文溢出(usage 超窗),已压缩历史消息');\n }\n\n return final;\n }\n }\n\n /**\n * 计算溢出恢复的截断点:按 token 预算从最旧消息开始丢弃。\n *\n * 预算随恢复次数指数收紧(contextWindow × ratio × 0.5^recovery),且每次\n * 至少丢弃可丢弃部分的一半,保证重试规模必然小于上次溢出(token 估算\n * 偏小时也成立)。最后一条消息(当前请求/最新产出)始终保留。\n * 返回被压缩段的结束下标(messages[0..split) 为被压缩段);0 = 已到\n * 最小集,单条请求即超窗,无法恢复。\n */\n private computeOverflowSplit(messages: Message[], recovery: number): number {\n const contextWindow = this._model.contextWindow;\n if (!contextWindow || contextWindow <= 0) return 0;\n const target = Math.max(\n Math.floor(contextWindow * this._contextBudgetRatio * 0.5 ** recovery),\n 1,\n );\n\n let total = 0;\n for (const m of messages) total += estimateMessageTokens(m);\n\n const droppable = messages.length - 1; // 最后一条必保\n if (droppable <= 0) return 0;\n // 至少丢弃一半可丢弃消息,保证恢复必然缩小规模(估算偏小时的兜底)\n const mustDrop = Math.max(Math.floor(droppable / 2), 1);\n\n let dropUntil = 0;\n while (dropUntil < droppable && (dropUntil < mustDrop || total > target)) {\n total -= estimateMessageTokens(messages[dropUntil]);\n dropUntil += 1;\n }\n return dropUntil;\n }\n\n /**\n * 溢出恢复:摘要优先、硬截断兜底(原地修改会话消息)。\n *\n * 开启 compaction(默认)时,被压缩段先尝试 LLM 摘要替换(compactionSummary\n * 消息),摘要失败或序列化超摘要预算(请求本身会超窗)则降级纯丢弃;\n * 关闭 compaction 时维持旧行为纯截断。截断/摘要后均经 ensureToolPairing\n * 修复保留段的工具配对。返回是否执行了恢复动作(false = 无可压缩,单条\n * 请求即超窗)。\n */\n private async recoverFromOverflow(\n compilation: Compilation,\n recovery: number,\n sessionKey: string,\n signal: AbortSignal,\n ): Promise<boolean> {\n const messages = compilation.messages;\n const split = this.computeOverflowSplit(messages, recovery);\n if (split <= 0) return false;\n\n const useCompaction =\n !!this._compaction &&\n this._compaction.enabled !== false &&\n this._compaction.onOverflow !== false;\n if (useCompaction) {\n await this.compactOrTruncate(\n messages, split, sessionKey, compilation.traceId, signal, 'overflow',\n );\n return true;\n }\n\n const kept = ensureToolPairing(messages.slice(split));\n messages.splice(0, messages.length, ...kept);\n return true;\n }\n\n /**\n * 阈值触发内置摘要压缩(runLoop 每轮模型调用前检查,低频):\n * 估算 token 超过 contextWindow × triggerRatio(默认 contextBudgetRatio)\n * 时,将历史压缩到 targetRatio(默认 0.5)——最新消息保留目标的一半,\n * 其余部分摘要替换;摘要失败降级硬截断。\n */\n private async maybeCompactByThreshold(\n compilation: Compilation,\n sessionKey: string,\n signal: AbortSignal,\n ): Promise<void> {\n // 未配置 compaction = 保持旧行为(不压缩,溢出时硬截断兜底)\n if (!this._compaction || this._compaction.enabled === false) return;\n const contextWindow = this._model.contextWindow;\n if (!contextWindow || contextWindow <= 0) return;\n\n const messages = compilation.messages;\n const triggerTokens = Math.floor(\n contextWindow * (this._compaction?.triggerRatio ?? this._contextBudgetRatio),\n );\n\n let total = 0;\n for (const m of messages) total += estimateMessageTokens(m);\n if (total <= triggerTokens) return;\n\n // 从尾部累计保留最新消息,保留量为压缩目标的一半\n const targetTokens = Math.floor(\n contextWindow * (this._compaction?.targetRatio ?? 0.5),\n );\n const keepTokens = Math.max(Math.floor(targetTokens / 2), 1);\n\n let kept = 0;\n let split = messages.length;\n for (let i = messages.length - 1; i >= 0; i--) {\n if (kept >= keepTokens) {\n split = i + 1;\n break;\n }\n kept += estimateMessageTokens(messages[i]);\n split = i;\n }\n // 无可压缩段(最新消息已占满保留预算):等待下一轮\n if (split <= 0 || split >= messages.length) return;\n\n const mode = await this.compactOrTruncate(\n messages, split, sessionKey, compilation.traceId, signal, 'threshold',\n );\n console.warn(\n `[Runtime] 上下文达阈值(约 ${total} token > ${triggerTokens}),已${mode === 'summary' ? '摘要压缩' : '截断'}历史`,\n );\n }\n\n /**\n * 手动压缩指定会话(交互命令 /compact 等):跳过阈值判断,\n * 直接将历史压缩至 targetRatio 保留量(复用 maybeCompactByThreshold\n * 的保留段计算与 compactOrTruncate 执行路径),压缩后持久化。\n */\n async compact(sessionKey?: string): Promise<'summary' | 'truncate' | null> {\n if (!this._compaction || this._compaction.enabled === false) return null;\n const key = sessionKey ?? this._sessionKey;\n const session = this.getSession(key);\n const messages = session.messages;\n if (messages.length === 0) return null;\n\n const contextWindow = this._model.contextWindow;\n if (!contextWindow || contextWindow <= 0) return null;\n\n // 与 maybeCompactByThreshold 相同的保留段计算:保留 target 的一半(最新消息)\n const targetTokens = Math.floor(\n contextWindow * (this._compaction.targetRatio ?? 0.5),\n );\n const keepTokens = Math.max(Math.floor(targetTokens / 2), 1);\n\n let kept = 0;\n let split = messages.length;\n for (let i = messages.length - 1; i >= 0; i--) {\n if (kept >= keepTokens) {\n split = i + 1;\n break;\n }\n kept += estimateMessageTokens(messages[i]);\n split = i;\n }\n // 无可压缩段(最新消息已占满保留预算)\n if (split <= 0 || split >= messages.length) return null;\n\n const mode = await this.compactOrTruncate(\n messages, split, key, `manual-${Date.now().toString(36)}`,\n new AbortController().signal, 'threshold',\n );\n try {\n await this.persistSession(key, session);\n } catch (err) {\n console.warn('[Runtime] 手动压缩后持久化失败:', (err as Error)?.message);\n }\n return mode;\n }\n\n /**\n * 执行压缩:messages[0..split) 为被压缩段,原地替换。\n *\n * 摘要成功 → 被压缩段替换为单条 compactionSummary 消息(资源层 pinned);\n * 序列化超摘要预算或摘要调用失败 → 降级纯丢弃(旧行为)。两种路径均对\n * 保留段执行 ensureToolPairing(被压缩段边界可能截断工具配对)。上报\n * onCompaction 遥测。\n */\n private async compactOrTruncate(\n messages: Message[],\n split: number,\n sessionKey: string,\n traceId: string,\n signal: AbortSignal,\n trigger: 'threshold' | 'overflow',\n ): Promise<'summary' | 'truncate'> {\n const compacted = messages.slice(0, split);\n const tokensBefore = messages.reduce((sum, m) => sum + estimateMessageTokens(m), 0);\n\n let mode: 'summary' | 'truncate' = 'truncate';\n let summaryText = '';\n\n const summaryEnabled = !!this._compaction && this._compaction.enabled !== false;\n if (summaryEnabled && compacted.length > 0) {\n const summaryBudget = Math.floor(\n this._model.contextWindow * COMPACTION_SUMMARY_BUDGET_RATIO,\n );\n const inputText = compacted\n .map(m => messageToSummaryLine(m))\n .filter(line => line.length > 0)\n .join('\\n');\n // 预算判断:被压缩段超预算时摘要请求自身必然超窗,不发 doomed 请求\n if (inputText && estimateTextTokens(inputText) <= summaryBudget) {\n const summary = await this.summarizeMessages(\n inputText, sessionKey, traceId, signal,\n );\n if (summary && summary.trim()) {\n summaryText = summary.trim();\n mode = 'summary';\n }\n }\n }\n\n let tokensAfter: number;\n if (mode === 'summary') {\n const summaryMsg = this.createCompactionSummaryMessage(summaryText);\n const kept = ensureToolPairing(messages.slice(split));\n messages.splice(0, messages.length, summaryMsg, ...kept);\n tokensAfter = estimateMessageTokens(summaryMsg)\n + kept.reduce((sum, m) => sum + estimateMessageTokens(m), 0);\n } else {\n const kept = ensureToolPairing(messages.slice(split));\n messages.splice(0, messages.length, ...kept);\n tokensAfter = kept.reduce((sum, m) => sum + estimateMessageTokens(m), 0);\n }\n\n await this.emitTelemetry('onCompaction', {\n traceId,\n sessionKey,\n mode,\n trigger,\n tokensBefore,\n tokensAfter,\n droppedMessages: split,\n summary: mode === 'summary' ? summaryText : undefined,\n } satisfies CompactionTelemetryInfo);\n return mode;\n }\n\n /**\n * 调用模型生成摘要文本。失败(模型错误/中止/空产出)返回 null,\n * 由调用方降级硬截断——摘要失败不影响主流程。\n */\n private async summarizeMessages(\n inputText: string,\n sessionKey: string,\n traceId: string,\n signal: AbortSignal,\n ): Promise<string | null> {\n const prompt = this._compaction?.prompt ?? DEFAULT_COMPACTION_PROMPT;\n const context: Context = {\n systemPrompt: prompt,\n messages: [{ role: 'user', content: inputText, timestamp: Date.now() }],\n };\n\n const startedAt = Date.now();\n let text = '';\n let usage: Usage | undefined;\n let failed = false;\n try {\n for await (const event of this._streamFn(this._model, context, { signal })) {\n if (event.type === 'text_delta') {\n text += event.delta;\n } else if (event.type === 'error') {\n failed = true;\n usage = event.message.usage;\n break;\n } else if (event.type === 'done') {\n usage = event.message.usage;\n if (event.message.stopReason === 'error') failed = true;\n // 非流式式产出兜底:done 前无 text_delta 时从消息体取文本\n if (!text) text = extractText(event.message.content);\n break;\n }\n }\n } catch {\n return null; // 摘要异常(网络/中止等):降级截断\n }\n if (failed || !text.trim()) return null;\n\n // 摘要调用也计入 onModelCall(成本对账):独立 span,stream=false\n await this.emitTelemetry('onModelCall', {\n traceId,\n spanId: newSpanId(),\n sessionKey,\n modelId: this._model.id,\n attempts: 1,\n inputTokens: usage?.input ?? estimateTextTokens(inputText),\n outputTokens: usage?.output ?? estimateTextTokens(text),\n durationMs: Date.now() - startedAt,\n stream: false,\n });\n return text;\n }\n\n /** 构造 compactionSummary 消息(内部扩展 role,发出前经 buildContext 转 user) */\n private createCompactionSummaryMessage(text: string): Message {\n return {\n role: 'compactionSummary',\n content: text,\n timestamp: Date.now(),\n } as unknown as Message;\n }\n\n /**\n * 统一模型调用埋点生成器:run()(streamModel)与 stream()(runLoopStream)两路径共用。\n * 职责:模型调用计时、spanId、attempts 累计、onRetry 转发、onModelCall 上报\n * (含 tokens / cost / errorClass / ttft)。\n */\n private async *streamModelEvents(\n compilation: Compilation,\n signal: AbortSignal,\n stream: boolean,\n ): AsyncGenerator<StreamEvent> {\n const sessionKey = this.resolveSessionKey(compilation.request);\n const modelStartedAt = Date.now();\n const spanId = newSpanId();\n let attempts = 1; // 含首次调用\n let ttftAt: number | undefined;\n let lastAssistant: AssistantMessage | undefined;\n\n const options: StreamOptions = { signal };\n if (this._thinkingLevel !== 'off' && this._model.reasoning) {\n options.reasoning = this._thinkingLevel;\n }\n // provider 内部 retry() 真正退避时回调:累计 attempts + 转发 onRetry 事件\n options.onRetryAttempt = (info) => {\n attempts += 1;\n void this.emitTelemetry('onRetry', {\n traceId: compilation.traceId,\n spanId, // P2:重试明细关联到本模型调用 span\n provider: this._model.provider,\n modelId: this._model.id,\n attempt: info.attempt,\n errorClass: classifyError(info.error),\n status: statusOfRetryError(info.error),\n delayMs: info.delayMs,\n willRetry: true,\n });\n };\n\n try {\n // beforeModelCall:插件可在此改写最终 Context(如 skills 目录注入 / 工具附加)\n const context = await this._hooks.beforeModelCall.promise(\n this.buildContext(compilation.messages),\n );\n for await (const event of this._streamFn(this._model, context, options)) {\n if (stream && event.type === 'text_delta' && ttftAt === undefined) {\n ttftAt = Date.now();\n }\n if (event.type === 'done' || event.type === 'error') {\n lastAssistant = event.message;\n }\n yield event;\n }\n } finally {\n const assistant = lastAssistant;\n const errorClass = assistant?.errorMessage\n ? (errorClassFromMessage(assistant.errorMessage) as ErrorClass | undefined) ?? 'unknown'\n : undefined;\n await this.emitTelemetry('onModelCall', {\n traceId: compilation.traceId,\n spanId,\n sessionKey,\n modelId: this._model.id,\n attempts,\n inputTokens: assistant?.usage?.input ?? 0,\n outputTokens: assistant?.usage?.output ?? 0,\n cacheRead: assistant?.usage?.cacheRead,\n cacheWrite: assistant?.usage?.cacheWrite,\n durationMs: Date.now() - modelStartedAt,\n stream,\n errorClass,\n });\n // 流式:记录首个模型调用的首 token 延迟(run 级 onRunEnd 读取)\n if (stream && ttftAt !== undefined && compilation.ttftMs === undefined) {\n compilation.ttftMs = ttftAt - modelStartedAt;\n }\n }\n }\n\n /**\n * 触发遥测回调。全可选、失败不阻断主流程。\n */\n private async emitTelemetry<E extends keyof Telemetry>(\n event: E,\n info: Parameters<NonNullable<Telemetry[E]>>[0],\n ): Promise<void> {\n const fn = this._telemetry?.[event];\n if (!fn) return;\n try {\n await Promise.resolve((fn as (arg: unknown) => unknown)(info));\n } catch (err) {\n // 遥测失败不应影响主流程\n console.warn(`[aipack] telemetry \"${String(event)}\" 上报失败:`, err);\n }\n }\n\n /** traceId 生成:优先用注入的生成器(测试可确定性) */\n private newTraceId(): string {\n return this._traceIdGenerator ? this._traceIdGenerator() : newTraceId();\n }\n\n /** 组装并上报 run 级完成事件(_run/_stream 内部统一调用) */\n private async emitRunEnd(\n request: Request,\n sessionKey: string,\n compilation: Compilation,\n result: Result,\n queuedMs: number,\n activeStartedAt: number,\n ): Promise<void> {\n const activeMs = Date.now() - activeStartedAt;\n await this.emitTelemetry('onRunEnd', {\n traceId: compilation.traceId,\n sessionKey,\n // 请求未显式指定 model 时补实际模型(模型排行按 run 级 requests 统计,缺省会落入 'unknown')\n request: request.model ? request : { ...request, model: this._model.id },\n durationMs: activeMs + queuedMs,\n activeMs,\n queuedMs,\n turnCount: compilation.turnCount ?? 0,\n result,\n success: result.success,\n errorClass: this.runErrorClass(compilation),\n tokens: {\n input: result.usage.input ?? 0,\n output: result.usage.output ?? 0,\n cacheRead: result.usage.cacheRead,\n cacheWrite: result.usage.cacheWrite,\n },\n ttftMs: compilation.ttftMs,\n });\n }\n\n /** run 级错误分类:terminate → 'terminated';否则只看最后一条 assistant 消息(与 buildResult 的 result.success 同口径) */\n private runErrorClass(compilation: Compilation): ErrorClass | undefined {\n if (compilation.terminateReason) return 'terminated';\n const messages = compilation.messages;\n for (let i = messages.length - 1; i >= 0; i--) {\n const m = messages[i];\n if (m.role === 'assistant') {\n // 最后一条 assistant 无 errorMessage → run 成功(早期轮次失败已被后续轮次恢复,不判错误)\n if (!(m as AssistantMessage).errorMessage) return undefined;\n const cls = errorClassFromMessage((m as AssistantMessage).errorMessage!);\n return (cls as ErrorClass | undefined) ?? 'unknown';\n }\n }\n return undefined;\n }\n\n private buildResult(compilation: Compilation): Result {\n const messages = compilation.messages;\n let content = '';\n let stopReason = 'completed';\n let error: string | undefined;\n const toolsUsed: string[] = [];\n const usage: Record<string, number> = {};\n\n for (const msg of messages) {\n if (msg.role === 'assistant') {\n const assistant = msg as AssistantMessage;\n content = extractText(assistant.content);\n stopReason = assistant.stopReason ?? 'completed';\n error = assistant.errorMessage;\n if (assistant.usage) {\n usage.input = (usage.input ?? 0) + assistant.usage.input;\n usage.output = (usage.output ?? 0) + assistant.usage.output;\n usage.total = (usage.total ?? 0) + assistant.usage.total;\n if (assistant.usage.cacheRead) usage.cacheRead = (usage.cacheRead ?? 0) + assistant.usage.cacheRead;\n if (assistant.usage.cacheWrite) usage.cacheWrite = (usage.cacheWrite ?? 0) + assistant.usage.cacheWrite;\n }\n }\n if (msg.role === 'toolResult') {\n const toolMsg = msg as ToolResultMessage;\n if (!toolsUsed.includes(toolMsg.toolName)) {\n toolsUsed.push(toolMsg.toolName);\n }\n }\n }\n\n // 填充资源快照(此前 Result.resources 永远 undefined)\n const resources = messagesToResources(messages);\n\n const builder = new ResultBuilder()\n .content(content)\n .toolsUsed(toolsUsed)\n .usage(usage)\n .stopReason(stopReason)\n .error(error)\n .resources(resources)\n .metadata('traceId', compilation.traceId);\n\n // beforeToolCall/afterToolCall 请求终止:覆盖 stopReason 并记录原因\n if (compilation.terminateReason) {\n builder.stopReason('terminated').metadata('terminateReason', compilation.terminateReason);\n }\n\n // 回合上限耗尽:调用方据此区分\"正常完成\"与\"被截断\"(模型仍想调用工具)\n if (compilation.maxTurnsExhausted) {\n builder.stopReason('max_turns').metadata('maxTurns', true);\n }\n\n return builder.build();\n }\n\n private streamEventToChunk(event: StreamEvent): ResultChunk | null {\n switch (event.type) {\n case 'text_delta':\n return { type: 'text', content: event.delta };\n case 'thinking_delta':\n return { type: 'thinking', content: event.delta };\n case 'error':\n // 模型调用错误(无 API Key / 鉴权失败 / 网络错误 / HTTP 4xx-5xx 等)\n // 以 error 事件流入,errorMessage 已由 stream-openai/anthropic 填好。\n return {\n type: 'error',\n content: event.message.errorMessage || '模型调用出错',\n };\n default:\n return null;\n }\n }\n\n // ─── 便捷方法 ───────────────────────────────────────────────────\n\n /** 终止指定会话的运行(默认会话;会话不存在为 no-op) */\n abort(sessionKey?: string): void {\n this._sessions.get(sessionKey ?? this._sessionKey)?.abortController?.abort();\n }\n\n /** 检查指定会话是否正在运行(默认会话;会话不存在返回 false) */\n isBusy(sessionKey?: string): boolean {\n return this._sessions.get(sessionKey ?? this._sessionKey)?.isStreaming ?? false;\n }\n\n /** 等待指定会话空闲(默认会话;基于 promise,无轮询) */\n async waitForIdle(sessionKey?: string, timeoutMs?: number): Promise<void> {\n const session = this._sessions.get(sessionKey ?? this._sessionKey);\n if (!session || !session.isStreaming) return;\n\n if (timeoutMs === undefined) {\n await new Promise<void>(resolve => {\n session.idleResolvers.push(resolve);\n });\n return;\n }\n\n // 带超时等待:超时 reject 并把自己从等待队列移除,避免 markIdle 唤醒残留 resolver\n await new Promise<void>((resolve, reject) => {\n const resolver = () => {\n clearTimeout(timer);\n resolve();\n };\n const timer = setTimeout(() => {\n const i = session.idleResolvers.indexOf(resolver);\n if (i >= 0) session.idleResolvers.splice(i, 1);\n reject(new Error(\n `[Runtime] waitForIdle 超时(${timeoutMs}ms): ${sessionKey ?? 'default'}`,\n ));\n }, timeoutMs);\n session.idleResolvers.push(resolver);\n });\n }\n\n /** 清除指定会话消息(仅内存;下次 run 会从存储恢复) */\n clearSession(sessionKey?: string): void {\n const session = this._sessions.get(sessionKey ?? this._sessionKey);\n if (!session) return;\n session.messages = [];\n session.hydrated = false;\n }\n\n /** 删除指定会话(内存 + 存储),返回是否删除成功 */\n async deleteSession(sessionKey?: string): Promise<boolean> {\n const key = sessionKey ?? this._sessionKey;\n const session = this._sessions.get(key);\n // 等待在途任务完成后再清理\n if (session) {\n await session.queue;\n this._sessions.delete(key);\n }\n if (!this._sessionStorage) return true;\n const storage = this._sessionStorage;\n if (!storage.withLock) return storage.delete(key);\n // 删除同样持存储锁,避免与另一进程的写入竞争\n return storage.withLock(key, () => storage.delete(key));\n }\n}\n\n// ─── 工厂函数 ─────────────────────────────────────────────────────\n\nexport function createRuntime(options?: RuntimeOptions): Runtime {\n return AgentRuntime.create(options);\n}\n","/**\n * core/event-stream.ts - 流式事件队列工具\n *\n * 统一各执行器 stream() 的 push-pull 事件队列实现:\n * 后台执行图逻辑,事件按发生顺序产出给消费者,\n * 同时同步分发到外部事件监听(on() API 的 eventSink)。\n */\n\nimport type { MultiAgentEvent } from './types';\n\n/**\n * 创建流式事件生成器。\n *\n * @param execute - 后台执行函数,通过 emit 发出事件;\n * 返回的 Promise 决不 reject(错误应转换为 graph_error 事件后 resolve)\n * @param sink - 外部事件监听(可选),异常会被吞掉以防中断事件传播\n */\nexport function createEventStream(\n execute: (emit: (event: MultiAgentEvent) => void) => Promise<void>,\n sink?: (event: MultiAgentEvent) => void,\n): AsyncGenerator<MultiAgentEvent> {\n const eventQueue: MultiAgentEvent[] = [];\n let resolveEvent: (() => void) | null = null;\n let done = false;\n\n const emit = (event: MultiAgentEvent) => {\n eventQueue.push(event);\n if (sink) {\n try { sink(event); } catch { /* 防止监听器异常中断事件传播 */ }\n }\n resolveEvent?.();\n };\n\n const graphPromise = execute(emit).finally(() => {\n done = true;\n resolveEvent?.();\n });\n\n return (async function* (): AsyncGenerator<MultiAgentEvent> {\n while (!done || eventQueue.length > 0) {\n if (eventQueue.length > 0) {\n yield eventQueue.shift()!;\n } else {\n await new Promise<void>(resolve => { resolveEvent = resolve; });\n }\n }\n await graphPromise;\n })();\n}\n\n/** 将执行 Promise 的成功/失败转换为事件(供 createEventStream 的 execute 使用) */\nexport function settleAsEvent(\n promise: Promise<unknown>,\n emit: (event: MultiAgentEvent) => void,\n onError?: (errorMsg: string) => void,\n): Promise<void> {\n return promise.then(\n () => { /* 成功事件由调用方在 promise 内部发出 */ },\n (err) => {\n const errorMsg = err instanceof Error ? err.message : String(err);\n onError?.(errorMsg);\n emit({ type: 'graph_error', error: errorMsg });\n },\n );\n}\n","/**\n * core/executor.ts - 图执行引擎\n *\n * 负责 AgentGraph 的执行逻辑:从入口节点出发,\n * 根据边条件遍历图,依次执行各节点的 Runtime。\n */\n\nimport type { Runtime, RuntimeOptions, Result, Request } from '@aipack-ai/agent';\nimport { createRuntime } from '@aipack-ai/agent';\nimport { createRequest } from '@aipack-ai/agent';\nimport type {\n AgentNode,\n AgentEdge,\n SharedContext,\n MultiAgentResult,\n MultiAgentEvent,\n NodeExecutionState,\n GraphExecutionState,\n GraphExecutionOpts,\n} from './types';\nimport { createSharedContext, storeOriginalInput } from './context';\nimport { createEventStream } from './event-stream';\n\n// ─── GraphAbortedError: 中止信号 ───────────────────────────────\n\n/** abort() 触发的中止错误,run() 会将其转换为 stopReason='aborted' 的结果 */\nexport class GraphAbortedError extends Error {\n constructor() {\n super('AgentGraph: 执行已被中止');\n this.name = 'GraphAbortedError';\n }\n}\n\n// ─── toInputText: 提取输入文本(供事件摘要使用) ─────────────────\n\n/** 将 string | Request 输入提取为文本(agent_start 事件的 input 摘要字段) */\nexport function toInputText(input: string | Request): string {\n return typeof input === 'string' ? input : input.message;\n}\n\n// ─── NodeTimeoutError: 节点超时 ─────────────────────────────────\n\n/** 节点执行超时错误(timeoutMs 触发,可配合 retry 重试) */\nexport class NodeTimeoutError extends Error {\n constructor(nodeId: string, timeoutMs: number) {\n super(`AgentGraph: 节点 \"${nodeId}\" 执行超时(${timeoutMs}ms)`);\n this.name = 'NodeTimeoutError';\n }\n}\n\n// ─── ensureRuntime: 确保 AgentNode 拥有 Runtime 实例 ────────────\n\nconst runtimeCache = new WeakMap<AgentNode, Runtime>();\n\nexport function ensureRuntime(node: AgentNode): Runtime {\n let rt = runtimeCache.get(node);\n if (rt) return rt;\n\n if (typeof (node.runtime as Runtime).run === 'function') {\n rt = node.runtime as Runtime;\n } else {\n rt = createRuntime(node.runtime as RuntimeOptions);\n }\n runtimeCache.set(node, rt);\n return rt;\n}\n\n// ─── executeNode: 执行单个 Agent 节点 ───────────────────────────\n\n/** 单次节点执行(不含重试) */\nasync function executeNodeOnce(\n node: AgentNode,\n req: Request,\n): Promise<Result> {\n const runtime = ensureRuntime(node);\n\n if (node.timeoutMs != null && node.timeoutMs > 0) {\n let timer: ReturnType<typeof setTimeout> | undefined;\n try {\n return await Promise.race([\n runtime.run(req),\n new Promise<never>((_, reject) => {\n timer = setTimeout(() => reject(new NodeTimeoutError(node.id, node.timeoutMs!)), node.timeoutMs);\n }),\n ]);\n } finally {\n if (timer !== undefined) clearTimeout(timer);\n }\n }\n return runtime.run(req);\n}\n\nexport async function executeNode(\n node: AgentNode,\n input: string | Request,\n ctx: SharedContext,\n): Promise<Result> {\n // 构建 Request\n let req: Request;\n if (typeof input === 'string') {\n req = createRequest(input, { sessionKey: `multi-agent:${node.id}` });\n } else {\n req = { ...input, sessionKey: input.sessionKey ?? `multi-agent:${node.id}` };\n }\n\n // 重试循环(节点级 retry 配置,超时/失败均计入重试)\n const maxAttempts = Math.max(1, node.retry?.maxAttempts ?? 1);\n const backoffMs = node.retry?.backoffMs ?? 0;\n\n let lastErr: unknown;\n let succeeded: Result | undefined;\n\n for (let attempt = 1; attempt <= maxAttempts; attempt++) {\n if (attempt > 1 && backoffMs > 0) {\n await new Promise(resolve => setTimeout(resolve, backoffMs));\n }\n try {\n succeeded = await executeNodeOnce(node, req);\n break;\n } catch (err) {\n lastErr = err;\n }\n }\n\n if (succeeded === undefined) {\n throw lastErr;\n }\n\n // 输出映射\n if (node.outputMapping) {\n node.outputMapping(succeeded, ctx);\n }\n\n return succeeded;\n}\n\n// ─── resolveInput: 解析下一个节点的输入 ─────────────────────────\n\nexport function resolveInput(\n edge: AgentEdge | undefined,\n prevResult: Result,\n ctx: SharedContext,\n node: AgentNode,\n originalInput: string | Request,\n): string | Request {\n // 优先级:edge.transform > node.inputMapping > 传递上一个结果\n if (edge?.transform) {\n return edge.transform(prevResult, ctx);\n }\n if (node.inputMapping) {\n return node.inputMapping(ctx);\n }\n return prevResult.content;\n}\n\n// ─── findNextEdges: 查找满足条件的出边 ─────────────────────────\n\nexport function findNextEdges(\n fromId: string,\n edges: AgentEdge[],\n result: Result,\n ctx: SharedContext,\n): AgentEdge[] {\n const outEdges = edges.filter(e => e.from === fromId);\n const matched: AgentEdge[] = [];\n\n for (const edge of outEdges) {\n // 无条件边默认匹配\n if (!edge.condition || edge.condition(result, ctx)) {\n matched.push(edge);\n }\n }\n return matched;\n}\n\n// ─── GraphExecutor: 图执行器 ─────────────────────────────────────\n\nexport class GraphExecutor {\n private nodes: Map<string, AgentNode> = new Map();\n private edges: AgentEdge[] = [];\n private entryId?: string;\n private finishCondition?: (ctx: SharedContext) => boolean;\n private abortController = new AbortController();\n /** 外部事件监听(on() API 的底层接线),事件会同步分发 */\n private eventSink?: (event: MultiAgentEvent) => void;\n /** 并行分支最大并发数(默认不限制) */\n private concurrency: number;\n /** 单节点最大访问次数(环图防死循环) */\n private maxVisitsPerNode: number;\n private state: GraphExecutionState = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n\n constructor(opts?: GraphExecutionOpts) {\n this.concurrency = opts?.concurrency ?? Infinity;\n this.maxVisitsPerNode = opts?.maxVisitsPerNode ?? 10;\n }\n\n addNode(node: AgentNode): this {\n this.nodes.set(node.id, node);\n this.state.nodeStates.set(node.id, 'pending');\n return this;\n }\n\n addEdge(edge: AgentEdge): this {\n this.edges.push(edge);\n return this;\n }\n\n setEntry(agentId: string): this {\n this.entryId = agentId;\n return this;\n }\n\n setFinish(condition: (ctx: SharedContext) => boolean): this {\n this.finishCondition = condition;\n return this;\n }\n\n /** 注入外部事件监听(由 AgentGraph 实现的 on() 接线) */\n setEventSink(sink?: (event: MultiAgentEvent) => void): this {\n this.eventSink = sink;\n return this;\n }\n\n getState(): GraphExecutionState {\n // 深拷贝快照:防止外部通过返回值篡改内部状态\n return {\n ...this.state,\n nodeStates: new Map(this.state.nodeStates),\n nodeResults: new Map(this.state.nodeResults),\n };\n }\n\n abort(): void {\n this.abortController.abort();\n }\n\n /** 每次 run/stream 前重置中止信号,避免上一次的 abort 永久失效 */\n private resetAbortController(): void {\n this.abortController = new AbortController();\n }\n\n /** 每次 run/stream 前重置执行状态,避免残留上一次的 nodeStates/结果 */\n private resetState(): void {\n this.state = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n for (const id of this.nodes.keys()) {\n this.state.nodeStates.set(id, 'pending');\n }\n }\n\n private throwIfAborted(): void {\n if (this.abortController.signal.aborted) {\n throw new GraphAbortedError();\n }\n }\n\n /** 同步执行图 */\n async run(input: string | Request): Promise<MultiAgentResult> {\n // 前置校验:入口节点相关错误直接抛出\n if (!this.entryId) {\n throw new Error('AgentGraph: 入口节点未设置,请调用 setEntry()');\n }\n if (!this.nodes.has(this.entryId)) {\n throw new Error(`AgentGraph: 入口节点 \"${this.entryId}\" 不存在`);\n }\n\n this.resetAbortController();\n this.resetState();\n const ctx = createSharedContext({\n meta: { traceId: `ma-${Date.now()}`, startTime: Date.now() },\n });\n storeOriginalInput(ctx, input);\n const emit = this.eventSink ?? (() => {});\n\n try {\n const result = await this.executeGraph(input, ctx, emit);\n emit({ type: 'graph_done', result });\n return result;\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.error = errorMsg;\n if (err instanceof GraphAbortedError) {\n // 中止:保留最后完成的节点输出\n const lastCompleted = [...this.state.nodeResults.values()].at(-1);\n const abortedResult: MultiAgentResult = {\n content: lastCompleted?.content ?? '',\n lastAgentId: this.state.currentAgentId ?? '',\n agentResults: new Map(this.state.nodeResults),\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: 'aborted',\n context: ctx,\n success: false,\n error: err.message,\n };\n emit({ type: 'graph_error', error: err.message });\n return abortedResult;\n }\n emit({ type: 'graph_error', error: errorMsg });\n return {\n content: '',\n lastAgentId: this.state.currentAgentId ?? '',\n agentResults: new Map(this.state.nodeResults),\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: 'error',\n context: ctx,\n success: false,\n error: errorMsg,\n };\n }\n }\n\n /** 流式执行图 */\n stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n // 前置校验\n if (!this.entryId) {\n throw new Error('AgentGraph: 入口节点未设置,请调用 setEntry()');\n }\n if (!this.nodes.has(this.entryId)) {\n throw new Error(`AgentGraph: 入口节点 \"${this.entryId}\" 不存在`);\n }\n\n this.resetAbortController();\n this.resetState();\n const ctx = createSharedContext({\n meta: { traceId: `ma-${Date.now()}`, startTime: Date.now() },\n });\n storeOriginalInput(ctx, input);\n\n return createEventStream(\n emit => this.executeGraph(input, ctx, emit).then(\n (result) => { emit({ type: 'graph_done', result }); },\n (err) => {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.error = errorMsg;\n emit({ type: 'graph_error', error: errorMsg });\n },\n ),\n this.eventSink,\n );\n }\n\n /** 核心执行逻辑 */\n private async executeGraph(\n input: string | Request,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n ): Promise<MultiAgentResult> {\n const entryNode = this.nodes.get(this.entryId!)!;\n\n let currentId = this.entryId!;\n let currentInput: string | Request = input;\n let lastResult: Result | undefined;\n let lastAgentId = currentId;\n let stepsCompleted = 0;\n const totalUsage: Record<string, number> = {};\n\n // 执行入口节点\n this.state.currentAgentId = currentId;\n this.state.nodeStates.set(currentId, 'running');\n emit({ type: 'agent_start', agentId: currentId, agentName: entryNode.name, input: toInputText(currentInput) });\n\n try {\n lastResult = await executeNode(entryNode, currentInput, ctx);\n this.state.nodeStates.set(currentId, 'completed');\n this.state.nodeResults.set(currentId, lastResult);\n this.mergeUsage(totalUsage, lastResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: currentId, agentName: entryNode.name, result: lastResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(currentId, 'failed');\n emit({ type: 'agent_error', agentId: currentId, agentName: entryNode.name, error: errorMsg });\n throw err;\n }\n\n lastAgentId = currentId;\n\n // 检查终止条件\n if (this.finishCondition?.(ctx)) {\n return this.buildResult(lastResult!, lastAgentId, ctx, totalUsage, stepsCompleted, 'finish_condition');\n }\n\n // ── 沿边遍历(wave 模式:支持并行分支 fan-out) ─────────────\n // frontier:上一轮完成的节点,等待评估出边\n // 单条边匹配 → 顺序执行(与旧语义一致)\n // 多条边匹配 → 并行执行(受 concurrency 限制),发出 parallel_start/parallel_done\n let frontier: Array<{ id: string; result: Result }> = [{ id: currentId, result: lastResult }];\n // 允许环形(如review→coder),用计数防止无限循环\n const visitCount = new Map<string, number>();\n let stopReason = 'completed';\n\n while (frontier.length > 0) {\n // 中止检查:abort() 后不再遍历后续节点\n this.throwIfAborted();\n\n // 收集本 wave 的候选边(按 frontier 顺序,目标节点去重:同目标只执行一次,取首条入边)\n const candidates: Array<{ edge: AgentEdge; from: { id: string; result: Result }; node: AgentNode }> = [];\n const seenTargets = new Set<string>();\n for (const from of frontier) {\n const nextEdges = findNextEdges(from.id, this.edges, from.result, ctx);\n for (const edge of nextEdges) {\n if (seenTargets.has(edge.to)) continue;\n seenTargets.add(edge.to);\n const nextNode = this.nodes.get(edge.to);\n if (!nextNode) {\n throw new Error(`AgentGraph: 目标节点 \"${edge.to}\" 不存在`);\n }\n candidates.push({ edge, from, node: nextNode });\n }\n }\n\n if (candidates.length === 0) {\n // 无出边,图执行完毕\n break;\n }\n\n // 访问上限检查(安全阀,逐候选过滤)\n const allowed = [];\n let truncated = false;\n for (const c of candidates) {\n const count = (visitCount.get(c.edge.to) ?? 0) + 1;\n if (count > this.maxVisitsPerNode) {\n truncated = true;\n continue;\n }\n visitCount.set(c.edge.to, count);\n allowed.push(c);\n }\n if (allowed.length === 0) {\n // 安全截断而非正常完成,通过 stopReason 区分\n if (truncated) stopReason = 'max_visits_exceeded';\n break;\n }\n\n // 解析各候选的输入\n const tasks = allowed.map(c => ({\n node: c.node,\n input: resolveInput(c.edge, c.from.result, ctx, c.node, input),\n fromId: c.edge.from,\n }));\n\n // 执行本 wave\n let waveResults: Array<{ id: string; result: Result }>;\n if (tasks.length === 1) {\n // 单分支:顺序执行(保持与历史语义一致)\n const t = tasks[0];\n this.state.currentAgentId = t.node.id;\n this.state.nodeStates.set(t.node.id, 'running');\n emit({ type: 'edge_traversed', from: t.fromId, to: t.node.id });\n emit({ type: 'agent_start', agentId: t.node.id, agentName: t.node.name, input: toInputText(t.input) });\n let result: Result;\n try {\n result = await executeNode(t.node, t.input, ctx);\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(t.node.id, 'failed');\n emit({ type: 'agent_error', agentId: t.node.id, agentName: t.node.name, error: errorMsg });\n throw err;\n }\n this.state.nodeStates.set(t.node.id, 'completed');\n this.state.nodeResults.set(t.node.id, result);\n this.mergeUsage(totalUsage, result.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: t.node.id, agentName: t.node.name, result });\n waveResults = [{ id: t.node.id, result }];\n } else {\n // 多分支:并行执行(fail-fast,受 concurrency 限制)\n waveResults = await this.executeWave(tasks, ctx, emit, totalUsage);\n stepsCompleted += waveResults.length;\n this.state.stepsCompleted = stepsCompleted;\n }\n\n lastResult = waveResults[waveResults.length - 1].result;\n lastAgentId = waveResults[waveResults.length - 1].id;\n frontier = waveResults;\n\n // 检查终止条件\n if (this.finishCondition?.(ctx)) {\n return this.buildResult(lastResult!, lastAgentId, ctx, totalUsage, stepsCompleted, 'finish_condition');\n }\n }\n\n return this.buildResult(lastResult!, lastAgentId, ctx, totalUsage, stepsCompleted, stopReason);\n }\n\n /** 并行执行一个 wave 的节点(fail-fast + concurrency 限流) */\n private async executeWave(\n tasks: Array<{ node: AgentNode; input: string | Request; fromId: string }>,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Array<{ id: string; result: Result }>> {\n const results: Array<{ id: string; result: Result }> = [];\n emit({ type: 'parallel_start', agentIds: tasks.map(t => t.node.id) });\n\n const runOne = async (t: { node: AgentNode; input: string | Request; fromId: string }): Promise<void> => {\n this.state.currentAgentId = t.node.id;\n this.state.nodeStates.set(t.node.id, 'running');\n emit({ type: 'edge_traversed', from: t.fromId, to: t.node.id });\n emit({ type: 'agent_start', agentId: t.node.id, agentName: t.node.name, input: toInputText(t.input) });\n try {\n const result = await executeNode(t.node, t.input, ctx);\n this.state.nodeStates.set(t.node.id, 'completed');\n this.state.nodeResults.set(t.node.id, result);\n this.mergeUsage(totalUsage, result.usage);\n results.push({ id: t.node.id, result });\n emit({ type: 'agent_result', agentId: t.node.id, agentName: t.node.name, result });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(t.node.id, 'failed');\n emit({ type: 'agent_error', agentId: t.node.id, agentName: t.node.name, error: errorMsg });\n throw err;\n }\n };\n\n if (this.concurrency >= tasks.length) {\n await Promise.all(tasks.map(t => runOne(t)));\n } else {\n // 限流并发池\n let index = 0;\n const executing = new Set<Promise<void>>();\n const enqueue = (): Promise<void> | null => {\n if (index >= tasks.length) return null;\n const i = index++;\n const p: Promise<void> = runOne(tasks[i]).finally(() => { executing.delete(p); });\n executing.add(p);\n p.catch(() => {}); // fail-fast 提前退出后防 unhandledRejection\n return p;\n };\n for (let i = 0; i < this.concurrency && index < tasks.length; i++) {\n enqueue();\n }\n while (executing.size > 0) {\n await Promise.race(executing);\n enqueue();\n }\n }\n\n emit({ type: 'parallel_done', results: new Map(results.map(r => [r.id, r.result])) });\n return results;\n }\n\n private buildResult(\n lastResult: Result,\n lastAgentId: string,\n ctx: SharedContext,\n totalUsage: Record<string, number>,\n stepsCompleted: number,\n stopReason: string,\n ): MultiAgentResult {\n this.state.finished = true;\n return {\n content: lastResult.content,\n lastAgentId,\n agentResults: new Map(this.state.nodeResults),\n totalUsage,\n stepsCompleted,\n stopReason,\n context: ctx,\n success: lastResult.success,\n error: lastResult.error,\n };\n }\n\n private mergeUsage(total: Record<string, number>, usage: Record<string, number>): void {\n for (const [key, value] of Object.entries(usage)) {\n total[key] = (total[key] ?? 0) + value;\n }\n }\n}\n","/**\n * core/graph.ts - AgentGraph 实现\n *\n * 基于声明式 API(addNode/addEdge/setEntry/setFinish)构建图,\n * 委托 GraphExecutor 执行。\n */\n\nimport type { Request } from '@aipack-ai/agent';\nimport type { AgentNode, AgentEdge, AgentGraph, SharedContext, EventListener, MultiAgentResult, MultiAgentEvent, GraphExecutionState, GraphExecutionOpts } from './types';\nimport { GraphExecutor } from './executor';\nimport { SimpleEventBus } from './context';\n\n// 中止错误类型透传导出(供使用方 instanceof 判断)\nexport { GraphAbortedError } from './executor';\n\n// ─── AgentGraphImpl ──────────────────────────────────────────────\n\nclass AgentGraphImpl implements AgentGraph {\n private executor: GraphExecutor;\n /** on() 注册的监听器,按 MultiAgentEvent.type 分发 */\n private bus = new SimpleEventBus();\n\n constructor(opts?: GraphExecutionOpts) {\n this.executor = new GraphExecutor(opts);\n }\n\n addNode(node: AgentNode): this {\n this.executor.addNode(node);\n return this;\n }\n\n addEdge(edge: AgentEdge): this {\n this.executor.addEdge(edge);\n return this;\n }\n\n setEntry(agentId: string): this {\n this.executor.setEntry(agentId);\n return this;\n }\n\n setFinish(condition: (ctx: SharedContext) => boolean): this {\n this.executor.setFinish(condition);\n return this;\n }\n\n async run(input: string | Request): Promise<MultiAgentResult> {\n this.executor.setEventSink(event => this.bus.emit(event.type, event));\n return this.executor.run(input);\n }\n\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n this.executor.setEventSink(event => this.bus.emit(event.type, event));\n yield* this.executor.stream(input);\n }\n\n getState(): GraphExecutionState {\n return this.executor.getState();\n }\n\n abort(): void {\n this.executor.abort();\n }\n\n on(event: string, listener: EventListener): this {\n this.bus.on(event, listener);\n return this;\n }\n}\n\n// ─── createAgentGraph 工厂函数 ───────────────────────────────────\n\n/** 创建空的 AgentGraph,通过链式调用定义图结构 */\nexport function createAgentGraph(opts?: GraphExecutionOpts): AgentGraph {\n return new AgentGraphImpl(opts);\n}\n","/**\n * patterns/pipeline.ts - Pipeline 顺序链模式\n *\n * 将多个 Agent 按顺序串联:A → B → C → ...\n * 前一个 Agent 的输出作为后一个 Agent 的输入。\n */\n\nimport type { AgentNode, AgentGraph, PipelineOpts } from '../core/types';\nimport { createAgentGraph } from '../core/graph';\n\n/**\n * 创建 Pipeline 顺序链\n *\n * @param agents - 按顺序排列的 Agent 节点列表\n * @param opts - Pipeline 配置选项\n * @returns AgentGraph 实例\n */\nexport function createPipeline(\n agents: AgentNode[],\n opts?: PipelineOpts,\n): AgentGraph {\n if (agents.length === 0) {\n throw new Error('Pipeline: 至少需要一个 Agent 节点');\n }\n\n const graph = createAgentGraph();\n\n // 添加所有节点\n for (const agent of agents) {\n graph.addNode(agent);\n }\n\n // 设置入口\n graph.setEntry(agents[0].id);\n\n // 添加顺序边\n for (let i = 0; i < agents.length - 1; i++) {\n const from = agents[i];\n const to = agents[i + 1];\n\n graph.addEdge({\n from: from.id,\n to: to.id,\n // 边上的转换:将前一个Agent的输出传递给下一个Agent\n transform: opts?.outputTransform\n ? (result, ctx) => opts.outputTransform!(result, ctx)\n : undefined,\n });\n }\n\n return graph;\n}\n","/**\n * patterns/router.ts - Router 条件路由模式\n *\n * 路由器 Agent 根据输入选择目标 Agent 执行。\n * 结构:Router → (条件匹配) → Target Agent\n */\n\nimport type { AgentNode, AgentGraph, RouterOpts } from '../core/types';\nimport { createAgentGraph } from '../core/graph';\nimport type { Result } from '@aipack-ai/agent';\n\n/**\n * 创建 Router 条件路由\n *\n * @param router - 路由器 Agent(负责意图识别)\n * @param targets - 目标 Agent 列表\n * @param opts - Router 配置选项(必须提供 resolve 函数)\n * @returns AgentGraph 实例\n */\nexport function createRouter(\n router: AgentNode,\n targets: AgentNode[],\n opts: RouterOpts,\n): AgentGraph {\n if (targets.length === 0) {\n throw new Error('Router: 至少需要一个目标 Agent');\n }\n\n const graph = createAgentGraph();\n\n // 添加路由器节点\n graph.addNode(router);\n\n // 添加目标节点\n for (const target of targets) {\n graph.addNode(target);\n }\n\n // 设置入口为路由器\n graph.setEntry(router.id);\n\n // 构建目标 ID 集合,用于校验与兜底路由\n const targetIds = new Set(targets.map(t => t.id));\n\n // resolve 包装:resolve 返回未知 ID 时回退到 defaultTarget(兜底路由)\n const defaultTarget = opts.defaultTarget && targetIds.has(opts.defaultTarget)\n ? opts.defaultTarget\n : undefined;\n const resolveTarget = (routerResult: Result): string => {\n const resolvedId = opts.resolve(routerResult);\n if (targetIds.has(resolvedId)) return resolvedId;\n return defaultTarget ?? resolvedId;\n };\n\n // 路由器到每个目标的条件边\n for (const target of targets) {\n graph.addEdge({\n from: router.id,\n to: target.id,\n // 条件:从路由器结果中解析目标ID(含 defaultTarget 兜底),匹配当前目标\n condition: (routerResult, _ctx) => {\n return resolveTarget(routerResult) === target.id;\n },\n // 转换:决定传给目标Agent的输入\n transform: (_routerResult, _ctx) => {\n // 默认传递原始输入(passOriginalInput=true)\n // 原始输入在 graph run 时传入,这里通过 blackboard 获取\n const originalInput = _ctx.blackboard.get('__original_input__');\n if (opts.passOriginalInput === false) {\n // 传递路由器的输出\n return _routerResult.content;\n }\n return (originalInput as string) ?? _routerResult.content;\n },\n });\n }\n\n return graph;\n}\n","/**\n * core/supervisor-executor.ts - Supervisor 执行器\n *\n * 实现 Supervisor 层级委派模式:\n * 1. Supervisor Agent 先执行,拆解任务并写入 SharedContext\n * 2. Worker Agents 根据调度策略执行(parallel / sequential / auto)\n * 3. 汇总所有 Worker 结果\n *\n * 失败策略(onWorkerError):\n * - 'fail-fast'(默认):任一 Worker 失败立即中止,整体返回 error\n * - 'skip':容忍失败,跳过失败 Worker,结果暴露 failedAgents 与 stopReason='partial_failure'\n */\n\nimport type { Result, Request } from '@aipack-ai/agent';\nimport type {\n AgentNode,\n SharedContext,\n MultiAgentResult,\n MultiAgentEvent,\n SupervisorOpts,\n GraphExecutionState,\n} from './types';\nimport { createSharedContext, storeOriginalInput } from './context';\nimport { executeNode, GraphAbortedError, toInputText } from './executor';\nimport { createEventStream } from './event-stream';\n\n// ─── SupervisorExecutor ──────────────────────────────────────────\n\nexport class SupervisorExecutor {\n private supervisorNode: AgentNode;\n private workerNodes: AgentNode[];\n private opts: Required<Omit<SupervisorOpts, 'onWorkerError'>> & {\n onWorkerError: NonNullable<SupervisorOpts['onWorkerError']>;\n };\n private abortController = new AbortController();\n /** 外部事件监听(on() API 的底层接线) */\n private eventSink?: (event: MultiAgentEvent) => void;\n /** 最近一次 run 中失败的 Worker ID(onWorkerError='skip' 时使用) */\n private failedAgents: string[] = [];\n private state: GraphExecutionState = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n\n constructor(supervisor: AgentNode, workers: AgentNode[], opts?: SupervisorOpts) {\n this.supervisorNode = supervisor;\n this.workerNodes = workers;\n this.opts = {\n schedule: opts?.schedule ?? 'parallel',\n concurrency: opts?.concurrency ?? Infinity,\n passOriginalInput: opts?.passOriginalInput ?? true,\n onWorkerError: opts?.onWorkerError ?? 'fail-fast',\n };\n\n // 初始化状态\n this.state.nodeStates.set(supervisor.id, 'pending');\n for (const w of workers) {\n this.state.nodeStates.set(w.id, 'pending');\n }\n }\n\n getState(): GraphExecutionState {\n // 深拷贝快照:防止外部通过返回值篡改内部状态\n return {\n ...this.state,\n nodeStates: new Map(this.state.nodeStates),\n nodeResults: new Map(this.state.nodeResults),\n };\n }\n\n /** 注入外部事件监听(由 AgentGraph 实现的 on() 接线) */\n setEventSink(sink?: (event: MultiAgentEvent) => void): this {\n this.eventSink = sink;\n return this;\n }\n\n abort(): void {\n this.abortController.abort();\n }\n\n /** 每次 run/stream 前重置中止信号、失败记录与执行状态 */\n private resetRun(): void {\n this.abortController = new AbortController();\n this.failedAgents = [];\n this.state = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n this.state.nodeStates.set(this.supervisorNode.id, 'pending');\n for (const w of this.workerNodes) {\n this.state.nodeStates.set(w.id, 'pending');\n }\n }\n\n private throwIfAborted(): void {\n if (this.abortController.signal.aborted) {\n throw new GraphAbortedError();\n }\n }\n\n /** 执行 Supervisor 模式 */\n async run(input: string | Request): Promise<MultiAgentResult> {\n this.resetRun();\n const ctx = createSharedContext({\n meta: { traceId: `sv-${Date.now()}`, startTime: Date.now() },\n });\n\n // 存储原始输入到 blackboard\n if (this.opts.passOriginalInput) {\n storeOriginalInput(ctx, input);\n }\n\n const emit = this.eventSink ?? (() => {});\n\n try {\n const result = await this.executeSupervisor(input, ctx, emit);\n emit({ type: 'graph_done', result });\n return result;\n } catch (err) {\n const result = this.buildErrorResult(ctx, err);\n emit({ type: 'graph_error', error: result.error ?? '' });\n return result;\n }\n }\n\n /** 流式执行 Supervisor 模式 */\n stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n this.resetRun();\n const ctx = createSharedContext({\n meta: { traceId: `sv-${Date.now()}`, startTime: Date.now() },\n });\n\n if (this.opts.passOriginalInput) {\n storeOriginalInput(ctx, input);\n }\n\n return createEventStream(\n emit => this.executeSupervisor(input, ctx, emit).then(\n (result) => { emit({ type: 'graph_done', result }); },\n (err) => {\n this.state.error = err instanceof Error ? err.message : String(err);\n emit({ type: 'graph_error', error: this.state.error });\n },\n ),\n this.eventSink,\n );\n }\n\n /** 核心执行逻辑 */\n private async executeSupervisor(\n input: string | Request,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n ): Promise<MultiAgentResult> {\n let stepsCompleted = 0;\n const totalUsage: Record<string, number> = {};\n\n // ── Step 1: 执行 Supervisor ────────────────────────────────\n this.throwIfAborted();\n this.state.currentAgentId = this.supervisorNode.id;\n this.state.nodeStates.set(this.supervisorNode.id, 'running');\n emit({ type: 'agent_start', agentId: this.supervisorNode.id, agentName: this.supervisorNode.name, input: toInputText(input) });\n\n let supervisorResult: Result;\n try {\n supervisorResult = await executeNode(this.supervisorNode, input, ctx);\n this.state.nodeStates.set(this.supervisorNode.id, 'completed');\n this.state.nodeResults.set(this.supervisorNode.id, supervisorResult);\n this.mergeUsage(totalUsage, supervisorResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: this.supervisorNode.id, agentName: this.supervisorNode.name, result: supervisorResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(this.supervisorNode.id, 'failed');\n emit({ type: 'agent_error', agentId: this.supervisorNode.id, agentName: this.supervisorNode.name, error: errorMsg });\n throw err;\n }\n\n // ── Step 2: 调度 Worker 执行 ──────────────────────────────\n const schedule = this.opts.schedule;\n let workerResults: Map<string, Result>;\n\n if (schedule === 'parallel') {\n workerResults = await this.executeWorkersParallel(ctx, emit, totalUsage);\n } else if (schedule === 'sequential') {\n workerResults = await this.executeWorkersSequential(ctx, emit, totalUsage);\n } else {\n // auto: 分析依赖,分层执行\n workerResults = await this.executeWorkersAuto(ctx, emit, totalUsage);\n }\n\n stepsCompleted += workerResults.size;\n this.state.stepsCompleted = stepsCompleted;\n\n // ── Step 3: 汇总结果 ──────────────────────────────────────\n // 取最后一个完成的 worker 的结果作为最终结果(skip 模式下最后的 worker 可能失败,需回退)\n const lastEntry = [...workerResults.entries()].at(-1);\n const finalResult = lastEntry?.[1] ?? supervisorResult;\n const finalAgentId = lastEntry?.[0] ?? this.supervisorNode.id;\n\n const hasFailures = this.failedAgents.length > 0;\n\n this.state.finished = true;\n return {\n content: finalResult.content,\n lastAgentId: finalAgentId,\n agentResults: new Map(this.state.nodeResults),\n totalUsage,\n stepsCompleted,\n stopReason: hasFailures ? 'partial_failure' : 'completed',\n context: ctx,\n success: true,\n ...(hasFailures ? { failedAgents: [...this.failedAgents] } : {}),\n };\n }\n\n /** 并行执行所有 Worker */\n private async executeWorkersParallel(\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Map<string, Result>> {\n const results = new Map<string, Result>();\n const workers = this.workerNodes;\n const concurrency = this.opts.concurrency;\n const skip = this.opts.onWorkerError === 'skip';\n\n emit({ type: 'parallel_start', agentIds: workers.map(w => w.id) });\n\n if (concurrency >= workers.length) {\n if (!skip) {\n // fail-fast:任一失败立即抛出\n await Promise.all(\n workers.map(async (worker) => {\n const r = await this.executeWorker(worker, ctx, emit, totalUsage);\n results.set(worker.id, r);\n return r;\n }),\n );\n } else {\n // skip:容忍失败\n const settled = await Promise.allSettled(\n workers.map(worker => this.executeWorker(worker, ctx, emit, totalUsage)),\n );\n for (let i = 0; i < settled.length; i++) {\n const s = settled[i];\n if (s.status === 'fulfilled') {\n results.set(workers[i].id, s.value);\n } else {\n this.failedAgents.push(workers[i].id);\n }\n }\n }\n } else {\n // 限制并发数\n let index = 0;\n const executing = new Set<Promise<void>>();\n\n const enqueue = (): Promise<void> | null => {\n if (index >= workers.length) return null;\n const worker = workers[index++];\n const p: Promise<void> = this.executeWorker(worker, ctx, emit, totalUsage).then(\n r => { results.set(worker.id, r); },\n err => {\n if (!skip) throw err;\n this.failedAgents.push(worker.id);\n },\n ).finally(() => { executing.delete(p); });\n executing.add(p);\n // 防止 fail-fast 提前退出后,仍在运行的 promise 触发 unhandledRejection\n p.catch(() => {});\n return p;\n };\n\n // 初始填充\n for (let i = 0; i < concurrency && index < workers.length; i++) {\n enqueue();\n }\n\n while (executing.size > 0) {\n await Promise.race(executing);\n enqueue();\n }\n }\n\n emit({ type: 'parallel_done', results });\n return results;\n }\n\n /** 顺序执行所有 Worker */\n private async executeWorkersSequential(\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Map<string, Result>> {\n const results = new Map<string, Result>();\n const skip = this.opts.onWorkerError === 'skip';\n\n for (const worker of this.workerNodes) {\n try {\n const result = await this.executeWorker(worker, ctx, emit, totalUsage);\n results.set(worker.id, result);\n } catch (err) {\n if (!skip) throw err;\n this.failedAgents.push(worker.id);\n }\n }\n\n return results;\n }\n\n /** 自动调度:按依赖分层执行\n *\n * 依赖推导规则:\n * 1. 显式声明 dependsOn 的 worker:依赖指定的 worker(依赖必须都在 workers 列表中,否则报错)\n * 2. 未声明 dependsOn 但有 inputMapping 的 worker:隐式依赖所有\"第 0 层\"worker(保持向后兼容)\n * 3. 其余 worker(无 dependsOn 且无 inputMapping):第 0 层,首批并行\n *\n * 按拓扑分层:同层并行执行(受 concurrency 限制),层间按序执行;依赖成环时报错。\n */\n private async executeWorkersAuto(\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Map<string, Result>> {\n const results = new Map<string, Result>();\n const skip = this.opts.onWorkerError === 'skip';\n const workerIds = new Set(this.workerNodes.map(w => w.id));\n\n // 构建依赖表\n const layer0 = this.workerNodes.filter(w => !w.inputMapping && !w.dependsOn);\n const deps = new Map<string, Set<string>>();\n for (const w of this.workerNodes) {\n if (w.dependsOn) {\n for (const dep of w.dependsOn) {\n if (!workerIds.has(dep)) {\n throw new Error(`Supervisor: Worker \"${w.id}\" 的 dependsOn 引用了不存在的 Worker \"${dep}\"`);\n }\n }\n deps.set(w.id, new Set(w.dependsOn));\n } else if (w.inputMapping) {\n // 向后兼容:隐式依赖所有\"第 0 层\"worker\n deps.set(w.id, new Set(layer0.map(l => l.id)));\n } else {\n deps.set(w.id, new Set());\n }\n }\n\n // 拓扑分层(Kahn 变体:逐层挑出依赖已全部完成的节点)\n const remaining = new Map(deps);\n const layers: AgentNode[][] = [];\n const doneIds = new Set<string>();\n while (remaining.size > 0) {\n const layer: AgentNode[] = [];\n for (const [id, depSet] of remaining) {\n if ([...depSet].every(d => doneIds.has(d))) {\n layer.push(this.workerNodes.find(w => w.id === id)!);\n }\n }\n if (layer.length === 0) {\n throw new Error(`Supervisor: auto 调度的 Worker 依赖存在环(涉及: ${[...remaining.keys()].join(', ')})`);\n }\n for (const w of layer) {\n remaining.delete(w.id);\n doneIds.add(w.id);\n }\n layers.push(layer);\n }\n\n // 逐层执行:层内并行(限流),层间顺序\n for (const layer of layers) {\n if (layer.length === 1) {\n try {\n const r = await this.executeWorker(layer[0], ctx, emit, totalUsage);\n results.set(layer[0].id, r);\n } catch (err) {\n if (!skip) throw err;\n this.failedAgents.push(layer[0].id);\n }\n continue;\n }\n\n emit({ type: 'parallel_start', agentIds: layer.map(w => w.id) });\n\n const runOne = async (worker: AgentNode): Promise<void> => {\n try {\n const r = await this.executeWorker(worker, ctx, emit, totalUsage);\n results.set(worker.id, r);\n } catch (err) {\n if (!skip) throw err;\n this.failedAgents.push(worker.id);\n }\n };\n\n if (this.opts.concurrency >= layer.length) {\n await Promise.all(layer.map(w => runOne(w)));\n } else {\n // 限流并发池\n let index = 0;\n const executing = new Set<Promise<void>>();\n const enqueue = (): Promise<void> | null => {\n if (index >= layer.length) return null;\n const i = index++;\n const p: Promise<void> = runOne(layer[i]).finally(() => { executing.delete(p); });\n executing.add(p);\n p.catch(() => {}); // fail-fast 提前退出后防 unhandledRejection\n return p;\n };\n for (let i = 0; i < this.opts.concurrency && index < layer.length; i++) {\n enqueue();\n }\n while (executing.size > 0) {\n await Promise.race(executing);\n enqueue();\n }\n }\n\n emit({ type: 'parallel_done', results: new Map(results) });\n }\n\n return results;\n }\n\n /** 执行单个 Worker */\n private async executeWorker(\n worker: AgentNode,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<Result> {\n this.throwIfAborted();\n this.state.currentAgentId = worker.id;\n this.state.nodeStates.set(worker.id, 'running');\n\n // 解析输入:优先 inputMapping,否则用 supervisor 的输出\n let workerInput: string | Request;\n try {\n if (worker.inputMapping) {\n workerInput = worker.inputMapping(ctx);\n } else {\n // 从 blackboard 获取 supervisor 分配给该 worker 的任务\n const tasks = ctx.blackboard.get('tasks') as Array<{ assignee: string; task: string }> | undefined;\n const myTask = tasks?.find(t => t.assignee === worker.id);\n workerInput = myTask ? myTask.task : (ctx.blackboard.get('__original_input__') as string ?? '');\n }\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(worker.id, 'failed');\n emit({ type: 'agent_error', agentId: worker.id, agentName: worker.name, error: errorMsg });\n throw err;\n }\n\n emit({ type: 'agent_start', agentId: worker.id, agentName: worker.name, input: toInputText(workerInput) });\n\n try {\n const result = await executeNode(worker, workerInput, ctx);\n this.state.nodeStates.set(worker.id, 'completed');\n this.state.nodeResults.set(worker.id, result);\n this.mergeUsage(totalUsage, result.usage);\n\n // 自动将 worker 结果写入 blackboard(方便后续 worker 读取)\n ctx.blackboard.set(`${worker.id}_result`, result.content);\n\n emit({ type: 'agent_result', agentId: worker.id, agentName: worker.name, result });\n return result;\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(worker.id, 'failed');\n emit({ type: 'agent_error', agentId: worker.id, agentName: worker.name, error: errorMsg });\n throw err;\n }\n }\n\n private buildErrorResult(ctx: SharedContext, err: unknown): MultiAgentResult {\n this.state.finished = true;\n const aborted = err instanceof GraphAbortedError;\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.error = errorMsg;\n const lastCompleted = [...this.state.nodeResults.values()].at(-1);\n return {\n content: aborted ? (lastCompleted?.content ?? '') : '',\n lastAgentId: this.state.currentAgentId ?? this.supervisorNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: aborted ? 'aborted' : 'error',\n context: ctx,\n success: false,\n error: errorMsg,\n ...(this.failedAgents.length > 0 ? { failedAgents: [...this.failedAgents] } : {}),\n };\n }\n\n private mergeUsage(total: Record<string, number>, usage: Record<string, number>): void {\n for (const [key, value] of Object.entries(usage)) {\n total[key] = (total[key] ?? 0) + value;\n }\n }\n}\n","/**\n * patterns/supervisor.ts - Supervisor 层级委派模式\n *\n * Supervisor Agent 拆解任务分配给 Worker Agents,\n * 根据调度策略执行(parallel / sequential / auto)。\n */\n\nimport type { AgentNode, AgentGraph, SupervisorOpts, EventListener, MultiAgentResult, MultiAgentEvent } from '../core/types';\nimport { SupervisorExecutor } from '../core/supervisor-executor';\nimport { SimpleEventBus } from '../core/context';\nimport type { Request } from '@aipack-ai/agent';\n\n// ─── SupervisorGraphImpl ─────────────────────────────────────────\n\nclass SupervisorGraphImpl implements AgentGraph {\n private executor: SupervisorExecutor;\n /** on() 注册的监听器,按 MultiAgentEvent.type 分发 */\n private bus = new SimpleEventBus();\n\n constructor(supervisor: AgentNode, workers: AgentNode[], opts?: SupervisorOpts) {\n this.executor = new SupervisorExecutor(supervisor, workers, opts);\n }\n\n // AgentGraph 接口方法(Supervisor 不使用 addNode/addEdge/setEntry/setFinish)\n addNode(): this {\n throw new Error('Supervisor 模式不支持手动 addNode,请在 createSupervisor() 中配置');\n }\n addEdge(): this {\n throw new Error('Supervisor 模式不支持手动 addEdge,调度由 Supervisor 自动管理');\n }\n setEntry(): this {\n throw new Error('Supervisor 模式不支持 setEntry,入口固定为 Supervisor');\n }\n setFinish(): this {\n throw new Error('Supervisor 模式不支持 setFinish,终止由 Supervisor 判定');\n }\n\n async run(input: string | Request): Promise<MultiAgentResult> {\n this.executor.setEventSink(event => this.bus.emit(event.type, event));\n return this.executor.run(input);\n }\n\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n this.executor.setEventSink(event => this.bus.emit(event.type, event));\n yield* this.executor.stream(input);\n }\n\n getState() {\n return this.executor.getState();\n }\n\n abort(): void {\n this.executor.abort();\n }\n\n on(event: string, listener: EventListener): this {\n this.bus.on(event, listener);\n return this;\n }\n}\n\n// ─── createSupervisor 工厂函数 ───────────────────────────────────\n\n/**\n * 创建 Supervisor 层级委派模式\n *\n * @param supervisor - Supervisor Agent(负责拆解任务并分配)\n * @param workers - Worker Agent 列表(负责执行具体任务)\n * @param opts - Supervisor 配置选项\n * @returns AgentGraph 实例\n */\nexport function createSupervisor(\n supervisor: AgentNode,\n workers: AgentNode[],\n opts?: SupervisorOpts,\n): AgentGraph {\n if (workers.length === 0) {\n throw new Error('Supervisor: 至少需要一个 Worker Agent');\n }\n\n return new SupervisorGraphImpl(supervisor, workers, opts);\n}\n","/**\n * core/debate-executor.ts - Debate 对抗评审执行器\n *\n * 实现 proposer ↔ reviewer 循环辩论模式:\n * 1. Proposer 生成初始结果\n * 2. Reviewer 审查并给出反馈\n * 3. 如果未收敛,将反馈转为 proposer 输入,回到步骤 1\n * 4. 收敛或达最大轮次时结束\n */\n\nimport type { Result, Request } from '@aipack-ai/agent';\nimport type {\n AgentNode,\n SharedContext,\n MultiAgentResult,\n MultiAgentEvent,\n DebateOpts,\n GraphExecutionState,\n} from './types';\nimport { createSharedContext, storeOriginalInput } from './context';\nimport { executeNode, GraphAbortedError, toInputText } from './executor';\nimport { createEventStream } from './event-stream';\n\n// ─── DebateExecutor ──────────────────────────────────────────────\n\nexport class DebateExecutor {\n private proposerNode: AgentNode;\n private reviewerNode: AgentNode;\n private maxRounds: number;\n private convergeWhen: (reviewerResult: Result) => boolean;\n private feedbackTransform: (reviewerResult: Result, proposerResult: Result) => string;\n private abortController = new AbortController();\n /** 外部事件监听(on() API 的底层接线) */\n private eventSink?: (event: MultiAgentEvent) => void;\n private state: GraphExecutionState = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n\n constructor(proposer: AgentNode, reviewer: AgentNode, opts: DebateOpts) {\n this.proposerNode = proposer;\n this.reviewerNode = reviewer;\n this.maxRounds = opts.maxRounds ?? 3;\n this.convergeWhen = opts.convergeWhen;\n this.feedbackTransform = opts.feedbackTransform ?? ((reviewerResult, proposerResult) => {\n return `以下是审查意见:\\n${reviewerResult.content}\\n\\n请修复以上问题并重新提交。原始输出:\\n${proposerResult.content}`;\n });\n\n this.state.nodeStates.set(proposer.id, 'pending');\n this.state.nodeStates.set(reviewer.id, 'pending');\n }\n\n getState(): GraphExecutionState {\n // 深拷贝快照:防止外部通过返回值篡改内部状态\n return {\n ...this.state,\n nodeStates: new Map(this.state.nodeStates),\n nodeResults: new Map(this.state.nodeResults),\n };\n }\n\n /** 注入外部事件监听(由 AgentGraph 实现的 on() 接线) */\n setEventSink(sink?: (event: MultiAgentEvent) => void): this {\n this.eventSink = sink;\n return this;\n }\n\n abort(): void {\n this.abortController.abort();\n }\n\n /** 每次 run/stream 前重置中止信号与执行状态 */\n private resetAbortController(): void {\n this.abortController = new AbortController();\n this.state = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n this.state.nodeStates.set(this.proposerNode.id, 'pending');\n this.state.nodeStates.set(this.reviewerNode.id, 'pending');\n }\n\n private throwIfAborted(): void {\n if (this.abortController.signal.aborted) {\n throw new GraphAbortedError();\n }\n }\n\n /** 执行 Debate */\n async run(input: string | Request): Promise<MultiAgentResult> {\n this.resetAbortController();\n const ctx = createSharedContext({\n meta: { traceId: `debate-${Date.now()}`, startTime: Date.now() },\n });\n storeOriginalInput(ctx, input);\n\n const emit = this.eventSink ?? (() => {});\n\n try {\n const result = await this.executeDebate(input, ctx, emit);\n emit({ type: 'graph_done', result });\n return result;\n } catch (err) {\n const result = this.buildErrorResult(ctx, err);\n emit({ type: 'graph_error', error: result.error ?? '' });\n return result;\n }\n }\n\n /** 流式执行 Debate */\n stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n this.resetAbortController();\n const ctx = createSharedContext({\n meta: { traceId: `debate-${Date.now()}`, startTime: Date.now() },\n });\n storeOriginalInput(ctx, input);\n\n return createEventStream(\n emit => this.executeDebate(input, ctx, emit).then(\n (result) => { emit({ type: 'graph_done', result }); },\n (err) => {\n this.state.error = err instanceof Error ? err.message : String(err);\n emit({ type: 'graph_error', error: this.state.error });\n },\n ),\n this.eventSink,\n );\n }\n\n /** 核心执行逻辑 */\n private async executeDebate(\n input: string | Request,\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n ): Promise<MultiAgentResult> {\n let stepsCompleted = 0;\n const totalUsage: Record<string, number> = {};\n let lastProposerResult!: Result;\n let lastReviewerResult!: Result;\n let convergedRound = 0;\n let convergeReason = '';\n let currentInput: string | Request = input;\n\n for (let round = 1; round <= this.maxRounds; round++) {\n this.throwIfAborted();\n emit({ type: 'round_start', round });\n\n // ── 执行 Proposer ──────────────────────────────────────\n this.state.currentAgentId = this.proposerNode.id;\n this.state.nodeStates.set(this.proposerNode.id, 'running');\n emit({ type: 'agent_start', agentId: this.proposerNode.id, agentName: this.proposerNode.name, input: toInputText(currentInput) });\n\n try {\n lastProposerResult = await executeNode(this.proposerNode, currentInput, ctx);\n this.state.nodeStates.set(this.proposerNode.id, 'completed');\n this.state.nodeResults.set(`${this.proposerNode.id}_r${round}`, lastProposerResult);\n this.mergeUsage(totalUsage, lastProposerResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: this.proposerNode.id, agentName: this.proposerNode.name, result: lastProposerResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(this.proposerNode.id, 'failed');\n emit({ type: 'agent_error', agentId: this.proposerNode.id, agentName: this.proposerNode.name, error: errorMsg });\n throw err;\n }\n\n // ── 执行 Reviewer ──────────────────────────────────────\n this.state.currentAgentId = this.reviewerNode.id;\n this.state.nodeStates.set(this.reviewerNode.id, 'running');\n emit({ type: 'agent_start', agentId: this.reviewerNode.id, agentName: this.reviewerNode.name, input: lastProposerResult.content });\n\n try {\n lastReviewerResult = await executeNode(this.reviewerNode, lastProposerResult.content, ctx);\n this.state.nodeStates.set(this.reviewerNode.id, 'completed');\n this.state.nodeResults.set(`${this.reviewerNode.id}_r${round}`, lastReviewerResult);\n this.mergeUsage(totalUsage, lastReviewerResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: this.reviewerNode.id, agentName: this.reviewerNode.name, result: lastReviewerResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(this.reviewerNode.id, 'failed');\n emit({ type: 'agent_error', agentId: this.reviewerNode.id, agentName: this.reviewerNode.name, error: errorMsg });\n throw err;\n }\n\n // ── 检查收敛 ────────────────────────────────────────────\n if (this.convergeWhen(lastReviewerResult)) {\n convergedRound = round;\n convergeReason = `收敛于第 ${round} 轮:reviewer 输出满足收敛条件`;\n emit({ type: 'converged', round, reason: convergeReason });\n break;\n }\n\n // ── 准备下一轮输入 ──────────────────────────────────────\n currentInput = this.feedbackTransform(lastReviewerResult, lastProposerResult);\n }\n\n // 最终结果:收敛时取 proposer 最后一轮输出,未收敛时也取 proposer 输出\n const finalResult = lastProposerResult;\n const stopReason = convergedRound > 0\n ? `converged_at_round_${convergedRound}`\n : `max_rounds_reached`;\n\n this.state.finished = true;\n return {\n content: finalResult.content,\n lastAgentId: this.reviewerNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage,\n stepsCompleted,\n stopReason,\n context: ctx,\n success: true,\n };\n }\n\n private buildErrorResult(ctx: SharedContext, err: unknown): MultiAgentResult {\n this.state.finished = true;\n const aborted = err instanceof GraphAbortedError;\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.error = errorMsg;\n const lastCompleted = [...this.state.nodeResults.values()].at(-1);\n return {\n content: aborted ? (lastCompleted?.content ?? '') : '',\n lastAgentId: this.proposerNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: aborted ? 'aborted' : 'error',\n context: ctx,\n success: false,\n error: errorMsg,\n };\n }\n\n private mergeUsage(total: Record<string, number>, usage: Record<string, number>): void {\n for (const [key, value] of Object.entries(usage)) {\n total[key] = (total[key] ?? 0) + value;\n }\n }\n}\n","/**\n * patterns/debate.ts - Debate 对抗评审模式\n *\n * Proposer 和 Reviewer 循环辩论,直到收敛或达最大轮次。\n */\n\nimport type { AgentNode, AgentGraph, DebateOpts, EventListener, MultiAgentResult, MultiAgentEvent } from '../core/types';\nimport { DebateExecutor } from '../core/debate-executor';\nimport { SimpleEventBus } from '../core/context';\nimport type { Request } from '@aipack-ai/agent';\n\n// ─── DebateGraphImpl ─────────────────────────────────────────────\n\nclass DebateGraphImpl implements AgentGraph {\n private executor: DebateExecutor;\n /** on() 注册的监听器,按 MultiAgentEvent.type 分发 */\n private bus = new SimpleEventBus();\n\n constructor(proposer: AgentNode, reviewer: AgentNode, opts: DebateOpts) {\n this.executor = new DebateExecutor(proposer, reviewer, opts);\n }\n\n addNode(): this { throw new Error('Debate 模式不支持手动 addNode'); }\n addEdge(): this { throw new Error('Debate 模式不支持手动 addEdge'); }\n setEntry(): this { throw new Error('Debate 模式不支持 setEntry'); }\n setFinish(): this { throw new Error('Debate 模式不支持 setFinish'); }\n\n async run(input: string | Request): Promise<MultiAgentResult> {\n this.executor.setEventSink(event => this.bus.emit(event.type, event));\n return this.executor.run(input);\n }\n\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n this.executor.setEventSink(event => this.bus.emit(event.type, event));\n yield* this.executor.stream(input);\n }\n\n getState() { return this.executor.getState(); }\n abort(): void { this.executor.abort(); }\n\n on(event: string, listener: EventListener): this {\n this.bus.on(event, listener);\n return this;\n }\n}\n\n// ─── createDebate 工厂函数 ───────────────────────────────────────\n\n/**\n * 创建 Debate 对抗评审模式\n *\n * @param proposer - 生成/修复方 Agent\n * @param reviewer - 审查方 Agent\n * @param opts - Debate 配置选项(必须提供 convergeWhen)\n * @returns AgentGraph 实例\n */\nexport function createDebate(\n proposer: AgentNode,\n reviewer: AgentNode,\n opts: DebateOpts,\n): AgentGraph {\n return new DebateGraphImpl(proposer, reviewer, opts);\n}\n","/**\n * core/map-reduce-executor.ts - MapReduce 并行聚合执行器\n *\n * 实现 MapReduce 模式:\n * 1. split:将输入拆分为多个子任务\n * 2. map:用 mapper Agent 并行处理每个子任务\n * 3. reduce:用 reducer Agent 汇总所有 mapper 结果\n *\n * 失败策略(onMapperError):\n * - 'fail-fast'(默认):任一子任务失败立即中止,整体返回 error\n * - 'skip':容忍失败,仅汇总成功的子任务,结果暴露 failedAgents 与 stopReason='partial_failure'\n */\n\nimport type { Result, Request } from '@aipack-ai/agent';\nimport type {\n AgentNode,\n SharedContext,\n MultiAgentResult,\n MultiAgentEvent,\n MapReduceOpts,\n GraphExecutionState,\n} from './types';\nimport { createSharedContext, storeOriginalInput } from './context';\nimport { executeNode, GraphAbortedError } from './executor';\nimport { createEventStream } from './event-stream';\n// ─── MapReduceExecutor ───────────────────────────────────────────\n\nexport class MapReduceExecutor {\n private mapperNode: AgentNode;\n private reducerNode: AgentNode;\n private split: (input: string) => string[];\n private concurrency: number;\n private onMapperError: 'fail-fast' | 'skip';\n private reduceInputFormat: (mapperResults: Map<number, Result>) => string;\n private abortController = new AbortController();\n /** 外部事件监听(on() API 的底层接线) */\n private eventSink?: (event: MultiAgentEvent) => void;\n private state: GraphExecutionState = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n\n constructor(mapper: AgentNode, reducer: AgentNode, opts: MapReduceOpts) {\n this.mapperNode = mapper;\n this.reducerNode = reducer;\n this.split = opts.split;\n this.concurrency = opts.concurrency ?? Infinity;\n this.onMapperError = opts.onMapperError ?? 'fail-fast';\n this.reduceInputFormat = opts.reduceInputFormat ?? ((mapperResults) => {\n const parts: string[] = [];\n for (const [idx, result] of mapperResults) {\n parts.push(`--- 子任务 ${idx + 1} ---\\n${result.content}`);\n }\n return parts.join('\\n\\n');\n });\n\n this.state.nodeStates.set(mapper.id, 'pending');\n this.state.nodeStates.set(reducer.id, 'pending');\n }\n\n getState(): GraphExecutionState {\n // 深拷贝快照:防止外部通过返回值篡改内部状态\n return {\n ...this.state,\n nodeStates: new Map(this.state.nodeStates),\n nodeResults: new Map(this.state.nodeResults),\n };\n }\n\n /** 注入外部事件监听(由 AgentGraph 实现的 on() 接线) */\n setEventSink(sink?: (event: MultiAgentEvent) => void): this {\n this.eventSink = sink;\n return this;\n }\n\n abort(): void {\n this.abortController.abort();\n }\n\n /** 每次 run/stream 前重置中止信号与执行状态 */\n private resetAbortController(): void {\n this.abortController = new AbortController();\n this.state = {\n nodeStates: new Map(),\n nodeResults: new Map(),\n stepsCompleted: 0,\n finished: false,\n };\n this.state.nodeStates.set(this.mapperNode.id, 'pending');\n this.state.nodeStates.set(this.reducerNode.id, 'pending');\n }\n\n private throwIfAborted(): void {\n if (this.abortController.signal.aborted) {\n throw new GraphAbortedError();\n }\n }\n\n /** 拆分输入并校验(每次 run/stream 只调用一次 split,避免副作用放大) */\n private splitInput(input: string | Request): string[] {\n const inputText = typeof input === 'string' ? input : input.message;\n const chunks = this.split(inputText);\n if (chunks.length === 0) {\n throw new Error('MapReduce: split 函数返回了空数组,至少需要一个子任务');\n }\n return chunks;\n }\n\n /** 执行 MapReduce */\n async run(input: string | Request): Promise<MultiAgentResult> {\n this.resetAbortController();\n const chunks = this.splitInput(input);\n\n const ctx = createSharedContext({\n meta: { traceId: `mr-${Date.now()}`, startTime: Date.now() },\n });\n storeOriginalInput(ctx, input);\n\n const emit = this.eventSink ?? (() => {});\n\n try {\n const result = await this.executeMapReduce(chunks, ctx, emit);\n emit({ type: 'graph_done', result });\n return result;\n } catch (err) {\n const result = this.buildErrorResult(ctx, err);\n emit({ type: 'graph_error', error: result.error ?? '' });\n return result;\n }\n }\n\n /** 流式执行 MapReduce */\n stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n this.resetAbortController();\n const chunks = this.splitInput(input);\n\n const ctx = createSharedContext({\n meta: { traceId: `mr-${Date.now()}`, startTime: Date.now() },\n });\n storeOriginalInput(ctx, input);\n\n return createEventStream(\n emit => this.executeMapReduce(chunks, ctx, emit).then(\n (result) => { emit({ type: 'graph_done', result }); },\n (err) => {\n this.state.error = err instanceof Error ? err.message : String(err);\n emit({ type: 'graph_error', error: this.state.error });\n },\n ),\n this.eventSink,\n );\n }\n\n /** 核心执行逻辑 */\n private async executeMapReduce(\n chunks: string[],\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n ): Promise<MultiAgentResult> {\n const totalUsage: Record<string, number> = {};\n\n this.throwIfAborted();\n\n // ── Step 1+2: Map(并行执行 mapper,split 已在外层完成) ──\n this.state.nodeStates.set(this.mapperNode.id, 'running');\n // 为每个子任务登记虚拟节点状态(与 nodeResults 的虚拟 ID 对齐)\n chunks.forEach((_, i) => {\n this.state.nodeStates.set(`${this.mapperNode.id}_${i}`, 'pending');\n });\n\n const { results: mapperResults, failed } = await this.runMappers(chunks, ctx, emit, totalUsage);\n\n let stepsCompleted = mapperResults.size + failed.length;\n this.state.stepsCompleted = stepsCompleted;\n\n this.state.nodeStates.set(this.mapperNode.id, 'completed');\n const mapperResultsForEmit = new Map<string, Result>();\n for (const [idx, result] of mapperResults) {\n mapperResultsForEmit.set(`${this.mapperNode.id}_${idx}`, result);\n }\n emit({ type: 'parallel_done', results: mapperResultsForEmit });\n\n // 将 mapper 结果写入 blackboard\n ctx.blackboard.set('mapper_results', mapperResults);\n\n if (failed.length > 0 && mapperResults.size === 0) {\n throw new Error(`MapReduce: 所有 mapper 均失败(${failed.length}/${chunks.length})`);\n }\n\n // ── Step 3: Reduce ─────────────────────────────────────────\n const reduceInput = this.reduceInputFormat(mapperResults);\n\n this.throwIfAborted();\n this.state.currentAgentId = this.reducerNode.id;\n this.state.nodeStates.set(this.reducerNode.id, 'running');\n emit({ type: 'agent_start', agentId: this.reducerNode.id, agentName: this.reducerNode.name, input: reduceInput });\n\n let reducerResult: Result;\n try {\n reducerResult = await executeNode(this.reducerNode, reduceInput, ctx);\n this.state.nodeStates.set(this.reducerNode.id, 'completed');\n this.state.nodeResults.set(this.reducerNode.id, reducerResult);\n this.mergeUsage(totalUsage, reducerResult.usage);\n stepsCompleted++;\n this.state.stepsCompleted = stepsCompleted;\n emit({ type: 'agent_result', agentId: this.reducerNode.id, agentName: this.reducerNode.name, result: reducerResult });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(this.reducerNode.id, 'failed');\n emit({ type: 'agent_error', agentId: this.reducerNode.id, agentName: this.reducerNode.name, error: errorMsg });\n throw err;\n }\n\n this.state.finished = true;\n const hasFailures = failed.length > 0;\n return {\n content: reducerResult.content,\n lastAgentId: this.reducerNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage,\n stepsCompleted,\n stopReason: hasFailures ? 'partial_failure' : 'completed',\n context: ctx,\n success: true,\n ...(hasFailures ? { failedAgents: failed } : {}),\n };\n }\n\n /** 并行执行所有 mapper 子任务(统一处理并发限制与失败策略) */\n private async runMappers(\n chunks: string[],\n ctx: SharedContext,\n emit: (event: MultiAgentEvent) => void,\n totalUsage: Record<string, number>,\n ): Promise<{ results: Map<number, Result>; failed: string[] }> {\n const results = new Map<number, Result>();\n const failed: string[] = [];\n const skip = this.onMapperError === 'skip';\n const mapperId = this.mapperNode.id;\n\n const mapperAgentIds = chunks.map((_, i) => `${mapperId}_${i}`);\n emit({ type: 'parallel_start', agentIds: mapperAgentIds });\n\n const runOne = async (index: number): Promise<void> => {\n const agentId = `${mapperId}_${index}`;\n const agentName = `${this.mapperNode.name}#${index + 1}`;\n emit({ type: 'agent_start', agentId, agentName, input: chunks[index] });\n this.state.nodeStates.set(agentId, 'running');\n try {\n const result = await executeNode(this.mapperNode, chunks[index], ctx);\n this.state.nodeResults.set(agentId, result);\n this.state.nodeStates.set(agentId, 'completed');\n this.mergeUsage(totalUsage, result.usage);\n results.set(index, result);\n emit({ type: 'agent_result', agentId, agentName, result });\n } catch (err) {\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.nodeStates.set(agentId, 'failed');\n emit({ type: 'agent_error', agentId, agentName, error: errorMsg });\n if (!skip) throw err;\n failed.push(agentId);\n }\n };\n\n if (this.concurrency >= chunks.length) {\n // 无限制并发\n const promises = chunks.map((_, i) => runOne(i));\n if (!skip) {\n await Promise.all(promises);\n } else {\n // runOne 在 skip 模式下不会 reject,allSettled 仅作双保险\n await Promise.allSettled(promises);\n }\n } else {\n // 限制并发数\n let index = 0;\n const executing = new Set<Promise<void>>();\n\n const enqueue = (): Promise<void> | null => {\n if (index >= chunks.length) return null;\n const i = index++;\n const p: Promise<void> = runOne(i).finally(() => { executing.delete(p); });\n executing.add(p);\n // 防止 fail-fast 提前退出后,仍在运行的 promise 触发 unhandledRejection\n p.catch(() => {});\n return p;\n };\n\n // 初始填充\n for (let i = 0; i < this.concurrency && index < chunks.length; i++) {\n enqueue();\n }\n\n while (executing.size > 0) {\n await Promise.race(executing);\n enqueue();\n }\n }\n\n return { results, failed };\n }\n\n private buildErrorResult(ctx: SharedContext, err: unknown): MultiAgentResult {\n this.state.finished = true;\n const aborted = err instanceof GraphAbortedError;\n const errorMsg = err instanceof Error ? err.message : String(err);\n this.state.error = errorMsg;\n const lastCompleted = [...this.state.nodeResults.values()].at(-1);\n return {\n content: aborted ? (lastCompleted?.content ?? '') : '',\n lastAgentId: this.mapperNode.id,\n agentResults: new Map(this.state.nodeResults),\n totalUsage: {},\n stepsCompleted: this.state.stepsCompleted,\n stopReason: aborted ? 'aborted' : 'error',\n context: ctx,\n success: false,\n error: errorMsg,\n };\n }\n\n private mergeUsage(total: Record<string, number>, usage: Record<string, number>): void {\n for (const [key, value] of Object.entries(usage)) {\n total[key] = (total[key] ?? 0) + value;\n }\n }\n}\n","/**\n * patterns/map-reduce.ts - MapReduce 并行聚合模式\n *\n * 将输入拆分为子任务,用 mapper 并行处理,再用 reducer 汇总。\n */\n\nimport type { AgentNode, AgentGraph, MapReduceOpts, EventListener, MultiAgentResult, MultiAgentEvent } from '../core/types';\nimport { MapReduceExecutor } from '../core/map-reduce-executor';\nimport { SimpleEventBus } from '../core/context';\nimport type { Request } from '@aipack-ai/agent';\n\n// ─── MapReduceGraphImpl ──────────────────────────────────────────\n\nclass MapReduceGraphImpl implements AgentGraph {\n private executor: MapReduceExecutor;\n /** on() 注册的监听器,按 MultiAgentEvent.type 分发 */\n private bus = new SimpleEventBus();\n\n constructor(mapper: AgentNode, reducer: AgentNode, opts: MapReduceOpts) {\n this.executor = new MapReduceExecutor(mapper, reducer, opts);\n }\n\n addNode(): this { throw new Error('MapReduce 模式不支持手动 addNode'); }\n addEdge(): this { throw new Error('MapReduce 模式不支持手动 addEdge'); }\n setEntry(): this { throw new Error('MapReduce 模式不支持 setEntry'); }\n setFinish(): this { throw new Error('MapReduce 模式不支持 setFinish'); }\n\n async run(input: string | Request): Promise<MultiAgentResult> {\n this.executor.setEventSink(event => this.bus.emit(event.type, event));\n return this.executor.run(input);\n }\n\n async *stream(input: string | Request): AsyncGenerator<MultiAgentEvent> {\n this.executor.setEventSink(event => this.bus.emit(event.type, event));\n yield* this.executor.stream(input);\n }\n\n getState() { return this.executor.getState(); }\n abort(): void { this.executor.abort(); }\n\n on(event: string, listener: EventListener): this {\n this.bus.on(event, listener);\n return this;\n }\n}\n\n// ─── createMapReduce 工厂函数 ────────────────────────────────────\n\n/**\n * 创建 MapReduce 并行聚合模式\n *\n * @param mapper - 映射方 Agent(处理单个子任务)\n * @param reducer - 汇总方 Agent(合并所有 mapper 结果)\n * @param opts - MapReduce 配置选项(必须提供 split 函数)\n * @returns AgentGraph 实例\n */\nexport function createMapReduce(\n mapper: AgentNode,\n reducer: AgentNode,\n opts: MapReduceOpts,\n): AgentGraph {\n return new MapReduceGraphImpl(mapper, reducer, opts);\n}\n","/**\n * jsonrpc.ts - JSON-RPC 2.0 编解码 + 消息分类(纯函数)\n *\n * 不依赖任何 Node API,可在任意 JS 运行时使用。stdio 传输层以行分隔\n * 逐条调用 parseMessage / serialize。\n */\n\nexport type JsonRpcId = number | string | null;\n\nexport interface JsonRpcRequest {\n jsonrpc: '2.0';\n id: Exclude<JsonRpcId, null>;\n method: string;\n params?: unknown;\n}\n\nexport interface JsonRpcNotification {\n jsonrpc: '2.0';\n method: string;\n params?: unknown;\n}\n\nexport interface JsonRpcSuccessResponse {\n jsonrpc: '2.0';\n id: JsonRpcId;\n result: unknown;\n}\n\nexport interface JsonRpcErrorResponse {\n jsonrpc: '2.0';\n id: JsonRpcId;\n error: { code: number; message: string; data?: unknown };\n}\n\nexport type JsonRpcResponse = JsonRpcSuccessResponse | JsonRpcErrorResponse;\n\nexport type JsonRpcMessage =\n | JsonRpcRequest\n | JsonRpcNotification\n | JsonRpcResponse;\n\n// ─── 标准错误码 ─────────────────────────────────────────────────\n\nexport const PARSE_ERROR = -32700;\nexport const INVALID_REQUEST = -32600;\nexport const METHOD_NOT_FOUND = -32601;\nexport const INVALID_PARAMS = -32602;\nexport const INTERNAL_ERROR = -32603;\n\n// ─── 构造 ─────────────────────────────────────────────────────\n\nexport function createRequest(\n id: Exclude<JsonRpcId, null>,\n method: string,\n params?: unknown,\n): JsonRpcRequest {\n const req: JsonRpcRequest = { jsonrpc: '2.0', id, method };\n if (params !== undefined) req.params = params;\n return req;\n}\n\nexport function createNotification(method: string, params?: unknown): JsonRpcNotification {\n const n: JsonRpcNotification = { jsonrpc: '2.0', method };\n if (params !== undefined) n.params = params;\n return n;\n}\n\nexport function createSuccessResponse(id: JsonRpcId, result: unknown): JsonRpcSuccessResponse {\n return { jsonrpc: '2.0', id, result };\n}\n\nexport function createErrorResponse(\n id: JsonRpcId,\n code: number,\n message: string,\n data?: unknown,\n): JsonRpcErrorResponse {\n const err: JsonRpcErrorResponse = { jsonrpc: '2.0', id, error: { code, message } };\n if (data !== undefined) err.error.data = data;\n return err;\n}\n\n// ─── 序列化 ───────────────────────────────────────────────────\n\nexport function serialize(message: JsonRpcMessage): string {\n return JSON.stringify(message);\n}\n\n// ─── 解析 / 分类 ───────────────────────────────────────────────\n\nfunction hasOwn(o: unknown, k: string): boolean {\n return typeof o === 'object' && o !== null && Object.prototype.hasOwnProperty.call(o, k);\n}\n\n/**\n * 解析一段字符串为 JSON-RPC 消息,或返回 null(非 JSON / 非合法 JSON-RPC)。\n * 容错:不要求 result/error 二者互斥以外的强校验,未知字段保留。\n */\nexport function parseMessage(raw: string): JsonRpcMessage | null {\n let obj: unknown;\n try {\n obj = JSON.parse(raw);\n } catch {\n return null;\n }\n return classify(obj);\n}\n\n/** 对已解析的对象做 JSON-RPC 2.0 形状判定(不入站不 JSON.parse 的场景) */\nexport function classify(obj: unknown): JsonRpcMessage | null {\n if (typeof obj !== 'object' || obj === null) return null;\n const o = obj as Record<string, unknown>;\n if (o.jsonrpc !== '2.0') return null;\n\n // 响应:有 result 或 error\n if (hasOwn(o, 'result') || hasOwn(o, 'error')) {\n return o as unknown as JsonRpcResponse;\n }\n // 请求 / 通知:有 method\n if (hasOwn(o, 'method') && typeof o.method === 'string') {\n // 有 id(非 null)即请求;通知无 id 字段\n if (hasOwn(o, 'id') && o.id !== null) return o as unknown as JsonRpcRequest;\n if (!hasOwn(o, 'id') || o.id === null) return o as unknown as JsonRpcNotification;\n }\n return null;\n}\n\nexport function isResponse(m: JsonRpcMessage): m is JsonRpcResponse {\n return 'result' in m || 'error' in m;\n}\n\nexport function isRequest(m: JsonRpcMessage): m is JsonRpcRequest {\n return !isResponse(m) && 'id' in m && (m as JsonRpcRequest).id !== null;\n}\n\nexport function isNotification(m: JsonRpcMessage): m is JsonRpcNotification {\n return !isResponse(m) && !('id' in m && (m as { id?: unknown }).id !== null);\n}\n\nexport function isErrorResponse(m: JsonRpcMessage): m is JsonRpcErrorResponse {\n return isResponse(m) && 'error' in m;\n}\n","/**\n * protocol.ts - MCP 协议子集消息构造 / 校验(纯函数)\n *\n * v1 范围:initialize / notifications/initialized / tools/list / tools/call /\n * ping / notifications/cancelled / notifications/tools/list_changed。\n * resources / prompts / sampling 留待后续版本。\n *\n * 设计原则:本模块只产 / 解 MCP 消息形状,不分配 JSON-RPC id(id 由会话层\n * McpClient 分配并经 jsonrpc.createRequest 注入),保证纯函数可单测。\n */\n\nimport {\n createRequest,\n createNotification,\n type JsonRpcRequest,\n type JsonRpcNotification,\n isErrorResponse,\n} from './jsonrpc';\n\n// ─── 协议版本 ─────────────────────────────────────────────────\n\n/** 客户端宣告版本(最新稳定) */\nexport const MCP_PROTOCOL_VERSION = '2025-06-18';\n/** 协议基线;server 声明版本 < 此值则视为不兼容 */\nexport const MCP_BASELINE_VERSION = '2024-11-05';\n\n// ─── 能力 / 信息 ─────────────────────────────────────────────\n\nexport interface McpClientInfo {\n name: string;\n version: string;\n}\n\nexport interface McpServerInfo {\n name: string;\n version: string;\n}\n\nexport interface McpServerCapabilities {\n tools?: { listChanged?: boolean };\n resources?: Record<string, unknown> | {};\n prompts?: Record<string, unknown> | {};\n logging?: Record<string, unknown> | {};\n [key: string]: unknown;\n}\n\n// ─── 工具形状 ─────────────────────────────────────────────────\n\nexport interface McpToolInfo {\n name: string;\n description?: string;\n /** JSON Schema,直接对接 agent Tool.parameters */\n inputSchema?: unknown;\n annotations?: unknown;\n}\n\nexport interface McpContentBlock {\n type: string;\n text?: string;\n data?: string;\n mimeType?: string;\n /** 规范中 resource 块的载荷在嵌套字段 */\n resource?: { uri: string; text?: string; blob?: string; mimeType?: string };\n}\n\nexport interface McpToolCallResult {\n content: McpContentBlock[];\n isError?: boolean;\n}\n\n// ─── initialize ───────────────────────────────────────────────\n\nexport interface McpInitializeResult {\n protocolVersion: string;\n serverInfo: McpServerInfo;\n capabilities: McpServerCapabilities;\n}\n\n/**\n * 协议版本协商:client 发送 clientVersion,server 返回其版本。\n * - server 版本 === clientVersion → ok,使用之\n * - server 版本 >= baseline → ok,使用 server 版本(降级)\n * - 否则不兼容\n */\nexport function negotiateProtocol(\n clientVersion: string,\n serverVersion: string,\n): { ok: boolean; version?: string } {\n if (!serverVersion || typeof serverVersion !== 'string') return { ok: false };\n if (serverVersion === clientVersion) return { ok: true, version: serverVersion };\n // 字符串序不足以判断版本先后,这里仅做基线存在性校验:只要 >= baseline 即接受\n if (serverVersion >= MCP_BASELINE_VERSION) return { ok: true, version: serverVersion };\n return { ok: false };\n}\n\nexport function createInitializeRequest(\n id: number | string,\n client: McpClientInfo,\n capabilities?: Record<string, unknown>,\n): JsonRpcRequest {\n return createRequest(id, 'initialize', buildInitializeParams(client, capabilities));\n}\n\n/** 构造 initialize 请求 params(协议版本 + 能力 + 客户端信息) */\nexport function buildInitializeParams(\n client: McpClientInfo,\n capabilities?: Record<string, unknown>,\n): Record<string, unknown> {\n return {\n protocolVersion: MCP_PROTOCOL_VERSION,\n capabilities: capabilities ?? {},\n clientInfo: client,\n };\n}\n\nexport function createInitializedNotification(): JsonRpcNotification {\n return createNotification('notifications/initialized');\n}\n\n/** 解析 initialize 响应 result;容错:缺省字段给出合理默认 */\nexport function parseInitializeResult(result: unknown): McpInitializeResult {\n const r = (result ?? {}) as Record<string, unknown>;\n const serverInfo = (r.serverInfo ?? { name: 'unknown', version: '0.0.0' }) as McpServerInfo;\n const capabilities = (r.capabilities ?? {}) as McpServerCapabilities;\n const protocolVersion = typeof r.protocolVersion === 'string' ? r.protocolVersion : '';\n return { protocolVersion, serverInfo, capabilities };\n}\n\n// ─── tools/list ──────────────────────────────────────────────\n\nexport function createListToolsRequest(id: number | string, cursor?: string): JsonRpcRequest {\n const params: Record<string, unknown> = {};\n if (cursor) params.cursor = cursor;\n return createRequest(id, 'tools/list', Object.keys(params).length ? params : undefined);\n}\n\nexport interface McpToolListResult {\n tools: McpToolInfo[];\n nextCursor?: string;\n}\n\nexport function parseToolListResponse(result: unknown): McpToolListResult {\n const r = (result ?? {}) as Record<string, unknown>;\n const rawTools = Array.isArray(r.tools) ? (r.tools as unknown[]) : [];\n const tools: McpToolInfo[] = [];\n for (const t of rawTools) {\n const tt = t as Record<string, unknown>;\n if (!tt || typeof tt.name !== 'string') continue; // 跳过非法工具\n tools.push({\n name: tt.name,\n description: typeof tt.description === 'string' ? tt.description : undefined,\n inputSchema: tt.inputSchema,\n annotations: tt.annotations,\n });\n }\n const nextCursor = typeof r.nextCursor === 'string' ? r.nextCursor : undefined;\n return { tools, nextCursor };\n}\n\n// ─── tools/call ───────────────────────────────────────────────\n\nexport function createCallToolRequest(\n id: number | string,\n name: string,\n args: unknown,\n): JsonRpcRequest {\n return createRequest(id, 'tools/call', { name, arguments: args ?? {} });\n}\n\n/**\n * 解析 tools/call 响应。容错:\n * - content 缺失 → 空数组\n * - 未知 type / 未知字段保留(由 adapter 层降级映射)\n * - JSON-RPC error 响应 → 转为 isError + 错误文本\n */\nexport function parseToolCallResult(result: unknown): McpToolCallResult {\n if (result && typeof result === 'object' && 'error' in result) {\n // 调用方传入的是整个 JSON-RPC error 对象(不应发生,但兜底)\n const err = (result as { error: { message?: string } }).error;\n return { content: [{ type: 'text', text: err?.message ?? 'MCP call error' }], isError: true };\n }\n const r = (result ?? {}) as Record<string, unknown>;\n const rawContent = Array.isArray(r.content) ? (r.content as unknown[]) : [];\n const content: McpContentBlock[] = [];\n for (const c of rawContent) {\n const cc = c as Record<string, unknown>;\n if (!cc || typeof cc.type !== 'string') {\n content.push({ type: 'text', text: '[unsupported content]' });\n continue;\n }\n content.push({\n type: cc.type,\n text: typeof cc.text === 'string' ? cc.text : undefined,\n data: typeof cc.data === 'string' ? cc.data : undefined,\n mimeType: typeof cc.mimeType === 'string' ? cc.mimeType : undefined,\n resource: cc.resource as McpContentBlock['resource'],\n });\n }\n if (content.length === 0) content.push({ type: 'text', text: '[empty result]' });\n // isError 仅在 true 时显式置位,否则 undefined(与 agent \"details.error 缺省 = 成功\" 约定一致)\n const isError = r.isError === true ? true : undefined;\n return { content, isError };\n}\n\n/** 把 JSON-RPC error 响应转为 MCP 工具调用结果(isError) */\nexport function errorResponseToCallResult(message: string): McpToolCallResult {\n return { content: [{ type: 'text', text: message }], isError: true };\n}\n\n// ─── ping ─────────────────────────────────────────────────────\n\nexport function createPingRequest(id: number | string): JsonRpcRequest {\n return createRequest(id, 'ping', {});\n}\n\n// ─── notifications ────────────────────────────────────────────\n\n/** 取消通知:告知 server 某请求已被取消(协作型 server 可停止计算) */\nexport function createCancelledNotification(\n requestId: number | string,\n reason?: string,\n): JsonRpcNotification {\n const params: Record<string, unknown> = { requestId };\n if (reason) params.reason = reason;\n return createNotification('notifications/cancelled', params);\n}\n\n/** 工具列表变更通知:订阅后 server 主动告知客户端重新拉取 */\nexport function createListChangedNotification(): JsonRpcNotification {\n return createNotification('notifications/tools/list_changed');\n}\n\nexport function isListChangedNotification(m: { method?: string }): boolean {\n return m.method === 'notifications/tools/list_changed';\n}\n\n// ─── 服务端方向:resources / prompts(M3,可选)──────────────\n// host 在 options 提供 resources / prompts 时才 advertise 对应 capability 并\n// 处理 resources/list | resources/read | prompts/list | prompts/get;\n// 未提供时 capability 缺省,方法回 -32601(method not found)。\n\nexport interface McpResource {\n uri: string;\n name?: string;\n description?: string;\n mimeType?: string;\n /** 内嵌文本(read 时返回 text 块) */\n text?: string;\n /** 内嵌二进制(base64;read 时返回 blob 块) */\n blob?: string;\n}\n\nexport interface McpPromptArgument {\n name: string;\n description?: string;\n required?: boolean;\n}\n\nexport interface McpPromptMessage {\n role: 'user' | 'assistant';\n content:\n | { type: 'text'; text: string }\n | { type: 'image'; data: string; mimeType?: string }\n | { type: 'resource'; resource: { uri: string; text?: string; blob?: string; mimeType?: string } };\n}\n\nexport interface McpPrompt {\n name: string;\n description?: string;\n arguments?: McpPromptArgument[];\n /** 静态消息(get 时返回);或由 host 外部动态构造 */\n messages?: McpPromptMessage[];\n}\n\n// ─── 服务端:入站请求 params 解析(纯函数,容错)──────────────\n\nexport function parseInitializeParams(params: unknown): {\n protocolVersion?: string;\n clientInfo?: McpClientInfo;\n capabilities?: Record<string, unknown>;\n} {\n const p = (params ?? {}) as Record<string, unknown>;\n return {\n protocolVersion: typeof p.protocolVersion === 'string' ? p.protocolVersion : undefined,\n clientInfo: p.clientInfo as McpClientInfo | undefined,\n capabilities: p.capabilities as Record<string, unknown> | undefined,\n };\n}\n\nexport function parseToolCallParams(params: unknown): { name?: string; arguments?: unknown } {\n const p = (params ?? {}) as Record<string, unknown>;\n return {\n name: typeof p.name === 'string' ? p.name : undefined,\n arguments: p.arguments,\n };\n}\n\nexport function parseListToolsParams(params: unknown): { cursor?: string } {\n const p = (params ?? {}) as Record<string, unknown>;\n return { cursor: typeof p.cursor === 'string' ? p.cursor : undefined };\n}\n\nexport function parseResourceReadParams(params: unknown): { uri?: string } {\n const p = (params ?? {}) as Record<string, unknown>;\n return { uri: typeof p.uri === 'string' ? p.uri : undefined };\n}\n\nexport function parsePromptGetParams(params: unknown): { name?: string; arguments?: Record<string, unknown> } {\n const p = (params ?? {}) as Record<string, unknown>;\n return {\n name: typeof p.name === 'string' ? p.name : undefined,\n arguments: p.arguments as Record<string, unknown> | undefined,\n };\n}\n\n// ─── 服务端:响应 result 构造(纯函数;host 用 createSuccessResponse 包装)──\n\nexport interface McpServerInfoLike {\n name: string;\n version: string;\n}\n\n/** 服务端 initialize 响应 result */\nexport function createInitializeResult(\n serverInfo: McpServerInfoLike,\n capabilities: McpServerCapabilities,\n): unknown {\n return {\n protocolVersion: MCP_PROTOCOL_VERSION,\n capabilities,\n serverInfo,\n };\n}\n\n/** 服务端 tools/list 响应 result */\nexport function buildToolsListResult(\n tools: Array<{ name: string; description?: string; inputSchema?: unknown }>,\n nextCursor?: string,\n): unknown {\n const list = tools.map((t) => {\n const out: Record<string, unknown> = { name: t.name };\n if (t.description !== undefined) out.description = t.description;\n out.inputSchema = t.inputSchema ?? { type: 'object', properties: {} };\n return out;\n });\n const r: Record<string, unknown> = { tools: list };\n if (nextCursor) r.nextCursor = nextCursor;\n return r;\n}\n\n/** 服务端 tools/call 响应 result */\nexport function buildToolCallResult(content: McpContentBlock[], isError?: boolean): unknown {\n const r: Record<string, unknown> = { content: content.length ? content : [{ type: 'text', text: '[empty result]' }] };\n if (isError) r.isError = true;\n return r;\n}\n\n/** 服务端 resources/list 响应 result */\nexport function buildResourcesListResult(resources: McpResource[], nextCursor?: string): unknown {\n const list = resources.map((r0) => {\n const out: Record<string, unknown> = { uri: r0.uri };\n if (r0.name !== undefined) out.name = r0.name;\n if (r0.description !== undefined) out.description = r0.description;\n if (r0.mimeType !== undefined) out.mimeType = r0.mimeType;\n return out;\n });\n const r: Record<string, unknown> = { resources: list };\n if (nextCursor) r.nextCursor = nextCursor;\n return r;\n}\n\n/** 服务端 resources/read 响应 result(按 uri 查找;未命中返回 null 交由 host 报错) */\nexport function buildResourceReadResult(resource: McpResource): unknown {\n const contents: Record<string, unknown> = { uri: resource.uri };\n if (resource.mimeType !== undefined) contents.mimeType = resource.mimeType;\n if (resource.text !== undefined) contents.text = resource.text;\n else if (resource.blob !== undefined) contents.blob = resource.blob;\n return { contents: [contents] };\n}\n\n/** 服务端 prompts/list 响应 result */\nexport function buildPromptsListResult(prompts: McpPrompt[], nextCursor?: string): unknown {\n const list = prompts.map((p0) => {\n const out: Record<string, unknown> = { name: p0.name };\n if (p0.description !== undefined) out.description = p0.description;\n if (p0.arguments !== undefined) out.arguments = p0.arguments;\n return out;\n });\n const r: Record<string, unknown> = { prompts: list };\n if (nextCursor) r.nextCursor = nextCursor;\n return r;\n}\n\n/** 服务端 prompts/get 响应 result */\nexport function buildPromptGetResult(messages: McpPromptMessage[]): unknown {\n return { messages: messages ?? [] };\n}\n\n// ─── sampling(server ↔ client LLM 补全请求,2025-06-18)──────────\n// server 经 sampling/createMessage 请求 client 用其 LLM 生成补全;双向:\n// - 客户端方向:外部 server 发起 → 本库 McpClient 应答(onSampling 钩子)\n// - 服务端方向:McpServerHost 发起 → 外部 client 应答(host.sampleLLM,\n// 经传输层出站通道;stdio-runner 自动接线请求/响应关联)\n\nexport interface McpSamplingContentBlock {\n type: 'text' | 'image';\n text?: string; // type=text\n data?: string; // type=image (base64)\n mimeType?: string; // type=image\n}\n\nexport interface McpSamplingMessage {\n role: 'user' | 'assistant';\n content: McpSamplingContentBlock | McpSamplingContentBlock[];\n}\n\nexport interface McpModelPreferences {\n hints?: Array<'cost' | 'speed' | 'intelligence' | 'quality'>;\n costPriority?: number;\n speedPriority?: number;\n intelligencePriority?: number;\n qualityPriority?: number;\n [key: string]: unknown;\n}\n\nexport interface McpCreateMessageParams {\n messages: McpSamplingMessage[];\n modelPreferences?: McpModelPreferences;\n systemPrompt?: string;\n includeContext?: 'none' | 'thisServer' | 'allServers';\n maxTokens?: number;\n stopSequences?: string[];\n metadata?: Record<string, unknown>;\n}\n\nexport interface McpCreateMessageResult {\n role: 'assistant';\n content: McpSamplingContentBlock;\n model: string;\n stopReason?: 'endTurn' | 'stopSequence' | 'maxTokens' | 'other';\n stopSequence?: string;\n usage?: { inputTokens?: number; outputTokens?: number; totalTokens?: number };\n}\n\n/** 构造 sampling/createMessage 请求(服务端方向发起;id 由调用方分配) */\nexport function createSamplingRequest(\n id: number | string,\n params: McpCreateMessageParams,\n): JsonRpcRequest {\n return createRequest(id, 'sampling/createMessage', params);\n}\n\n/** 解析入站 sampling/createMessage 请求 params(客户端方向应答用);容错:缺 messages 返回空数组 */\nexport function parseCreateMessageParams(payload: unknown): McpCreateMessageParams {\n const p = (payload ?? {}) as Record<string, unknown>;\n const messages = Array.isArray(p.messages) ? (p.messages as McpSamplingMessage[]) : [];\n const out: McpCreateMessageParams = { messages };\n if (p.systemPrompt !== undefined) out.systemPrompt = p.systemPrompt as string;\n if (p.includeContext !== undefined) out.includeContext = p.includeContext as McpCreateMessageParams['includeContext'];\n if (p.maxTokens !== undefined) out.maxTokens = p.maxTokens as number;\n if (p.modelPreferences !== undefined) out.modelPreferences = p.modelPreferences as McpModelPreferences;\n if (p.stopSequences !== undefined) out.stopSequences = p.stopSequences as string[];\n if (p.metadata !== undefined) out.metadata = p.metadata as Record<string, unknown>;\n return out;\n}\n\n/** 构造 sampling/createMessage 响应 result(客户端方向应答用) */\nexport function buildCreateMessageResult(result: McpCreateMessageResult): unknown {\n const out: Record<string, unknown> = {\n role: 'assistant',\n content: result.content,\n model: result.model,\n };\n if (result.stopReason !== undefined) out.stopReason = result.stopReason;\n if (result.stopSequence !== undefined) out.stopSequence = result.stopSequence;\n if (result.usage !== undefined) out.usage = result.usage;\n return out;\n}\n\n/** 解析 sampling/createMessage 响应 result(服务端方向发起后解析应答);容错:缺省字段给默认 */\nexport function parseCreateMessageResult(payload: unknown): McpCreateMessageResult {\n const r = (payload ?? {}) as Record<string, unknown>;\n const content = (r.content ?? { type: 'text', text: '' }) as McpSamplingContentBlock;\n return {\n role: 'assistant',\n content: typeof content.type === 'string' ? content : { type: 'text', text: '' },\n model: typeof r.model === 'string' ? r.model : 'unknown',\n stopReason: r.stopReason as McpCreateMessageResult['stopReason'],\n stopSequence: typeof r.stopSequence === 'string' ? r.stopSequence : undefined,\n usage: r.usage as McpCreateMessageResult['usage'],\n };\n}\n\nexport { isErrorResponse };\n","/**\n * server/host.ts - MCP 服务端宿主(Node only,但消息分发逻辑为纯 async)\n *\n * 把 aipack 原生 Tool[] / resources / prompts 反向暴露为标准 MCP Server,\n * 供外部 MCP 客户端(Claude Desktop、Cursor 等)调用。\n *\n * 与 multi-agent/MCPBridge 的关系:泛化而非复制——MCPBridge 保持不动\n * (避免 breaking),本模块提供面向任意 Tool[] 的通用实现;MCPBridge 后续可迁移。\n *\n * 设计:\n * - 传输层无关:只产 / 解 JSON-RPC 消息,由 stdio-entry / http 入口驱动\n * - 入站三类消息:响应(不应收到,忽略)、通知(initialized/cancelled,no-op)、\n * 请求(dispatch:initialize / tools/* / resources/* / prompts/* / ping)\n * - 工具调用经 authorize 钩子裁决(stdio 本地默认放行;可注入 PermissionPolicy 包装)\n * - agent ToolResult.content → MCP content blocks(text/image 1:1;thinking/toolCall\n * 降级为文本摘要),details.error 存在 → isError\n * - 未知方法回 -32601;非法 params 内部抛错回 -32603\n */\n\nimport type {\n Tool,\n ToolResult,\n ContentBlock,\n TextContent,\n ImageContent,\n} from '@aipack-ai/agent';\nimport * as jsonrpc from '../client/jsonrpc';\nimport {\n createInitializeResult,\n buildToolsListResult,\n buildToolCallResult,\n buildResourcesListResult,\n buildResourceReadResult,\n buildPromptsListResult,\n buildPromptGetResult,\n parseToolCallParams,\n parseResourceReadParams,\n parsePromptGetParams,\n parseCreateMessageResult,\n createListChangedNotification,\n type McpServerCapabilities,\n type McpContentBlock,\n type McpResource,\n type McpPrompt,\n type McpServerInfoLike,\n type McpCreateMessageParams,\n type McpCreateMessageResult,\n} from '../client/protocol';\n\n// ─── 反向 content 映射(agent ContentBlock → MCP content block)──────────\n\n/**\n * agent ContentBlock → MCP McpContentBlock。\n * - text → { type:'text', text }\n * - image → { type:'image', data, mimeType }(缺 mimeType 降级文本)\n * - thinking → { type:'text', text }(MCP 无 thinking 概念,透传为文本)\n * - toolCall → { type:'text', text: JSON }(摘要)\n */\nexport function mapAgentContentToMcp(blocks: ContentBlock[]): McpContentBlock[] {\n const out: McpContentBlock[] = [];\n for (const b of blocks) {\n out.push(mapOneAgentBlock(b));\n }\n return out.length ? out : [{ type: 'text', text: '[empty result]' }];\n}\n\nfunction mapOneAgentBlock(b: ContentBlock): McpContentBlock {\n if (b.type === 'text') {\n const t = b as TextContent;\n return { type: 'text', text: t.text };\n }\n if (b.type === 'image') {\n const img = b as ImageContent;\n if (typeof img.data === 'string' && typeof img.mimeType === 'string') {\n return { type: 'image', data: img.data, mimeType: img.mimeType };\n }\n return { type: 'text', text: '[image: missing data/mimeType]' };\n }\n // thinking / toolCall:降级为文本摘要\n return { type: 'text', text: JSON.stringify(b) };\n}\n\n/** agent ToolResult → MCP tools/call 结果(isError 由 details.error 推导) */\nexport function toolResultToMcpCallResult(result: ToolResult): { content: McpContentBlock[]; isError?: boolean } {\n const isError = isToolResultError(result);\n return { content: mapAgentContentToMcp(result.content ?? []), isError: isError ? true : undefined };\n}\n\nfunction isToolResultError(result: ToolResult): boolean {\n const d = result.details;\n if (d && typeof d === 'object' && 'error' in (d as Record<string, unknown>)) {\n const e = (d as Record<string, unknown>).error;\n return !!e || typeof e === 'string';\n }\n return false;\n}\n\n// ─── 选项 ─────────────────────────────────────────────────────\n\nexport interface McpAuthorizeCall {\n /** 工具名 */\n toolName: string;\n /** 工具声明的权限能力 */\n permissions: readonly string[];\n /** 经 prepareArguments 处理后的参数 */\n args: unknown;\n}\n\n/**\n * 授权钩子:返回 true 放行、false 拒绝(→ isError 结果)。\n * stdio 本地默认放行(对齐计划\"本地拉起默认放行\");http 场景可注入\n * 包装 PermissionPolicy 的 authorize(check → allow/confirm 视为 true,deny/pending 视为 false)。\n */\nexport type McpAuthorizeFn = (call: McpAuthorizeCall) => Promise<boolean>;\n\nexport interface McpServerHostOptions {\n /** serverInfo.name */\n name: string;\n /** 默认 '0.1.0' */\n version?: string;\n /** 暴露的工具集合(静态数组或动态解析器,支持运行时热变更) */\n tools: Tool[] | (() => Tool[] | Promise<Tool[]>);\n /** 可选 resources(提供则 advertise resources capability 并处理 resources/* ) */\n resources?: McpResource[] | (() => McpResource[] | Promise<McpResource[]>);\n /** 可选 prompts(提供则 advertise prompts capability 并处理 prompts/* ) */\n prompts?: McpPrompt[] | (() => McpPrompt[] | Promise<McpPrompt[]>);\n /** 工具调用授权钩子;缺省放行 */\n authorize?: McpAuthorizeFn;\n /** 单次工具调用超时(默认不设,交由工具自身/runtime) */\n toolTimeoutMs?: number;\n /**\n * 启用 sampling 能力:advertise `sampling` capability,并提供 `sampleLLM()`\n * 供工具经传输层出站通道向外部 client 请求 LLM 补全。出站通道由传输层\n * (stdio-runner)经 `setOutboundRequest` 注入;未注入时 `sampleLLM` 抛错。\n */\n sampling?: boolean;\n /**\n * 直接注入出站请求通道(高级用例;stdio-runner 会自动注入,通常无需手填)。\n * 提供时同样会 advertise sampling 能力。\n */\n onOutboundRequest?: (method: string, params?: unknown) => Promise<unknown>;\n /** 服务端主动发出的通知(如 tools/list_changed)落点;stdio-entry 用以写 stdout */\n onNotification?: (msg: jsonrpc.JsonRpcNotification) => void;\n}\n\n// ─── McpServerHost ─────────────────────────────────────────────\n\n/**\n * MCP 服务端宿主。传输层无关——只产 / 解 JSON-RPC 消息。\n *\n * 用法(程序化):\n * const host = createMcpServerHost({ name: 'my-agent', tools: [...] });\n * const resp = await host.handleRequest(parsedRequest);\n *\n * 独立进程入口见 `./stdio-entry.ts`。\n */\nexport class McpServerHost {\n private serverInfo: McpServerInfoLike;\n private toolsResolver: () => Tool[] | Promise<Tool[]>;\n private resourcesResolver?: () => McpResource[] | Promise<McpResource[]>;\n private promptsResolver?: () => McpPrompt[] | Promise<McpPrompt[]>;\n private authorize?: McpAuthorizeFn;\n private toolTimeoutMs?: number;\n private onNotification?: (msg: jsonrpc.JsonRpcNotification) => void;\n private samplingEnabled: boolean;\n private outboundRequest?: (method: string, params?: unknown) => Promise<unknown>;\n private capabilities: McpServerCapabilities;\n\n constructor(options: McpServerHostOptions) {\n this.serverInfo = { name: options.name, version: options.version ?? '0.1.0' };\n this.toolsResolver = typeof options.tools === 'function'\n ? options.tools as () => Tool[] | Promise<Tool[]>\n : () => options.tools as Tool[];\n if (options.resources) {\n this.resourcesResolver = typeof options.resources === 'function'\n ? options.resources as () => McpResource[] | Promise<McpResource[]>\n : () => options.resources as McpResource[];\n }\n if (options.prompts) {\n this.promptsResolver = typeof options.prompts === 'function'\n ? options.prompts as () => McpPrompt[] | Promise<McpPrompt[]>\n : () => options.prompts as McpPrompt[];\n }\n this.authorize = options.authorize;\n this.toolTimeoutMs = options.toolTimeoutMs;\n this.onNotification = options.onNotification;\n this.outboundRequest = options.onOutboundRequest;\n this.samplingEnabled = options.sampling === true || !!options.onOutboundRequest;\n this.capabilities = this.computeCapabilities();\n }\n\n getServerInfo(): McpServerInfoLike {\n return { ...this.serverInfo };\n }\n\n getCapabilities(): McpServerCapabilities {\n return { ...this.capabilities };\n }\n\n private computeCapabilities(): McpServerCapabilities {\n const caps: Record<string, unknown> = { tools: {} };\n if (this.resourcesResolver) caps.resources = {};\n if (this.promptsResolver) caps.prompts = {};\n if (this.samplingEnabled) caps.sampling = {};\n return caps as McpServerCapabilities;\n }\n\n /** 主动通知客户端工具列表已变更 */\n notifyToolsListChanged(): void {\n this.onNotification?.(createListChangedNotification());\n }\n\n /**\n * 注入通知分发钩子(由传输层如 http-runner 调用):host 经此回调发出主动通知。\n * 与 setOutboundRequest 对称。重复调用以最后一次为准。\n */\n setOnNotification(fn: (msg: jsonrpc.JsonRpcNotification) => void): void {\n this.onNotification = fn;\n }\n\n /**\n * 注入出站请求通道(由传输层如 stdio-runner 调用):写入 JSON-RPC 请求\n * 并关联响应。注入后 `sampleLLM` 可向外部 client 请求 LLM 补全。\n */\n setOutboundRequest(fn: (method: string, params?: unknown) => Promise<unknown>): void {\n this.outboundRequest = fn;\n if (!this.samplingEnabled) {\n this.samplingEnabled = true;\n this.capabilities = this.computeCapabilities();\n }\n }\n\n /**\n * 经出站通道向外部 client 请求 LLM 补全(sampling/createMessage)。\n * 需传输层(stdio-runner)已注入出站通道;未注入则抛错。\n */\n async sampleLLM(params: McpCreateMessageParams): Promise<McpCreateMessageResult> {\n if (!this.outboundRequest) {\n throw new Error('sampling unavailable: outbound request channel not attached');\n }\n const raw = await this.outboundRequest('sampling/createMessage', params);\n return parseCreateMessageResult(raw);\n }\n\n /**\n * 处理一条入站 JSON-RPC 消息。\n * - 请求 → 返回响应(JsonRpcResponse)\n * - 通知 → 返回 null(不回写)\n * - 响应 / 非法消息 → 返回 null\n */\n async handleRequest(input: unknown): Promise<jsonrpc.JsonRpcMessage | null> {\n const msg = jsonrpc.classify(input);\n if (!msg) return null;\n\n if (jsonrpc.isResponse(msg)) return null; // 服务端不处理客户端响应\n\n if (jsonrpc.isNotification(msg)) {\n // notifications/initialized / notifications/cancelled:no-op\n return null;\n }\n\n if (!jsonrpc.isRequest(msg)) return null;\n return this.onRequest(msg as jsonrpc.JsonRpcRequest);\n }\n\n private async onRequest(req: jsonrpc.JsonRpcRequest): Promise<jsonrpc.JsonRpcMessage> {\n try {\n switch (req.method) {\n case 'initialize':\n return jsonrpc.createSuccessResponse(\n req.id,\n createInitializeResult(this.serverInfo, this.capabilities),\n );\n case 'notifications/initialized':\n return jsonrpc.createSuccessResponse(req.id, {});\n case 'tools/list':\n return jsonrpc.createSuccessResponse(\n req.id,\n buildToolsListResult(await this.toToolInfos(await this.toolsResolver())),\n );\n case 'tools/call':\n return jsonrpc.createSuccessResponse(req.id, await this.handleToolCall(req));\n case 'ping':\n return jsonrpc.createSuccessResponse(req.id, {});\n case 'resources/list':\n if (!this.resourcesResolver) break;\n return jsonrpc.createSuccessResponse(\n req.id,\n buildResourcesListResult(await this.resourcesResolver()),\n );\n case 'resources/read': {\n if (!this.resourcesResolver) break;\n const { uri } = parseResourceReadParams(req.params);\n if (!uri) return jsonrpc.createErrorResponse(req.id, jsonrpc.INVALID_PARAMS, 'resources/read requires uri');\n const found = (await this.resourcesResolver()).find((r) => r.uri === uri);\n if (!found) return jsonrpc.createErrorResponse(req.id, jsonrpc.INVALID_PARAMS, `resource not found: ${uri}`);\n return jsonrpc.createSuccessResponse(req.id, buildResourceReadResult(found));\n }\n case 'prompts/list':\n if (!this.promptsResolver) break;\n return jsonrpc.createSuccessResponse(\n req.id,\n buildPromptsListResult(await this.promptsResolver()),\n );\n case 'prompts/get': {\n if (!this.promptsResolver) break;\n const { name } = parsePromptGetParams(req.params);\n if (!name) return jsonrpc.createErrorResponse(req.id, jsonrpc.INVALID_PARAMS, 'prompts/get requires name');\n const found = (await this.promptsResolver()).find((p) => p.name === name);\n if (!found) return jsonrpc.createErrorResponse(req.id, jsonrpc.INVALID_PARAMS, `prompt not found: ${name}`);\n return jsonrpc.createSuccessResponse(req.id, buildPromptGetResult(found.messages ?? []));\n }\n default:\n break;\n }\n return jsonrpc.createErrorResponse(\n req.id,\n jsonrpc.METHOD_NOT_FOUND,\n `method not found: ${req.method}`,\n );\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n return jsonrpc.createErrorResponse(req.id, jsonrpc.INTERNAL_ERROR, message);\n }\n }\n\n private async handleToolCall(req: jsonrpc.JsonRpcRequest): Promise<unknown> {\n const { name, arguments: args } = parseToolCallParams(req.params);\n if (!name) {\n return buildToolCallResult(\n [{ type: 'text', text: 'tools/call requires name' }],\n true,\n );\n }\n const tools = await this.toolsResolver();\n const tool = tools.find((t) => t.name === name);\n if (!tool) {\n return buildToolCallResult(\n [{ type: 'text', text: `unknown tool: ${name}` }],\n true,\n );\n }\n\n const prepared = tool.prepareArguments ? tool.prepareArguments(args) : args;\n\n // 授权(stdio 本地默认放行)\n if (this.authorize) {\n const allowed = await this.authorize({\n toolName: tool.name,\n permissions: tool.permissions ?? [],\n args: prepared,\n });\n if (!allowed) {\n return buildToolCallResult(\n [{ type: 'text', text: `permission denied: ${tool.name}` }],\n true,\n );\n }\n }\n\n let result: ToolResult;\n try {\n result = await this.callWithTimeout(tool, prepared);\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err);\n return buildToolCallResult(\n [{ type: 'text', text: `tool execution failed: ${message}` }],\n true,\n );\n }\n const mapped = toolResultToMcpCallResult(result);\n return buildToolCallResult(mapped.content, mapped.isError);\n }\n\n private callWithTimeout(tool: Tool, args: unknown): Promise<ToolResult> {\n if (!this.toolTimeoutMs) return tool.execute('mcp', args);\n return new Promise<ToolResult>((resolve, reject) => {\n const ac = new AbortController();\n const timer = setTimeout(() => {\n ac.abort();\n reject(new Error(`tools/call timeout: ${tool.name} (${this.toolTimeoutMs}ms)`));\n }, this.toolTimeoutMs);\n tool.execute('mcp', args, ac.signal).then(\n (r) => { clearTimeout(timer); resolve(r); },\n (e) => { clearTimeout(timer); reject(e); },\n );\n });\n }\n\n private toToolInfos(tools: Tool[]): Array<{ name: string; description?: string; inputSchema?: unknown }> {\n return tools.map((t) => ({\n name: t.name,\n description: t.description,\n inputSchema: t.parameters,\n }));\n }\n}\n\n/** 工厂 */\nexport function createMcpServerHost(options: McpServerHostOptions): McpServerHost {\n return new McpServerHost(options);\n}\n","/**\n * extensions/mcp-bridge.ts - MCPBridge Extension\n *\n * 将 AgentGraph 暴露为 MCP (Model Context Protocol) 工具,\n * 使外部 MCP 客户端可以直接调用多 Agent 编排图。\n *\n * 设计原则:不依赖外部 MCP SDK,仅输出符合 MCP 规范的 JSON 结构,\n * 由宿主环境(如 aipack CLI)负责实际的 MCP 传输层。\n */\n\nimport type { AgentGraph, MCPBridgeOpts, MultiAgentResult } from '../core/types';\nimport type { Tool, ToolResult, ContentBlock } from '@aipack-ai/agent';\nimport { createMcpServerHost } from '@aipack-ai/mcp';\nimport type { McpServerHost } from '@aipack-ai/mcp';\n\n// ─── MCP 工具定义 ────────────────────────────────────────────────\n\n/** MCP 工具参数定义 */\nexport interface MCPToolParameter {\n name: string;\n description: string;\n type: 'string' | 'number' | 'boolean' | 'object' | 'array';\n required?: boolean;\n}\n\n/** MCP 工具定义 */\nexport interface MCPToolDefinition {\n /** 工具名 */\n name: string;\n /** 工具描述 */\n description: string;\n /** 参数 schema */\n parameters: MCPToolParameter[];\n}\n\n/** MCP 工具调用请求 */\nexport interface MCPToolCallRequest {\n /** 工具名 */\n name: string;\n /** 参数 */\n arguments: Record<string, unknown>;\n}\n\n/** MCP 工具调用结果 */\nexport interface MCPToolCallResult {\n /** 是否错误 */\n isError?: boolean;\n /** 结果内容列表 */\n content: Array<{\n type: 'text' | 'image' | 'resource';\n text?: string;\n data?: string;\n mimeType?: string;\n }>;\n}\n\n// ─── MCPBridge ───────────────────────────────────────────────────\n\n/**\n * MCPBridge:将 AgentGraph 注册为 MCP 工具\n *\n * 用法:\n * ```typescript\n * const bridge = new MCPBridge(graph, { toolPrefix: 'ma_' });\n *\n * // 获取工具列表(供 MCP Server 注册)\n * const tools = bridge.listTools();\n *\n * // 处理工具调用\n * const result = await bridge.handleCall({ name: 'ma_run', arguments: { input: '...' } });\n *\n * // M3:经标准 stdio MCP Server 暴露(补齐传输层,供 Claude Desktop 等拉起)\n * import { runStdioServer } from '@aipack-ai/mcp';\n * await runStdioServer(bridge.toMcpServerHost());\n * ```\n *\n * M3 起,run/status 核心逻辑在 handleCall(legacy)与 asTools(统一路径)间共享,\n * 避免与 packages/mcp 的协议实现重复。\n */\nexport class MCPBridge {\n private graph: AgentGraph;\n private opts: Required<MCPBridgeOpts>;\n\n constructor(graph: AgentGraph, opts?: MCPBridgeOpts) {\n this.graph = graph;\n this.opts = {\n serverName: opts?.serverName ?? 'aipack-multi-agent',\n serverVersion: opts?.serverVersion ?? '1.0.0',\n toolPrefix: opts?.toolPrefix ?? '',\n };\n }\n\n /** 获取 MCP Server 信息 */\n getServerInfo() {\n return {\n name: this.opts.serverName,\n version: this.opts.serverVersion,\n };\n }\n\n /** 列出所有可用 MCP 工具(legacy 形状:MCPToolDefinition[]) */\n listTools(): MCPToolDefinition[] {\n const prefix = this.opts.toolPrefix;\n\n return [\n {\n name: `${prefix}run`,\n description: '运行多Agent编排图,传入用户输入,返回执行结果',\n parameters: [\n {\n name: 'input',\n description: '用户输入文本',\n type: 'string',\n required: true,\n },\n ],\n },\n {\n name: `${prefix}status`,\n description: '获取当前图执行状态',\n parameters: [],\n },\n ];\n }\n\n // ─── 核心逻辑(handleCall 与 asTools 共享,单一来源)──────────────\n\n /** run 工具核心:执行图并序列化为 MCP 形状结果 */\n private async runTool(input: unknown): Promise<MCPToolCallResult> {\n const inputText = input as string | undefined;\n if (!inputText) {\n return {\n isError: true,\n content: [{ type: 'text', text: '缺少必需参数: input' }],\n };\n }\n\n const result = await this.graph.run(inputText);\n return {\n content: [\n {\n type: 'text',\n text: JSON.stringify({\n success: result.success,\n content: result.content,\n lastAgentId: result.lastAgentId,\n stepsCompleted: result.stepsCompleted,\n stopReason: result.stopReason,\n totalUsage: result.totalUsage,\n }, null, 2),\n },\n ],\n };\n }\n\n /** status 工具核心:图执行状态序列化为 MCP 形状结果 */\n private statusTool(): MCPToolCallResult {\n const state = this.graph.getState();\n return {\n content: [\n {\n type: 'text',\n text: JSON.stringify({\n currentAgentId: state.currentAgentId,\n stepsCompleted: state.stepsCompleted,\n finished: state.finished,\n error: state.error,\n nodeStates: Object.fromEntries(state.nodeStates),\n }, null, 2),\n },\n ],\n };\n }\n\n /** 处理 MCP 工具调用(legacy API,行为保持不变) */\n async handleCall(request: MCPToolCallRequest): Promise<MCPToolCallResult> {\n const prefix = this.opts.toolPrefix;\n const runToolName = `${prefix}run`;\n const statusToolName = `${prefix}status`;\n\n try {\n if (request.name === runToolName) {\n return await this.runTool(request.arguments.input);\n }\n if (request.name === statusToolName) {\n return this.statusTool();\n }\n return {\n isError: true,\n content: [{ type: 'text', text: `未知工具: ${request.name}` }],\n };\n } catch (err) {\n return {\n isError: true,\n content: [\n {\n type: 'text',\n text: `执行错误: ${err instanceof Error ? err.message : String(err)}`,\n },\n ],\n };\n }\n }\n\n // ─── M3 统一:暴露为 agent 原生 Tool[],接入 McpServerHost / stdio 传输 ──\n\n /**\n * 将 AgentGraph 暴露为 agent 原生 `Tool[]`(JSON Schema 参数 + execute)。\n * 可直接喂给 `@aipack-ai/mcp` 的 `createMcpServerHost({ tools })`,\n * 再经 `runStdioServer` 拉起为标准 stdio MCP Server——补齐 MCPBridge\n * 原本缺失的传输层(\"由宿主环境负责实际的 MCP 传输\" 这一缺口)。\n *\n * 工具 `${prefix}run` / `${prefix}status` 与 legacy `listTools()`/`handleCall()`\n * 共享 `runTool` / `statusTool` 核心,语义一致。\n */\n asTools(): Tool[] {\n const prefix = this.opts.toolPrefix;\n return [\n {\n name: `${prefix}run`,\n description: '运行多Agent编排图,传入用户输入,返回执行结果',\n parameters: {\n type: 'object',\n properties: { input: { type: 'string', description: '用户输入文本' } },\n required: ['input'],\n },\n permissions: [],\n execute: async (_id: string, args: unknown): Promise<ToolResult> => {\n const input = (args as { input?: string } | null)?.input;\n return toToolResult(await this.runTool(input));\n },\n },\n {\n name: `${prefix}status`,\n description: '获取当前图执行状态',\n parameters: { type: 'object', properties: {} },\n permissions: [],\n execute: async (): Promise<ToolResult> => toToolResult(this.statusTool()),\n },\n ];\n }\n\n /**\n * 构建一个 `McpServerHost`(来自 `@aipack-ai/mcp`),把本 AgentGraph 作为\n * 标准 MCP Server 暴露。配合 `runStdioServer(host)` 即可经 stdin/stdout\n * 服务外部 MCP 客户端(Claude Desktop / Cursor)。\n *\n * 与 legacy `handleCall()` 共享 `runTool` / `statusTool` 核心,保证语义一致。\n */\n toMcpServerHost(): McpServerHost {\n return createMcpServerHost({\n name: this.opts.serverName,\n version: this.opts.serverVersion,\n tools: this.asTools(),\n });\n }\n}\n\n/** MCPToolCallResult → agent ToolResult(isError → details.error,对齐 mcp 包约定) */\nfunction toToolResult(r: MCPToolCallResult): ToolResult {\n const isError = r.isError === true;\n return {\n content: r.content as ContentBlock[],\n details: isError ? { error: r.content[0]?.text ?? 'error' } : undefined,\n };\n}\n\n// ─── createMCPBridge 工厂函数 ────────────────────────────────────\n\n/** 创建 MCPBridge */\nexport function createMCPBridge(graph: AgentGraph, opts?: MCPBridgeOpts): MCPBridge {\n return new MCPBridge(graph, opts);\n}\n\n/**\n * 便捷工厂:从 AgentGraph 直接构建一个 `McpServerHost`(@aipack-ai/mcp),\n * 供 `runStdioServer(host)` 拉起为标准 stdio MCP Server。\n *\n * ```typescript\n * import { runStdioServer } from '@aipack-ai/mcp';\n * const host = createMultiAgentMcpServerHost(graph, { serverName: 'my-graph' });\n * await runStdioServer(host);\n * ```\n */\nexport function createMultiAgentMcpServerHost(graph: AgentGraph, opts?: MCPBridgeOpts): McpServerHost {\n return new MCPBridge(graph, opts).toMcpServerHost();\n}\n","/**\n * extensions/debug.ts - 可视化调试扩展\n *\n * 提供:\n * 1. DOT 格式图结构导出(可用 Graphviz 渲染)\n * 2. 执行 Trace 记录(GraphTrace)\n * 3. 执行过程日志\n */\n\nimport type {\n AgentGraph,\n AgentNode,\n AgentEdge,\n GraphTrace,\n TraceStep,\n MultiAgentEvent,\n MultiAgentResult,\n NodeExecutionState,\n} from '../core/types';\n\n// ─── GraphDebugger ───────────────────────────────────────────────\n\n/**\n * GraphDebugger:图可视化调试工具\n *\n * 用法:\n * ```typescript\n * const debugger_ = new GraphDebugger(graph);\n *\n * // 导出 DOT 格式\n * const dot = debugger_.toDOT();\n *\n * // 运行并记录 trace\n * const trace = await debugger_.trace('用户输入');\n *\n * // 导出 trace 为 JSON\n * const json = debugger_.traceToJSON(trace);\n * ```\n */\nexport class GraphDebugger {\n private graph: AgentGraph;\n private nodes: Map<string, AgentNode> = new Map();\n private edges: AgentEdge[] = [];\n private entryId?: string;\n\n constructor(graph: AgentGraph, nodes?: AgentNode[], edges?: AgentEdge[], entryId?: string) {\n this.graph = graph;\n if (nodes) {\n for (const node of nodes) {\n this.nodes.set(node.id, node);\n }\n }\n if (edges) {\n this.edges = edges;\n }\n this.entryId = entryId;\n }\n\n /** 设置图元数据(供无法直接访问内部结构的场景使用) */\n setGraphMeta(nodes: AgentNode[], edges: AgentEdge[], entryId?: string): void {\n this.nodes.clear();\n for (const node of nodes) {\n this.nodes.set(node.id, node);\n }\n this.edges = edges;\n this.entryId = entryId;\n }\n\n /** 导出为 DOT 格式 */\n toDOT(): string {\n const lines: string[] = [];\n lines.push('digraph AgentGraph {');\n lines.push(' rankdir=LR;');\n lines.push(' node [shape=box, style=filled, fillcolor=\"#e8f4fd\", fontname=\"Arial\"];');\n lines.push(' edge [fontname=\"Arial\", fontsize=10];');\n lines.push('');\n\n // 节点\n for (const [id, node] of this.nodes) {\n const isEntry = id === this.entryId;\n const fillColor = isEntry ? '#4CAF50' : '#e8f4fd';\n const fontColor = isEntry ? 'white' : 'black';\n const label = `${node.name}\\\\n(${id})`;\n lines.push(` \"${id}\" [label=\"${label}\", fillcolor=\"${fillColor}\", fontcolor=\"${fontColor}\"];`);\n }\n\n lines.push('');\n\n // 边\n for (const edge of this.edges) {\n const hasCondition = !!edge.condition;\n const style = hasCondition ? 'dashed' : 'solid';\n const label = hasCondition ? '条件' : '';\n lines.push(` \"${edge.from}\" -> \"${edge.to}\" [style=${style}, label=\"${label}\"];`);\n }\n\n lines.push('}');\n return lines.join('\\n');\n }\n\n /** 执行图并记录 Trace */\n async trace(input: string): Promise<GraphTrace> {\n const traceId = `trace-${Date.now()}`;\n const graphStartTime = Date.now();\n const steps: TraceStep[] = [];\n let stepIndex = 0;\n let finalResult: MultiAgentResult | undefined;\n\n // 收集事件\n for await (const event of this.graph.stream(input)) {\n if (event.type === 'agent_start') {\n stepIndex++;\n steps.push({\n step: stepIndex,\n agentId: event.agentId,\n agentName: event.agentName,\n startTime: Date.now(),\n duration: 0,\n input: event.input ?? '',\n output: '',\n state: 'running',\n });\n } else if (event.type === 'agent_result') {\n // 找最后一个匹配的 running step(同一 agent 可能执行多次)\n const step = this.findLastRunning(steps, event.agentId);\n if (step) {\n step.duration = Date.now() - step.startTime;\n step.output = this.truncate(event.result.content, 200);\n step.state = 'completed';\n } else {\n // 如果找不到 running step,回退到找最后一个同 agentId 的 step\n const fallback = this.findLastById(steps, event.agentId);\n if (fallback) {\n fallback.duration = Date.now() - fallback.startTime;\n fallback.output = this.truncate(event.result.content, 200);\n fallback.state = 'completed';\n }\n }\n } else if (event.type === 'agent_error') {\n const step = this.findLastRunning(steps, event.agentId);\n if (step) {\n step.duration = Date.now() - step.startTime;\n step.error = event.error;\n step.state = 'failed';\n }\n } else if (event.type === 'graph_done') {\n finalResult = event.result;\n }\n }\n\n // 获取最终结果\n const state = this.graph.getState();\n const graphDuration = Date.now() - graphStartTime;\n\n return {\n traceId,\n startTime: graphStartTime,\n duration: graphDuration,\n steps,\n result: {\n success: finalResult ? finalResult.success : !state.error,\n content: finalResult?.content ?? '',\n stopReason: finalResult?.stopReason ?? (state.error ? 'error' : 'completed'),\n stepsCompleted: finalResult?.stepsCompleted ?? state.stepsCompleted,\n },\n };\n }\n\n /** 将 Trace 转为 JSON 字符串 */\n traceToJSON(trace: GraphTrace): string {\n return JSON.stringify(trace, null, 2);\n }\n\n /** 将 Trace 转为可读的执行日志 */\n traceToLog(trace: GraphTrace): string {\n const lines: string[] = [];\n lines.push(`=== Graph Trace: ${trace.traceId} ===`);\n lines.push(`Duration: ${trace.duration}ms`);\n lines.push('');\n\n for (const step of trace.steps) {\n const status = step.state === 'completed' ? 'OK' : step.state === 'failed' ? 'FAIL' : step.state;\n lines.push(`[${step.step}] ${step.agentName} (${step.agentId}) - ${status} (${step.duration}ms)`);\n if (step.input) lines.push(` Input: ${this.truncate(step.input, 100)}`);\n if (step.output) lines.push(` Output: ${this.truncate(step.output, 100)}`);\n if (step.error) lines.push(` Error: ${step.error}`);\n lines.push('');\n }\n\n lines.push(`Result: ${trace.result.success ? 'SUCCESS' : 'FAILED'} (${trace.result.stopReason})`);\n return lines.join('\\n');\n }\n\n private truncate(text: string, maxLength: number): string {\n if (text.length <= maxLength) return text;\n return text.slice(0, maxLength) + '...';\n }\n\n /** 找最后一个匹配 agentId 且状态为 running 的 step */\n private findLastRunning(steps: TraceStep[], agentId: string): TraceStep | undefined {\n for (let i = steps.length - 1; i >= 0; i--) {\n if (steps[i].agentId === agentId && steps[i].state === 'running') {\n return steps[i];\n }\n }\n return undefined;\n }\n\n /** 找最后一个匹配 agentId 的 step(不管状态) */\n private findLastById(steps: TraceStep[], agentId: string): TraceStep | undefined {\n for (let i = steps.length - 1; i >= 0; i--) {\n if (steps[i].agentId === agentId) {\n return steps[i];\n }\n }\n return undefined;\n }\n}\n\n// ─── createDebugger 工厂函数 ─────────────────────────────────────\n\n/** 创建 GraphDebugger */\nexport function createDebugger(graph: AgentGraph): GraphDebugger {\n return new GraphDebugger(graph);\n}\n"],"mappings":"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","names":[]}
|