- Authors

- Name
- Youngju Kim
- @fjvbn20031
- 引言 — 为什么现在需要多智能体协作
- 多智能体系统概览
- 四种编排模式
- 框架对比
- 深入监督者模式
- 集成 MCP 协议
- 实战案例: 客户支持多智能体系统
- 故障处理策略
- 可观测性 (Observability)
- 生产部署检查清单
- 模式选择指南
- 安全考量
- 性能优化
- 结语
- 参考资料

引言 — 为什么现在需要多智能体协作
预计到 2026 年,能动型(agentic)AI 将搭载进 40% 的企业应用中(Gartner)。范式正在从单一的通用智能体,转向面向特定领域的多智能体协作。随着 NIST AI Agent Standards Initiative 的发布,安全性与互操作性的标准化也正式启动。
本文将分析 四种主要的多智能体编排模式,并提供 LangGraph、CrewAI、AutoGen 各框架的实现代码。
多智能体系统概览
单一智能体的局限
单一智能体存在以下几方面的局限。
| 局限 | 说明 |
|---|---|
| 上下文窗口饱和 | 任务越复杂,提示词越长,性能随之下降 |
| 工具过载 | 给单个智能体挂载几十个工具,会导致工具选择准确率下降 |
| 单点故障 | 只要有一个智能体失败,整个工作流就会中断 |
| 专业性不足 | 通用提示词很难在各个领域都取得最优结果 |
| 可扩展性受限 | 工作量增加时无法做水平扩展 |
多智能体解决的问题
多智能体系统通过 分工与协作 来克服上述局限。
- 专业化:每个智能体专精于特定领域
- 并行处理:同时执行相互独立的任务
- 故障隔离:单个智能体的失败不会影响整个系统
- 动态编排:根据任务灵活调整智能体组合
四种编排模式
模式一: 单一智能体 (Single Agent)
这是最基础的模式,由一个智能体处理所有任务。
from langchain.agents import create_tool_calling_agent
from langchain_openai import ChatOpenAI
from langchain.tools import tool
@tool
def search_web(query: str) -> str:
"""在网络上搜索信息。"""
# 检索逻辑
return f"Search results for: {query}"
@tool
def calculate(expression: str) -> str:
"""执行数学计算。"""
return str(eval(expression))
@tool
def write_file(filename: str, content: str) -> str:
"""将内容写入文件。"""
with open(filename, "w") as f:
f.write(content)
return f"File {filename} written successfully"
llm = ChatOpenAI(model="gpt-4o")
tools = [search_web, calculate, write_file]
agent = create_tool_calling_agent(llm, tools, prompt_template)
适用场景:任务简单,且工具数量在 5 个以下
模式二: 层级式多智能体 (Hierarchical Multi-Agent)
监督者(Supervisor)智能体 将任务分发给下级智能体,并汇总它们的结果。
from langgraph.graph import StateGraph, START, END
from langgraph.prebuilt import create_react_agent
from langchain_openai import ChatOpenAI
from typing import TypedDict, Annotated, Literal
import operator
class SupervisorState(TypedDict):
messages: Annotated[list, operator.add]
next_agent: str
final_answer: str
llm = ChatOpenAI(model="gpt-4o")
# 定义下级智能体
researcher = create_react_agent(
llm,
tools=[search_web],
state_modifier="You are a research specialist. Find accurate information."
)
analyst = create_react_agent(
llm,
tools=[calculate],
state_modifier="You are a data analyst. Analyze data and provide insights."
)
writer = create_react_agent(
llm,
tools=[write_file],
state_modifier="You are a technical writer. Create clear documentation."
)
# 监督者路由逻辑
def supervisor_router(state: SupervisorState) -> Literal["researcher", "analyst", "writer", "__end__"]:
"""由监督者决定下一个智能体。"""
last_message = state["messages"][-1]
response = llm.invoke([
{"role": "system", "content": """You are a supervisor managing a team.
Route to: researcher (for information), analyst (for data), writer (for documentation).
Return __end__ when the task is complete."""},
{"role": "user", "content": last_message.content}
])
return response.content.strip()
# 构建图
graph = StateGraph(SupervisorState)
graph.add_node("supervisor", supervisor_router)
graph.add_node("researcher", researcher)
graph.add_node("analyst", analyst)
graph.add_node("writer", writer)
graph.add_edge(START, "supervisor")
graph.add_conditional_edges("supervisor", supervisor_router)
graph.add_edge("researcher", "supervisor")
graph.add_edge("analyst", "supervisor")
graph.add_edge("writer", "supervisor")
app = graph.compile()
适用场景:需要集中式控制,且任务顺序需要动态决定的情况
模式三: 顺序流水线 (Sequential Pipeline)
各智能体按预先设定的顺序处理任务,前一个智能体的输出会成为下一个智能体的输入。
from langgraph.graph import StateGraph, START, END
from typing import TypedDict, Annotated
import operator
class PipelineState(TypedDict):
messages: Annotated[list, operator.add]
research_output: str
analysis_output: str
report_output: str
def research_node(state: PipelineState) -> PipelineState:
"""第一步:信息收集"""
result = researcher.invoke({"messages": state["messages"]})
return {"research_output": result["messages"][-1].content}
def analysis_node(state: PipelineState) -> PipelineState:
"""第二步:分析"""
analysis_prompt = f"Analyze this research: {state['research_output']}"
result = analyst.invoke({"messages": [{"role": "user", "content": analysis_prompt}]})
return {"analysis_output": result["messages"][-1].content}
def report_node(state: PipelineState) -> PipelineState:
"""第三步:撰写报告"""
report_prompt = f"""Write a report based on:
Research: {state['research_output']}
Analysis: {state['analysis_output']}"""
result = writer.invoke({"messages": [{"role": "user", "content": report_prompt}]})
return {"report_output": result["messages"][-1].content}
# 流水线图
pipeline = StateGraph(PipelineState)
pipeline.add_node("research", research_node)
pipeline.add_node("analysis", analysis_node)
pipeline.add_node("report", report_node)
pipeline.add_edge(START, "research")
pipeline.add_edge("research", "analysis")
pipeline.add_edge("analysis", "report")
pipeline.add_edge("report", END)
app = pipeline.compile()
适用场景:任务顺序明确,且每个阶段的输出会作为下一阶段输入的情况
模式四: 去中心化蜂群 (Decentralized Swarm)
各智能体自主协作,在没有中央协调者的情况下完成任务。
from langgraph.graph import StateGraph, START, END
from typing import TypedDict, Annotated, Literal
import operator
class SwarmState(TypedDict):
messages: Annotated[list, operator.add]
current_agent: str
task_board: dict # 共享任务看板
def agent_handoff(state: SwarmState, agent_name: str, target: str) -> SwarmState:
"""智能体间的交接(handoff)"""
return {
"current_agent": target,
"messages": state["messages"] + [
{"role": "system", "content": f"Handoff from {agent_name} to {target}"}
]
}
def triage_agent(state: SwarmState) -> Literal["researcher", "analyst", "writer"]:
"""分诊智能体:将任务路由给合适的智能体"""
last_message = state["messages"][-1]
if "search" in last_message.content.lower():
return "researcher"
elif "analyze" in last_message.content.lower():
return "analyst"
else:
return "writer"
def researcher_with_handoff(state: SwarmState):
"""研究员完成工作后交接给下一个智能体"""
result = researcher.invoke({"messages": state["messages"]})
# 如果需要分析则交给 analyst,否则结束
return agent_handoff(state, "researcher", "analyst")
def analyst_with_handoff(state: SwarmState):
"""分析师完成工作后交接给下一个智能体"""
result = analyst.invoke({"messages": state["messages"]})
return agent_handoff(state, "analyst", "writer")
# 蜂群图
swarm = StateGraph(SwarmState)
swarm.add_node("triage", triage_agent)
swarm.add_node("researcher", researcher_with_handoff)
swarm.add_node("analyst", analyst_with_handoff)
swarm.add_node("writer", writer)
swarm.add_edge(START, "triage")
swarm.add_conditional_edges("triage", triage_agent)
swarm.add_edge("researcher", "analyst")
swarm.add_edge("analyst", "writer")
swarm.add_edge("writer", END)
app = swarm.compile()
适用场景:需要智能体自主判断、灵活协作的情况
框架对比
LangGraph vs CrewAI vs AutoGen
| 特性 | LangGraph | CrewAI | AutoGen |
|---|---|---|---|
| 架构 | 基于图的状态机 | 基于角色的智能体团队 | 基于对话的多智能体 |
| 灵活性 | 非常高(低层级控制) | 中等(抽象化 API) | 高(可自定义) |
| 学习曲线 | 高 | 低 | 中 |
| 状态管理 | 内置(支持检查点) | 较基础 | 基于对话历史 |
| Human-in-the-Loop | 原生支持 | 基本支持 | 原生支持 |
| 流式输出 | 原生支持 | 有限 | 基于事件 |
| 生产就绪度 | 高 | 中 | 高 |
| 社区规模 | 大 | 中 | 大 |
| 许可证 | MIT | MIT | MIT |
CrewAI 实现示例
from crewai import Agent, Task, Crew, Process
# 定义智能体
researcher = Agent(
role="Senior Research Analyst",
goal="Find comprehensive and accurate information about the given topic",
backstory="""You are an expert researcher with decades of experience
in gathering and synthesizing information from multiple sources.""",
verbose=True,
allow_delegation=True,
tools=[search_tool, scrape_tool]
)
analyst = Agent(
role="Data Analyst",
goal="Analyze research findings and extract actionable insights",
backstory="""You are a skilled data analyst who excels at finding
patterns and drawing meaningful conclusions from data.""",
verbose=True,
tools=[analysis_tool, chart_tool]
)
writer = Agent(
role="Technical Writer",
goal="Create clear and comprehensive reports",
backstory="""You are an experienced technical writer who can transform
complex analyses into readable documents.""",
verbose=True,
tools=[write_tool]
)
# 定义任务
research_task = Task(
description="Research the latest trends in AI agent orchestration",
expected_output="A comprehensive summary of findings with sources",
agent=researcher
)
analysis_task = Task(
description="Analyze the research findings and identify key patterns",
expected_output="An analytical report with data-driven insights",
agent=analyst,
context=[research_task] # 引用前一个任务的结果
)
report_task = Task(
description="Write a final report combining research and analysis",
expected_output="A polished report ready for stakeholders",
agent=writer,
context=[research_task, analysis_task]
)
# 构建并执行 Crew
crew = Crew(
agents=[researcher, analyst, writer],
tasks=[research_task, analysis_task, report_task],
process=Process.sequential, # 或 Process.hierarchical
verbose=True
)
result = crew.kickoff()
print(result)
AutoGen 实现示例
from autogen import AssistantAgent, UserProxyAgent, GroupChat, GroupChatManager
# 智能体设置
config_list = [{"model": "gpt-4o", "api_key": "YOUR_API_KEY"}]
researcher = AssistantAgent(
name="Researcher",
system_message="""You are a research specialist.
Find accurate and relevant information.
When your research is complete, say RESEARCH_DONE.""",
llm_config={"config_list": config_list}
)
analyst = AssistantAgent(
name="Analyst",
system_message="""You are a data analyst.
Analyze the research findings and provide insights.
When analysis is complete, say ANALYSIS_DONE.""",
llm_config={"config_list": config_list}
)
writer = AssistantAgent(
name="Writer",
system_message="""You are a technical writer.
Create clear documentation based on research and analysis.
When the report is complete, say TERMINATE.""",
llm_config={"config_list": config_list}
)
user_proxy = UserProxyAgent(
name="Admin",
human_input_mode="NEVER",
code_execution_config={"work_dir": "output"},
is_termination_msg=lambda x: "TERMINATE" in x.get("content", "")
)
# 群聊设置
group_chat = GroupChat(
agents=[user_proxy, researcher, analyst, writer],
messages=[],
max_round=20,
speaker_selection_method="round_robin"
)
manager = GroupChatManager(
groupchat=group_chat,
llm_config={"config_list": config_list}
)
# 执行
user_proxy.initiate_chat(
manager,
message="Research AI agent orchestration patterns and write a report."
)
深入监督者模式
动态路由实现
这是一个进阶实现:由监督者分析任务,并将其路由给最合适的智能体。
from langgraph.graph import StateGraph, START, END
from langchain_openai import ChatOpenAI
from pydantic import BaseModel, Field
from typing import Literal
class RouteDecision(BaseModel):
"""监督者的路由决策"""
next_agent: Literal["researcher", "analyst", "writer", "FINISH"] = Field(
description="The next agent to route to"
)
reasoning: str = Field(
description="Why this agent was chosen"
)
task_description: str = Field(
description="Specific task for the chosen agent"
)
llm = ChatOpenAI(model="gpt-4o")
structured_llm = llm.with_structured_output(RouteDecision)
SUPERVISOR_PROMPT = """You are a supervisor managing a team of agents.
Based on the current state and conversation, decide:
1. Which agent should work next
2. What specific task they should perform
3. Whether the overall task is complete (FINISH)
Available agents:
- researcher: Searches for information and gathers data
- analyst: Analyzes data and provides insights
- writer: Creates reports and documentation
Current conversation:
{messages}
Task Board:
{task_board}
"""
def supervisor_node(state):
"""监督者节点:动态路由"""
decision = structured_llm.invoke(
SUPERVISOR_PROMPT.format(
messages=state["messages"],
task_board=state.get("task_board", "Empty")
)
)
return {
"next_agent": decision.next_agent,
"messages": state["messages"] + [
{"role": "system",
"content": f"Supervisor routed to {decision.next_agent}: {decision.task_description}"}
]
}
集成 Human-in-the-Loop
这是一种在工作流中插入需要人工审批环节的模式。
from langgraph.checkpoint.memory import MemorySaver
from langgraph.graph import StateGraph, START, END
checkpointer = MemorySaver()
def human_approval_node(state):
"""等待人工审批的节点"""
# 该节点触发 interrupt 时,执行会被中断
# 人工批准后通过 resume 继续执行
return {
"messages": state["messages"] + [
{"role": "system", "content": "Awaiting human approval..."}
],
"approval_status": "pending"
}
def check_approval(state) -> Literal["approved", "rejected"]:
"""检查审批状态"""
return state.get("approval_status", "pending")
# 向图中添加 Human-in-the-Loop
graph = StateGraph(SupervisorState)
graph.add_node("supervisor", supervisor_node)
graph.add_node("researcher", researcher)
graph.add_node("human_review", human_approval_node)
graph.add_node("writer", writer)
graph.add_edge(START, "supervisor")
graph.add_edge("supervisor", "researcher")
graph.add_edge("researcher", "human_review")
graph.add_conditional_edges(
"human_review",
check_approval,
{"approved": "writer", "rejected": "supervisor"}
)
graph.add_edge("writer", END)
# 用检查点保存和恢复状态
app = graph.compile(checkpointer=checkpointer, interrupt_before=["human_review"])
# 执行后从中断点恢复
config = {"configurable": {"thread_id": "review-thread-1"}}
result = app.invoke(initial_state, config)
# 人工批准后恢复
app.invoke(None, config) # resume with approval
集成 MCP 协议
什么是 Model Context Protocol (MCP)
MCP 是 Anthropic 发布的智能体间互操作性协议,让智能体能够以标准化的方式访问外部工具与数据源。
# MCP 服务器实现示例
from mcp import Server, Tool
import asyncio
server = Server("analytics-server")
@server.tool()
async def query_database(query: str) -> str:
"""在数据库中执行 SQL 查询。"""
# 实际的数据库连接与查询执行
result = await db.execute(query)
return str(result)
@server.tool()
async def generate_chart(data: str, chart_type: str) -> str:
"""基于数据生成图表。"""
# 图表生成逻辑
return f"Chart generated: {chart_type}"
@server.resource("schema://tables")
async def list_tables() -> str:
"""可用的数据库表列表"""
tables = await db.get_tables()
return "\n".join(tables)
# 运行服务器
async def main():
async with server.run_stdio() as running:
await running.wait()
asyncio.run(main())
MCP 客户端与多智能体的联动
from mcp import ClientSession, StdioServerParameters
from langchain_mcp_adapters.tools import load_mcp_tools
from langgraph.prebuilt import create_react_agent
# MCP 服务器连接设置
server_params = StdioServerParameters(
command="python",
args=["analytics_server.py"]
)
async def create_mcp_agent():
"""创建使用 MCP 工具的智能体"""
async with ClientSession(*server_params) as session:
await session.initialize()
# 将 MCP 工具转换为 LangChain 工具
tools = await load_mcp_tools(session)
# 创建智能体
agent = create_react_agent(
ChatOpenAI(model="gpt-4o"),
tools,
state_modifier="You are a data analyst with access to database tools."
)
return agent
实战案例: 客户支持多智能体系统
架构设计
这是一个把客户支持系统实现为层级式多智能体系统的实战示例。
from langgraph.graph import StateGraph, START, END
from langchain_openai import ChatOpenAI
from typing import TypedDict, Annotated, Literal
import operator
class CustomerSupportState(TypedDict):
messages: Annotated[list, operator.add]
customer_id: str
issue_category: str
sentiment: str
resolution: str
escalated: bool
# 分诊智能体
def triage_agent(state: CustomerSupportState) -> CustomerSupportState:
"""对客户咨询分类,并路由给合适的专业智能体"""
llm = ChatOpenAI(model="gpt-4o")
response = llm.invoke([
{"role": "system", "content": """Classify the customer issue into one of:
- billing: Payment, invoice, subscription issues
- technical: Product bugs, errors, configuration
- general: General inquiries, feedback
Also assess sentiment: positive, neutral, negative, urgent"""},
{"role": "user", "content": state["messages"][-1].content}
])
# 解析分类结果
return {
"issue_category": "technical", # 解析结果
"sentiment": "negative"
}
# 技术支持智能体
def technical_support_agent(state: CustomerSupportState) -> CustomerSupportState:
"""诊断技术问题并给出解决方案"""
llm = ChatOpenAI(model="gpt-4o")
response = llm.invoke([
{"role": "system", "content": """You are a technical support specialist.
Diagnose the issue and provide step-by-step solutions.
If the issue requires engineering escalation, set escalated=true."""},
{"role": "user", "content": str(state["messages"])}
])
return {
"resolution": response.content,
"messages": [{"role": "assistant", "content": response.content}]
}
# 账单支持智能体
def billing_support_agent(state: CustomerSupportState) -> CustomerSupportState:
"""处理与付款相关的问题"""
llm = ChatOpenAI(model="gpt-4o")
response = llm.invoke([
{"role": "system", "content": """You are a billing specialist.
Handle payment issues, refunds, and subscription changes."""},
{"role": "user", "content": str(state["messages"])}
])
return {
"resolution": response.content,
"messages": [{"role": "assistant", "content": response.content}]
}
# 升级(escalation)智能体
def escalation_agent(state: CustomerSupportState) -> CustomerSupportState:
"""将复杂问题升级到上一级"""
return {
"escalated": True,
"messages": [
{"role": "system",
"content": f"Issue escalated for customer {state['customer_id']}"}
]
}
# 路由函数
def route_issue(state: CustomerSupportState) -> Literal["technical", "billing", "general"]:
return state["issue_category"]
def check_escalation(state: CustomerSupportState) -> Literal["escalate", "resolve"]:
if state.get("escalated"):
return "escalate"
return "resolve"
# 构建图
workflow = StateGraph(CustomerSupportState)
workflow.add_node("triage", triage_agent)
workflow.add_node("technical", technical_support_agent)
workflow.add_node("billing", billing_support_agent)
workflow.add_node("escalation", escalation_agent)
workflow.add_edge(START, "triage")
workflow.add_conditional_edges("triage", route_issue, {
"technical": "technical",
"billing": "billing",
"general": "billing" # 一般咨询也由 billing 处理
})
workflow.add_conditional_edges("technical", check_escalation, {
"escalate": "escalation",
"resolve": END
})
workflow.add_edge("billing", END)
workflow.add_edge("escalation", END)
app = workflow.compile()
故障处理策略
重试与降级 (fallback) 模式
from tenacity import retry, stop_after_attempt, wait_exponential
from langgraph.graph import StateGraph
import logging
logger = logging.getLogger(__name__)
class AgentWithRetry:
"""包含重试逻辑的智能体封装"""
def __init__(self, agent, max_retries=3, fallback_agent=None):
self.agent = agent
self.max_retries = max_retries
self.fallback_agent = fallback_agent
@retry(
stop=stop_after_attempt(3),
wait=wait_exponential(multiplier=1, min=2, max=30)
)
async def invoke_with_retry(self, state):
"""通过重试逻辑调用智能体"""
try:
return await self.agent.ainvoke(state)
except Exception as e:
logger.error(f"Agent failed: {e}")
raise
async def invoke(self, state):
"""包含降级(fallback)的智能体调用"""
try:
return await self.invoke_with_retry(state)
except Exception as e:
if self.fallback_agent:
logger.warning(f"Falling back to backup agent: {e}")
return await self.fallback_agent.ainvoke(state)
raise
# 断路器(circuit breaker)模式
class CircuitBreaker:
"""断路器模式"""
def __init__(self, failure_threshold=5, recovery_timeout=60):
self.failure_count = 0
self.failure_threshold = failure_threshold
self.recovery_timeout = recovery_timeout
self.state = "closed" # closed(关闭)、open(打开)、half-open(半开)
self.last_failure_time = None
def can_execute(self) -> bool:
if self.state == "closed":
return True
if self.state == "open":
import time
if time.time() - self.last_failure_time > self.recovery_timeout:
self.state = "half-open"
return True
return False
return True # half-open(半开状态)
def record_success(self):
self.failure_count = 0
self.state = "closed"
def record_failure(self):
import time
self.failure_count += 1
self.last_failure_time = time.time()
if self.failure_count >= self.failure_threshold:
self.state = "open"
死信队列模式
import json
from datetime import datetime
class DeadLetterQueue:
"""保存处理失败消息的死信队列"""
def __init__(self, storage_path="dead_letters.json"):
self.storage_path = storage_path
self.messages = []
def add(self, message: dict, error: str, agent_name: str):
"""将失败的消息加入队列"""
entry = {
"timestamp": datetime.now().isoformat(),
"agent": agent_name,
"message": message,
"error": str(error),
"retry_count": 0
}
self.messages.append(entry)
self._persist()
def retry_all(self, agent_registry: dict):
"""重试队列中的所有消息"""
for entry in self.messages:
agent = agent_registry.get(entry["agent"])
if agent:
try:
agent.invoke(entry["message"])
self.messages.remove(entry)
except Exception as e:
entry["retry_count"] += 1
entry["last_error"] = str(e)
self._persist()
def _persist(self):
with open(self.storage_path, "w") as f:
json.dump(self.messages, f, indent=2)
可观测性 (Observability)
集成 LangSmith
import os
# 启用 LangSmith 追踪
os.environ["LANGCHAIN_TRACING_V2"] = "true"
os.environ["LANGCHAIN_API_KEY"] = "your-langsmith-api-key"
os.environ["LANGCHAIN_PROJECT"] = "multi-agent-orchestration"
# 收集自定义指标
from langsmith import Client
client = Client()
def track_agent_metrics(agent_name: str, duration: float, tokens: int, success: bool):
"""追踪智能体执行指标"""
client.create_run(
name=f"agent-{agent_name}",
run_type="chain",
inputs={"agent": agent_name},
outputs={
"duration_ms": duration * 1000,
"total_tokens": tokens,
"success": success
}
)
集成 OpenTelemetry
from opentelemetry import trace
from opentelemetry.sdk.trace import TracerProvider
from opentelemetry.sdk.trace.export import BatchSpanProcessor
from opentelemetry.exporter.otlp.proto.grpc.trace_exporter import OTLPSpanExporter
# 追踪器设置
provider = TracerProvider()
processor = BatchSpanProcessor(OTLPSpanExporter(endpoint="http://localhost:4317"))
provider.add_span_processor(processor)
trace.set_tracer_provider(provider)
tracer = trace.get_tracer("multi-agent-system")
def traced_agent_node(agent_name: str):
"""包含 OpenTelemetry 追踪的智能体节点"""
def node_fn(state):
with tracer.start_as_current_span(f"agent.{agent_name}") as span:
span.set_attribute("agent.name", agent_name)
span.set_attribute("agent.input_messages", len(state["messages"]))
try:
result = agent.invoke(state)
span.set_attribute("agent.success", True)
return result
except Exception as e:
span.set_attribute("agent.success", False)
span.record_exception(e)
raise
return node_fn
生产部署检查清单
设计阶段
- 是否为每个智能体明确定义了角色与工具
- 智能体间的通信协议是否已标准化
- 是否已建立状态管理策略(本地 vs 分布式)
- 是否针对各类故障场景制定了应对策略
- 是否已识别出需要 Human-in-the-Loop 的环节
实现阶段
- 是否为每个智能体分配了合适的模型(成本 vs 性能)
- 工具执行是否设置了超时
- 是否实现了重试逻辑与断路器
- 是否用死信队列追踪失败的任务
- 是否应用了输入输出校验(guard rails)
部署阶段
- 是否已构建可观测性流水线(LangSmith / OTEL)
- 是否能够按智能体追踪成本
- 是否应用了速率限制
- 是否已启用安全审计日志
- 是否已制定回滚策略
运维阶段
- 是否已建立智能体性能仪表盘
- 是否已设置异常检测告警
- 是否应用了提示词版本管理
- 是否已准备好 A/B 测试框架
- 是否有定期的提示词优化流程
模式选择指南
决策流程图
判断任务类型
|
├─ 简单任务(工具 5 个以下)─────> 单一智能体
|
├─ 顺序确定的多步骤任务 ─────> 流水线
|
├─ 需要动态路由的任务 ─────> 层级式(监督者)
|
└─ 需要自主协作的复杂任务 ─> 蜂群
各模式优缺点汇总
| 模式 | 优点 | 缺点 | 复杂度 | 适用规模 |
|---|---|---|---|---|
| 单一智能体 | 实现简单,易于调试 | 扩展性有限,容易上下文饱和 | 低 | 小规模 |
| 层级式 | 集中控制,支持动态路由 | 监督者瓶颈,存在单点故障 | 中 | 中规模 |
| 流水线 | 结果可预测,便于测试 | 灵活性不足,顺序执行有延迟 | 低-中 | 中规模 |
| 蜂群 | 灵活性高,自主协作 | 调试困难,行为难以预测 | 高 | 大规模 |
安全考量
智能体隔离
class SandboxedAgent:
"""在隔离环境中运行的智能体"""
def __init__(self, agent, allowed_tools: list, max_tokens: int = 4096):
self.agent = agent
self.allowed_tools = set(allowed_tools)
self.max_tokens = max_tokens
def invoke(self, state):
# 校验工具访问权限
requested_tools = self._extract_tool_calls(state)
unauthorized = requested_tools - self.allowed_tools
if unauthorized:
raise PermissionError(
f"Agent attempted to use unauthorized tools: {unauthorized}"
)
# 限制 token 使用量
if self._estimate_tokens(state) > self.max_tokens:
raise ResourceError("Token limit exceeded")
return self.agent.invoke(state)
def _extract_tool_calls(self, state) -> set:
# 从状态中提取工具调用
return set()
def _estimate_tokens(self, state) -> int:
# 估算 token 使用量
return 0
提示词注入防御
from langchain.output_parsers import PydanticOutputParser
from pydantic import BaseModel, validator
class SafeAgentOutput(BaseModel):
"""智能体输出校验模式"""
response: str
confidence: float
sources: list[str]
@validator("response")
def validate_response(cls, v):
# 检测被禁止的模式
forbidden_patterns = [
"ignore previous instructions",
"system prompt",
"bypass",
"jailbreak"
]
for pattern in forbidden_patterns:
if pattern.lower() in v.lower():
raise ValueError(f"Suspicious pattern detected: {pattern}")
return v
parser = PydanticOutputParser(pydantic_object=SafeAgentOutput)
性能优化
并行执行策略
from langgraph.graph import StateGraph, START, END
import asyncio
class ParallelState(TypedDict):
messages: Annotated[list, operator.add]
research_result: str
analysis_result: str
async def parallel_execution(state):
"""并行执行相互独立的智能体"""
research_task = asyncio.create_task(
researcher.ainvoke({"messages": state["messages"]})
)
analysis_task = asyncio.create_task(
analyst.ainvoke({"messages": state["messages"]})
)
research_result, analysis_result = await asyncio.gather(
research_task, analysis_task
)
return {
"research_result": research_result["messages"][-1].content,
"analysis_result": analysis_result["messages"][-1].content
}
# LangGraph 的 fan-out 模式
graph = StateGraph(ParallelState)
graph.add_node("research", researcher)
graph.add_node("analysis", analyst)
graph.add_node("synthesis", writer)
# 并行执行:从 START 同时分支到两个节点
graph.add_edge(START, "research")
graph.add_edge(START, "analysis")
# 两个结果都完成后进入 synthesis
graph.add_edge("research", "synthesis")
graph.add_edge("analysis", "synthesis")
graph.add_edge("synthesis", END)
缓存策略
from functools import lru_cache
import hashlib
import json
class AgentCache:
"""智能体响应缓存"""
def __init__(self, ttl_seconds=3600):
self.cache = {}
self.ttl = ttl_seconds
def get_cache_key(self, state: dict) -> str:
"""根据状态生成缓存键"""
state_str = json.dumps(state, sort_keys=True, default=str)
return hashlib.sha256(state_str.encode()).hexdigest()
def get(self, state: dict):
"""从缓存中查询结果"""
key = self.get_cache_key(state)
if key in self.cache:
entry = self.cache[key]
import time
if time.time() - entry["timestamp"] < self.ttl:
return entry["result"]
del self.cache[key]
return None
def set(self, state: dict, result):
"""将结果保存到缓存"""
import time
key = self.get_cache_key(state)
self.cache[key] = {
"result": result,
"timestamp": time.time()
}
结语
多智能体编排不仅仅是把多个智能体连接起来,核心在于 根据任务特性选择合适的模式,并具备 健壮的故障处理与可观测性。
要点总结:
- 从 单一智能体 起步,等复杂度上升后再转向多智能体
- 层级式模式 适合需要集中控制的场景
- 流水线模式 最适合顺序固定的工作流
- 蜂群模式 适合需要高自主性的复杂场景
- 框架选择上,可按用途在 LangGraph(灵活性)、CrewAI(快速原型开发)、AutoGen(基于对话)之间挑选