多 Agent 协作
Eino 提供两种协作方式:AgentAsTool(委派式,推荐)和 Workflow Agents(确定性编排),以及三种内置 Agent 模式:Supervisor、Plan-Execute、DeepAgent。
协作方式概览
| 方式 | 机制 | 适用场景 |
|---|---|---|
| AgentAsTool(推荐) | 子 Agent 包装为 Tool,父 Agent 自主决定调用 | 委派子任务、能力组合 |
| Workflow | Sequential / Parallel / Loop 确定性编排 | 流程固定的多步任务 |
AgentAsTool — 委派式协作
将子 Agent 包装为 Tool,父 Agent 像调用普通工具一样调用它。
// 创建子 Agent
subAgent, _ := adk.NewChatModelAgent(ctx, &adk.ChatModelAgentConfig{
Name: "researcher",
Description: "搜索并总结相关信息",
Instruction: "你是一个研究助手...",
Model: chatModel,
ToolsConfig: adk.ToolsConfig{
Tools: []tool.BaseTool{searchTool},
},
})
// 包装为 Tool
agentTool := adk.NewAgentTool(ctx, subAgent)
// 父 Agent 注册
parentAgent, _ := adk.NewChatModelAgent(ctx, &adk.ChatModelAgentConfig{
Name: "coordinator",
Description: "协调任务",
Instruction: "你是任务协调者...",
Model: chatModel,
ToolsConfig: adk.ToolsConfig{
Tools: []tool.BaseTool{agentTool},
},
})AgentTool 选项
| 选项 | 说明 |
|---|---|
WithFullChatHistoryAsInput() |
将父 Agent 完整对话历史作为子 Agent 输入(默认只传模型生成的 request 参数) |
WithAgentInputSchema(schema) |
自定义子 Agent 输入 schema |
事件流透传
ToolsConfig.EmitInternalEvents = true 时,子 Agent 的事件实时透传至父 Agent 事件流,终端用户可见子 Agent 中间过程。
💡 透传事件不影响父 Agent checkpoints,仅用于用户展示。唯一例外是
Interruptedaction 会跨边界传播。
关键特性
- 父 Agent 保持控制权,可基于子 Agent 结果继续推理
- 子 Agent 不继承父 Agent 完整对话历史 → 上下文隔离
- 多个子 Agent 可并行调用
- 子 Agent 间不共享上下文,各接收独立任务描述
Workflow Agents — 确定性编排
用于流程固定的多步任务。通过 Transfer 在 Agent 间传递上下文:上游输出自动拼接为下游输入 Messages。
Sequential — 顺序执行
sequential := adk.NewSequentialAgent(ctx, &adk.SequentialAgentConfig{
Name: "research_pipeline",
SubAgents: []adk.Agent{planAgent, searchAgent, writeAgent},
})- 严格按
SubAgents顺序线性执行 - 任一子 Agent 产生退出 / 中断动作,整个流程立即终止
- 下游可获取完整输入 + 所有前序 Agent 的输出
Parallel — 并发执行
parallel := adk.NewParallelAgent(ctx, &adk.ParallelAgentConfig{
Name: "multi_analysis",
SubAgents: []adk.Agent{sentimentAgent, keywordAgent, summaryAgent},
})- 所有子 Agent 同时启动,独立 goroutine 并发执行
- 共享同一份初始输入
- 通过
sync.WaitGroup等待全部完成后,按接收顺序输出到AsyncIterator
Loop — 循环执行
loop := adk.NewLoopAgent(ctx, &adk.LoopAgentConfig{
Name: "iterative_optimization",
SubAgents: []adk.Agent{analyzeAgent, improveAgent, validateAgent},
MaxIterations: 5,
})- 每次迭代是一次完整的 Sequential 执行
- 后续迭代的输入可访问所有历史信息(结果累积)
- 通过
BreakLoopAction 或达到MaxIterations退出 MaxIterations=0表示无限循环
内置 Agent 实现
以下 Agent 是 Eino 基于组件实现的开箱即用 Agent,无需自己定义协作逻辑。
Supervisor — 集中式协调
动态协调多个专业化 Agent 完成复杂任务。类似监管者:分发任务 → 收集结果 → 根据结果再次分发或修正。
supervisor, err := supervisor.New(ctx, &supervisor.Config{
SupervisorAgent: supervisorAgent,
SubAgents: []adk.Agent{
researchAgent,
experimentationAgent,
reportAgent,
},
})适用场景:任务动态分解、多轮调度、需要根据中间结果调整策略。
Plan-Execute — 结构化问题解决
“规划 → 执行 → 反思” 三阶段循环:
Planner(制定计划)→ Executor(执行首步)→ Replanner(评估)
├── 目标未达成 → 生成新计划 ↻
└── 目标达成 → 返回最终结果 ✓创建示例
researchAssistant := planexecute.New(ctx, &planexecute.Config{
Planner: adk.NewChatModelAgent(ctx, &adk.ChatModelAgentConfig{
Name: "research_planner",
Instruction: "制定详细的研究计划,包括文献调研、数据收集、分析方法等",
Model: gpt4Model,
}),
Executor: adk.NewChatModelAgent(ctx, &adk.ChatModelAgentConfig{
Name: "research_executor",
ToolsConfig: adk.ToolsConfig{
Tools: []tool.BaseTool{scholarSearchTool, dataAnalysisTool},
},
}),
Replanner: replannerAgent,
MaxIterations: 10,
})内部架构
外层 SequentialAgent(Planner 一次) + 内层 LoopAgent(Executor → Replanner 循环):
- Planner 生成初始
Plan(步骤列表),存入 Session - Executor 从 Plan 取首个步骤执行,结果存入 Session
- Replanner 评估进度,调用
PlanTool更新计划或RespondTool返回结果 - 循环直到任务完成或达到
MaxIterations
Plan 接口
type Plan interface {
FirstStep() string
json.Marshaler
json.Unmarshaler
}Planner 配置方式(二选一):
| 方式 | 说明 |
|---|---|
ChatModelWithFormattedOutput |
使用已配置结构化输出的模型 |
ToolCallingChatModel + ToolInfo |
通过工具调用生成 Plan 结构,默认使用 PlanToolInfo |
DeepAgent — 规划驱动的集中式协作
DeepAgent 是内置能力最全面的 Agent,预置了代码与任务管理工具集。
agent, err := deep.New(ctx, &deep.Config{
Name: "deep-agent",
ChatModel: gpt4Model,
SubAgents: []adk.Agent{LegalAgent, RiskControlAgent, FinanceAgent},
MaxIteration: 100,
})内置能力
| 能力 | 工具 | 说明 |
|---|---|---|
| 任务规划 | write_todos |
结构化 TODO 拆解与进度追踪 |
| 文件系统 | ls / read_file / write_file / edit_file / glob / grep |
本地文件操作 |
| Shell | execute(支持流式) |
命令执行 |
| 子 Agent | task |
将任务委派到上下文隔离的子 Agent |
| 上下文管理 | 大输出自动写文件 | 防 token 超限 |
架构特点
- 主 Agent 通过
task工具将子任务委派给子 Agent - 上下文隔离:子 Agent 仅接收分配的任务描述,不共享对话历史;主 Agent 仅接收最终结果,中间步骤不回传
- 内置
general-purpose子 Agent(与主 Agent 工具集相同),可在隔离上下文中执行通用任务 - 本质是多层 Supervisor 嵌套,但每层上下文不被污染
Config 核心字段
type Config struct {
Name string // Agent 标识
Description string // 用途描述
ChatModel model.BaseChatModel // 必填
Instruction string // System Prompt,空则使用内置默认
SubAgents []adk.Agent // 子 Agent
// 文件系统能力(三选一或组合)
Backend filesystem.Backend // ls / read / write / edit / glob / grep
Shell filesystem.Shell // execute(非流式)
StreamingShell filesystem.StreamingShell // execute(流式,与 Shell 互斥)
// 开关
WithoutWriteTodos bool // true → 关闭 write_todos
WithoutGeneralSubAgent bool // true → 关闭 general-purpose 子 Agent
MaxIteration int // 最大推理迭代次数
// 扩展与容错
Middlewares []adk.AgentMiddleware
Handlers []adk.ChatModelAgentMiddleware
ModelRetryConfig *adk.ModelRetryConfig
ModelFailoverConfig *adk.ModelFailoverConfig
}write_todos
type TODO struct {
Content string `json:"content"`
ActiveForm string `json:"activeForm"`
Status string `json:"status"` // pending | in_progress | completed
}- 模型调用
write_todos拆解任务 → 写入上下文 → 逐项执行 → 再次调用更新进度 - 内置 Prompt 含正反例指导何时使用(简单任务不必调用,避免适得其反)
上下文传递机制
三种跨 Agent 传递上下文的机制:
共享 Session
Runner.Run() 期间的 KV 存储,跨 Agent 共享:
adk.AddSessionValue(ctx, "key", value)
val, ok := adk.GetSessionValue(ctx, "key")
adk.AddSessionValues(ctx, map[string]any{"k1": v1})
// 运行前注入
runner.Run(ctx, messages, adk.WithSessionValues(map[string]any{"user_id": "123"}))🚨 SessionValues 基于 Context 实现,Runner 每次运行重新初始化 Context。运行前注入用
WithSessionValuesOption。
Transfer(Workflow Agent 间)
上游 Agent 输出自动拼接为下游 Agent 的输入 Messages,无需手动传递。
AgentAsTool(委派模式)
子 Agent 接收独立任务描述,不继承父对话历史(默认),或用 WithFullChatHistoryAsInput() 传入完整历史。
常见陷阱
| 陷阱 | 说明 |
|---|---|
| 🚨 DeepAgent 上下文过载 | 工具调用和中间推理过多时,开启 WithoutGeneralSubAgent 或精简子 Agent |
| 🚨 LoopAgent 无退出条件 | 须在逻辑中产出 BreakLoop Action 或设置合理 MaxIterations |
| 🚨 Parallel 中共享状态 | 并发写 Session Value 需自行加锁 |
| 🚨 AgentAsTool 子 Agent 无 Tools | 子 Agent 也是完整 Agent,需要配置自己的 Tools |