feat: expose graph orchestration mode, fix pipeline multi-agent, add Feishu tools (Phase 3)

增强编排 + 飞书深度集成:
- Graph 模式:暴露 orchestrator._graph() 到 run() 方法,workflow_integration 支持 graph nodes/edges
- Pipeline 修复:多 Agent 按步骤轮转分配,不再只用 agents[0]
- 4个飞书操作工具: feishu_create_doc / feishu_create_calendar_event / feishu_search_contacts / feishu_send_approval
- 飞书 @mention→Goal:feishu/ orange WS handler 支持 "目标: xxx" 触发自动创建 Goal

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
renjianbo
2026-05-08 20:08:26 +08:00
parent 926ec6c0a1
commit d0b55f2b16
6 changed files with 490 additions and 27 deletions

View File

@@ -151,8 +151,19 @@ class AgentOrchestrator:
question: str,
agents: List[OrchestratorAgentConfig],
on_llm_call: Optional[Callable[[Dict[str, Any]], Any]] = None,
graph_nodes: Optional[List[Dict[str, Any]]] = None,
graph_edges: Optional[List[Dict[str, Any]]] = None,
) -> OrchestratorResult:
"""执行多 Agent 编排。"""
"""执行多 Agent 编排。
Args:
mode: route / sequential / debate / pipeline / graph
question: 用户问题
agents: Agent 配置列表
on_llm_call: LLM 调用回调
graph_nodes: graph 模式的节点定义mode=graph 时必填)
graph_edges: graph 模式的边定义mode=graph 时必填)
"""
mode = mode.lower()
if mode == "route":
return await self._route(question, agents, on_llm_call)
@@ -162,8 +173,12 @@ class AgentOrchestrator:
return await self._debate(question, agents, on_llm_call)
elif mode == "pipeline":
return await self._pipeline(question, agents, on_llm_call)
elif mode == "graph":
if not graph_nodes:
raise ValueError("graph 模式需要提供 graph_nodes 参数")
return await self._graph(question, graph_nodes, graph_edges or [], on_llm_call)
else:
raise ValueError(f"不支持的编排模式: {mode},可选: route, sequential, debate, pipeline")
raise ValueError(f"不支持的编排模式: {mode},可选: route, sequential, debate, pipeline, graph")
async def _route(
self, question: str, agents: List[OrchestratorAgentConfig],
@@ -500,11 +515,13 @@ class AgentOrchestrator:
steps=steps,
)
# ── 2. Executor逐步骤执行 ──
executor_cfg = agents[0] if agents else OrchestratorAgentConfig(
id="executor", name="Executor",
system_prompt="你是一个有用的AI助手。",
)
# ── 2. Executor逐步骤执行(多 Agent 轮转分配)──
executor_pool = agents if agents else [
OrchestratorAgentConfig(
id="executor", name="Executor",
system_prompt="你是一个有用的AI助手。",
)
]
previous_output = "(尚无前序步骤)"
execution_results = []
@@ -514,6 +531,9 @@ class AgentOrchestrator:
step_desc = step_info.get("description", f"步骤 {step_num}")
step_expect = step_info.get("expected_output", "")
# 按步骤轮转分配 Agent不同步骤可分配给不同 Agent按专长匹配
executor_cfg = executor_pool[(step_num - 1) % len(executor_pool)]
executor_prompt = _EXECUTOR_STEP_PROMPT.format(
original_question=question,
plan_title=plan.get("plan_title", ""),
@@ -555,6 +575,7 @@ class AgentOrchestrator:
execution_results.append({
"step": step_num,
"description": step_desc,
"agent": executor_cfg.name,
"output": step_result.content,
"error": step_result.error if not step_result.success else None,
})
@@ -562,7 +583,7 @@ class AgentOrchestrator:
previous_output = step_result.content if step_result.success else f"(步骤{step_num}执行出错)"
if not step_result.success:
logger.warning(f"Pipeline 步骤{step_num} 执行失败: {step_result.error}")
logger.warning(f"Pipeline 步骤{step_num} ({executor_cfg.name}) 执行失败: {step_result.error}")
# ── 3. Reviewer审查并交付 ──
plan_steps_text = "\n".join(