news 2026/8/6 19:45:13

多智能体(Multi-Agent)编排实战:用 LangGraph 构建生产级 AI 系统

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
多智能体(Multi-Agent)编排实战:用 LangGraph 构建生产级 AI 系统

1. 引言:为什么需要多智能体编排

随着大语言模型(LLM)能力的持续提升,单一智能体在复杂业务场景中逐渐暴露出局限性:上下文窗口有限、工具调用链路过长、职责边界模糊、错误难以隔离。多智能体(Multi-Agent)架构通过将复杂任务拆解为多个专业智能体,各自负责特定子任务,再通过编排层协调协作,从而提升系统的可维护性、可扩展性和鲁棒性。

LangGraph 是 LangChain 团队推出的低层级编排框架,专为构建有状态、可循环、可细粒度控制的智能体工作流而设计。与 LangChain 的 Chain 相比,LangGraph 更贴近图计算模型,支持条件分支、循环、人工介入、持久化等生产级特性,是多智能体编排的理想底座。

本文将从零开始,围绕一个「智能客服工单处理系统」的实战案例,逐步讲解如何用 LangGraph 构建生产级多智能体系统,涵盖状态管理、图编排、智能体间通信、人工审批、持久化与可观测性等核心主题。

2. LangGraph 核心概念

在动手编码之前,先厘清 LangGraph 的五个核心抽象,它们是理解后续所有代码的基础。

  • State(状态):贯穿整个图执行过程的共享数据结构,可以是 TypedDict、Pydantic 模型或自定义类。每个节点读写 State 的指定字段,实现数据流转。
  • Node(节点):图中的一个执行单元,通常是一个 Python 函数,接收 State 并返回 State 的部分更新。
  • Edge(边):连接节点的有向边,定义执行顺序。普通边表示无条件流转,条件边根据 State 内容动态选择下一个节点。
  • Graph(图):由节点和边组成的执行拓扑,LangGraph 支持 StateGraph 和 MessageGraph 两种构建方式。
  • Checkpointer(检查点):持久化 State 快照的组件,支持断点续跑、时间旅行和人工介入。

下图展示了本文实战案例的整体编排拓扑:

flowchart TD A[入口: 工单接收] --> B{意图分类} B -->|技术问题| C[技术专家 Agent] B -->|账单问题| D[账单 Agent] B -->|通用咨询| E[通用客服 Agent] C --> F{是否需要升级} D --> F E --> G[直接回复] F -->|是| H[人工审批节点] F -->|否| I[生成最终回复] H --> I I --> J[结束] G --> J

3. 环境准备与项目结构

首先创建虚拟环境并安装依赖。建议使用 Python 3.10 及以上版本。

python -m venv .venv source .venv/bin/activate # Windows 下使用 .venv\Scripts\activate pip install langgraph langchain langchain-openai langchain-community pip install redis # 用于持久化 Checkpointer pip install langsmith # 用于可观测性追踪

项目目录结构如下:

multi_agent_system/ ├── main.py # 入口脚本 ├── state.py # State 定义 ├── agents/ │ ├── __init__.py │ ├── triage.py # 意图分类 Agent │ ├── technical.py # 技术专家 Agent │ ├── billing.py # 账单 Agent │ └── general.py # 通用客服 Agent ├── graph/ │ ├── __init__.py │ ├── builder.py # 图构建逻辑 │ └── edges.py # 条件边路由函数 ├── tools/ │ ├── __init__.py │ └── knowledge_base.py # 知识库检索工具 └── config.py # 全局配置

4. 定义全局状态(State)

State 是多智能体协作的「共享黑板」。我们使用 TypedDict 定义字段,并通过 Annotated 指定消息列表的合并策略。

# state.py from typing import Annotated, TypedDict, List, Optional from langgraph.graph.message import add_messages from langchain_core.messages import BaseMessage class AgentState(TypedDict): """全局共享状态""" # 原始工单内容 ticket_id: str customer_name: str ticket_text: str # 消息历史,使用 add_messages 自动合并 messages: Annotated[List[BaseMessage], add_messages] 意图分类结果 intent: Optional[str] 当前处理 Agent 的名称 current_agent: Optional[str] 是否需要人工审批 needs_human_approval: bool 最终回复 final_response: Optional[str]

关键点说明:

  • messages字段使用add_messages归约器,LangGraph 会自动将各节点返回的新消息追加到历史列表,避免手动拼接。
  • intentcurrent_agent等字段用于条件边路由决策。
  • needs_human_approval是人工介入的开关,当技术 Agent 判定问题复杂时置为 True。

5. 构建基础工具:知识库检索

为了让 Agent 具备领域知识,我们实现一个简单的知识库检索工具。生产环境可替换为向量数据库(如 Pinecone、Milvus)或 Elasticsearch。

# tools/knowledge_base.py from typing import List, Dict 模拟知识库数据,生产环境替换为向量检索 KNOWLEDGE_BASE = [ { "id": "KB001", "category": "technical", "keywords": ["登录", "密码", "认证失败"], "content": "如果用户遇到登录失败,请先引导其检查网络连接,然后尝试重置密码。若仍无法登录,可能是账号被锁定,需联系安全团队解锁。" }, { "id": "KB002", "category": "billing", "keywords": ["退款", "账单", "扣费"], "content": "退款申请需在账单生成后 30 天内提交。确认订单状态为已支付后,财务团队将在 3-5 个工作日内处理退款。" }, { "id": "KB003", "category": "general", "keywords": ["使用", "教程", "入门"], "content": "新用户可参考官方快速入门文档,包含账号注册、项目创建和第一个 API 调用的完整指引。" } ] def search_knowledge_base(query: str, category: str = None, top_k: int = 2) -> List[Dict]: """基于关键词匹配的知识库检索""" results = [] for item in KNOWLEDGE_BASE: if category and item["category"] != category: continue # 简单关键词命中评分 score = sum(1 for kw in item["keywords"] if kw in query) if score > 0: results.append({"score": score, **item}) results.sort(key=lambda x: x["score"], reverse=True) return results[:top_k]

在实际生产系统中,建议使用 Embedding 模型将查询和知识条目向量化,通过余弦相似度检索,召回效果远优于关键词匹配。

6. 实现意图分类 Agent

意图分类 Agent 是整个工作流的入口,负责判断工单属于技术问题、账单问题还是通用咨询。这里使用结构化输出(Structured Output)确保返回结果可被程序解析。

# agents/triage.py from langchain_openai import ChatOpenAI from langchain_core.messages import SystemMessage, HumanMessage from langchain_core.pydantic_v1 import BaseModel, Field from state import AgentState class IntentOutput(BaseModel): """意图分类结构化输出""" intent: str = Field(description="工单意图类别: technical / billing / general") confidence: float = Field(description="置信度 0-1") reasoning: str = Field(description="分类依据简述") def triage_agent(state: AgentState) -> AgentState: """意图分类节点""" llm = ChatOpenAI(model="gpt-4o", temperature=0) structured_llm = llm.with_structured_output(IntentOutput) system_prompt = """ 你是工单意图分类专家。请根据用户工单内容,判断其属于以下哪一类: - technical: 技术故障、报错、功能异常 - billing: 账单、扣费、退款、发票 - general: 产品咨询、使用教程、其他 只输出 JSON 格式结果。 """ result = structured_llm.invoke([ SystemMessage(content=system_prompt), HumanMessage(content=f"工单内容: {state['ticket_text']}") ]) return { "intent": result.intent, "messages": [HumanMessage(content=f"[意图分类] 判定为 {result.intent},置信度 {result.confidence:.2f}")] }

这里使用with_structured_output让模型直接输出 Pydantic 对象,避免手写 JSON 解析的脆弱性。生产环境建议增加置信度阈值判断,低于阈值时直接转人工。

7. 实现专业 Agent(技术 / 账单 / 通用)

三个专业 Agent 结构相似,均接收工单内容,结合知识库检索结果生成回复。以技术专家 Agent 为例:

# agents/technical.py from langchain_openai import ChatOpenAI from langchain_core.messages import SystemMessage, HumanMessage from state import AgentState from tools.knowledge_base import search_knowledge_base def technical_agent(state: AgentState) -> AgentState: """技术专家 Agent""" llm = ChatOpenAI(model="gpt-4o", temperature=0.3) # 检索相关知识 kb_results = search_knowledge_base(state["ticket_text"], category="technical") kb_context = "\n\n".join( f"[知识条目 {r['id']}] {r['content']}" for r in kb_results ) if kb_results else "知识库中未找到直接匹配条目。" system_prompt = f""" 你是资深技术支持工程师。请基于以下知识库内容,结合你的技术经验,为用户工单提供解决方案。 知识库参考: {kb_context} 要求: 先复述用户问题,确认理解正确 给出分步骤的解决方案 如果问题超出知识库范围且涉及账号安全、数据丢失等高风险场景,将 needs_human_approval 置为 True """ response = llm.invoke([ SystemMessage(content=system_prompt), HumanMessage(content=f"用户工单: {state['ticket_text']}") ]) 简单判断是否需要人工介入(生产环境可用 LLM 判断或规则引擎) needs_human = any(kw in state["ticket_text"] for kw in ["数据丢失", "账号被盗", "无法恢复"]) return { "current_agent": "technical", "needs_human_approval": needs_human, "messages": [HumanMessage(content=f"[技术专家] {response.content}")] }

账单 Agent 和通用客服 Agent 的实现模式完全一致,仅替换系统提示词和知识库分类参数。为节省篇幅,这里不再重复贴出,完整代码可在文末获取。

8. 实现人工审批节点

人工审批是多智能体系统生产化的关键能力。LangGraph 的interrupt机制允许图在特定节点暂停执行,等待人工输入后恢复。

# agents/human_approval.py from langgraph.types import interrupt, Command from state import AgentState def human_approval_node(state: AgentState) -> AgentState: """人工审批节点:暂停图执行,等待人工决策""" # 组装需要人工审核的信息 approval_request = { "ticket_id": state["ticket_id"], "customer": state["customer_name"], "ticket_text": state["ticket_text"], "agent_response": state["messages"][-1].content if state["messages"] else "", "question": "该工单涉及高风险操作,请审核是否批准以下回复?" } # 暂停执行,将审批请求发送给前端 user_decision = interrupt(approval_request) 根据人工决策更新状态 if user_decision.get("approved"): return { "needs_human_approval": False, "messages": [HumanMessage(content="[人工审批] 已批准该回复")] } else: # 人工驳回,可附带修改意见 feedback = user_decision.get("feedback", "请重新生成回复") return { "needs_human_approval": True, "messages": [HumanMessage(content=f"[人工审批] 已驳回,意见: {feedback}")] }

当图执行到interrupt时,LangGraph 会保存检查点并暂停。外部系统通过graph.invoke(Command(resume=...))恢复执行,传入人工决策结果。

9. 组装多智能体图

现在将上述节点组装成完整的 StateGraph。这是整个系统的核心编排逻辑。

# graph/builder.py from langgraph.graph import StateGraph, START, END from state import AgentState from agents.triage import triage_agent from agents.technical import technical_agent from agents.billing import billing_agent from agents.general import general_agent from agents.human_approval import human_approval_node def route_by_intent(state: AgentState) -> str: """根据意图分类结果路由到对应 Agent""" intent = state.get("intent") if intent == "technical": return "technical" elif intent == "billing": return "billing" else: return "general" def route_after_agent(state: AgentState) -> str: """判断是否需要人工审批""" if state.get("needs_human_approval"): return "human_approval" return "finalize" def build_graph(): """构建多智能体图""" graph = StateGraph(AgentState) # 添加节点 graph.add_node("triage", triage_agent) graph.add_node("technical", technical_agent) graph.add_node("billing", billing_agent) graph.add_node("general", general_agent) graph.add_node("human_approval", human_approval_node) graph.add_node("finalize", finalize_node) 添加边 graph.add_edge(START, "triage") graph.add_conditional_edges("triage", route_by_intent, { "technical": "technical", "billing": "billing", "general": "general" }) graph.add_conditional_edges("technical", route_after_agent, { "human_approval": "human_approval", "finalize": "finalize" }) graph.add_conditional_edges("billing", route_after_agent, { "human_approval": "human_approval", "finalize": "finalize" }) graph.add_conditional_edges("general", route_after_agent, { "human_approval": "human_approval", "finalize": "finalize" }) graph.add_edge("human_approval", "finalize") graph.add_edge("finalize", END) return graph.compile()

其中finalize_node负责从消息历史中提取最终回复并写入final_response字段:

# graph/builder.py 中补充 def finalize_node(state: AgentState) -> AgentState: """汇总最终回复""" # 取最后一个 Agent 的回复作为最终结果 for msg in reversed(state["messages"]): if msg.content.startswith("[技术专家]") or \ msg.content.startswith("[账单专家]") or \ msg.content.startswith("[通用客服]"): return {"final_response": msg.content} return {"final_response": "抱歉,暂时无法处理该工单,已转交人工客服。"}

10. 持久化与断点续跑

生产级系统必须支持持久化,以便在进程重启后恢复执行状态。LangGraph 提供 Checkpointer 抽象,这里以 Redis 为例:

# main.py 片段 from langgraph.checkpoint.redis import RedisSaver import redis 初始化 Redis 连接 redis_client = redis.Redis(host="localhost", port=6379, db=0) checkpointer = RedisSaver(redis_client) 编译图时传入 checkpointer app = build_graph() app = app.compile(checkpointer=checkpointer)

执行图并指定线程 ID,实现会话级状态隔离:

# main.py 片段 config = {"configurable": {"thread_id": "ticket-1001"}} initial_state = { "ticket_id": "ticket-1001", "customer_name": "张三", "ticket_text": "我无法登录账号,提示密码错误,但重置密码后仍然无法登录,怀疑账号被锁定。" } 首次执行 result = app.invoke(initial_state, config=config) print("意图:", result["intent"]) print("最终回复:", result["final_response"])

当图在人工审批节点暂停后,可通过Command(resume=...)恢复:

# 恢复执行,传入人工决策 from langgraph.types import Command resume_result = app.invoke( Command(resume={"approved": True}), config=config ) print("审批后最终回复:", resume_result["final_response"])

11. 可观测性与追踪

生产环境必须能观测每个 Agent 的输入输出、耗时和 Token 消耗。LangGraph 原生集成 LangSmith,只需配置环境变量即可自动追踪:

export LANGCHAIN_TRACING_V2=true export LANGCHAIN_API_KEY=your_langsmith_api_key export LANGCHAIN_PROJECT=multi_agent_system

此外,可以在节点函数中手动记录关键指标:

# 在节点中记录耗时 import time from langchain_core.callbacks import CallbackManager def technical_agent_with_metrics(state: AgentState) -> AgentState: start = time.time() result = technical_agent(state) elapsed = time.time() - start print(f"[Metrics] technical_agent 耗时: {elapsed:.2f}s") return result

12. 生产化最佳实践

将多智能体系统部署到生产环境,需要关注以下关键点:

  • 超时与重试:为每个节点设置超时时间,LLM 调用失败时自动重试,避免单点故障拖垮整个工作流。
  • 限流与配额:对 LLM API 调用做限流,防止并发过高导致成本失控。
  • 状态版本控制:State 结构变更时做好迁移策略,避免旧检查点无法恢复。
  • 安全与权限:Agent 调用外部工具时,必须做权限校验和敏感信息脱敏。
  • 灰度发布:新 Agent 或新提示词上线前,先在小流量灰度验证效果。
  • 成本控制:为每个 Agent 设置 Token 预算上限,超限自动降级到简单回复。

13. 总结与扩展方向

本文通过一个完整的智能客服工单处理系统,系统讲解了如何用 LangGraph 构建生产级多智能体系统。核心要点总结如下:

  • 使用StateGraph定义节点和边的执行拓扑,通过条件边实现动态路由。
  • 利用Annotated归约器管理消息历史的自动合并。
  • 通过interrupt机制实现人工审批,结合 Checkpointer 支持断点续跑。
  • 使用 Redis 等外部存储实现状态持久化,保证系统可恢复性。
  • 集成 LangSmith 实现全链路可观测性。

后续可扩展的方向包括:引入 ReAct 循环让 Agent 自主调用工具、使用 Supervisor 模式实现层级化编排、结合向量数据库构建更强大的知识检索、以及通过 LangGraph Cloud 实现一键部署和自动扩缩容。

多智能体编排是通往复杂 AI 应用的关键技术栈,LangGraph 提供了灵活且生产友好的基础设施。建议读者在本文示例基础上,结合自身业务场景逐步迭代,构建真正可落地的智能体系统。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/8/6 19:40:55

3分钟免安装微信解决方案:wechat-need-web浏览器插件详解

3分钟免安装微信解决方案:wechat-need-web浏览器插件详解 【免费下载链接】wechat-need-web 让微信网页版可用 / Allow the use of WeChat via webpage access 项目地址: https://gitcode.com/gh_mirrors/we/wechat-need-web 你是否曾在公司电脑上急需使用微…

作者头像 李华
网站建设 2026/8/6 19:40:49

实战拆解:年 GMV60 亿级私域团购系统 分销关系存储、分账对账与合规校验技术落地

私域社群团购行业从野蛮生长进入合规化深耕阶段,大量平台在业务规模扩张后集中暴露技术短板:分销层级加深后团队数据查询卡顿、高并发下单时段分润结算错漏频发、合规规则仅靠后台配置可被人为突破,最终成为业务增长的技术瓶颈。良久团购能稳…

作者头像 李华
网站建设 2026/8/6 19:40:27

ModernBERT-base量化指南:ONNX模型优化与Flash Attention加速实战

ModernBERT-base量化指南:ONNX模型优化与Flash Attention加速实战 【免费下载链接】ModernBERT-base 项目地址: https://ai.gitcode.com/hf_mirrors/answerdotai/ModernBERT-base ModernBERT-base是一款现代化的双向编码器Transformer模型,具备8…

作者头像 李华
网站建设 2026/8/6 19:40:05

【计算机毕业设计单片机案例】基于 STM32 单片机的声光报警式智能盆栽养护系统设计 基于 STM32/51 单片机的小型温室通风灌溉一体化控制系统(011702)

博主介绍:✌️码农一枚 ,专注于大学生项目实战开发、讲解和毕业🚢文撰写修改等。全栈领域优质创作者,博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于嵌入式单片机,Java、小程序技术领域和毕业项目实战 ✌️…

作者头像 李华
网站建设 2026/8/6 19:39:01

免费解锁B站大会员4K画质:手把手教你用Python下载高清视频

免费解锁B站大会员4K画质:手把手教你用Python下载高清视频 【免费下载链接】bilibili-downloader B站视频下载,支持下载大会员清晰度4K,持续更新中 项目地址: https://gitcode.com/gh_mirrors/bil/bilibili-downloader 你是否曾想过&a…

作者头像 李华
网站建设 2026/8/6 19:36:50

OpenClaw 为什么凉得这么快?

OpenClaw 为什么凉得这么快? 我用了几个 AI Agent 后,终于明白了一个残酷事实 前几个月,AI Agent 圈有多疯狂? 可能很多人还记得。 各种教程刷屏: “手把手教你部署 OpenClaw” “让 AI 24小时替你干活” “你的下一位…

作者头像 李华