【第 2 篇:框架选型——LangChain、LangGraph、CrewAI】
第 2 篇:框架选型——LangChain、LangGraph、CrewAI
系列记录:《从零搭建企业级 LLM 应用》,这是第 2 篇
上一篇:项目起点——《从零搭建企业级 LLM 应用》
下一篇:Dify——低代码开发平台,快速搭建一个智能体
主流 Agent 框架
选择框架时,不看框架有什么功能,先想清楚我需要什么。
仔细想了一下,我的路由需求其实很简单:
- 用户问一个问题
- 判断用户意图
- 发给对应的 Agent 去执行
- Agent 执行的时候,可能需要调好几次工具
- Agent 返回结果,原样展示
用户提问 → [判断用户query的意图] → 发给对应 Agent → Agent 自己决定怎么执行 → 返回结果
两个关键要求:
- 意图判别决定路由分发
- Agent 要自主——Agent 拿到任务后,自己决定调什么工具、调几次,不要我写死流程
先试了最简单的方案:关键词判断
一开始想的是,自己写个 if-else 不就行了:
def route(user_input):
if "统计" in user_input or "排名" in user_input:
return agent_1
elif "编写" in user_input:
return agent_2
else:
return agent_3
实际一跑就发现问题。用户说"帮我分析一下这个数据",没有"统计"两个字,直接误判。说"看看最近的情况",更无从判断了。
关键词匹配做路由,覆盖面和鲁棒性都不够。
差点选了 CrewAI
CrewAI——给每个 Agent 设定角色、目标、背景故事,让它们像团队一样协作。
1. 我真的需要 Agent 之间"协商"吗?
不需要。我的场景是:一次只有一个 Agent 干活,不需要它们互相讨论,只需要给不同的业务场景分发不同的 Agent 去处理
CrewAI 的优势是"多 Agent 协作",但我的场景根本没有协作需求。用它的代价(调度黑盒、调试困难)就不值得了。
2. 出问题了我能定位吗?
CrewAI 的调度过程比较黑盒——Agent 之间的协商逻辑我不完全可控。如果路由错了,很难知道是在哪个环节、什么原因导致的。
最后放弃 CrewAI 的核心原因是:我需要的是一个听话的路由器,不是一个会自己开会的团队。
LangChain 和 LangGraph 的区别
很多人以为 LangChain 和 LangGraph 是二选一的关系,我理解实际上它们解决的是不同层面的问题。
我项目里的第一个 import 就是 LangChain:
from langchain_openai import ChatOpenAI # LLM 抽象层
from langchain_core.tools import tool # 工具装饰器
from langchain_core.prompts import ChatPromptTemplate # Prompt 模板
from langchain_core.messages import HumanMessage, AIMessage # 消息类型
① 模型抽象层,换模型不用改业务代码
# 用 Qwen
llm = ChatOpenAI(model="qwen-plus", base_url="...", api_key="...")
# 哪天想换 Ollama 本地模型,只改 base_url 和 model
# llm = ChatOpenAI(model="qwen3:35b", base_url="...")
② @tool 装饰器,定义工具只要写个函数
@tool
def search_kb(query: str) -> str:
"""检索知识库"""
...
③ ChatPromptTemplate,结构化写 prompt
QUERY_REWRITE_PROMPT = ChatPromptTemplate.from_messages([
("system", "你是检索专家。把用户问题改写为更适合语义搜索的形式..."),
("human", "原始问题:{question}"),
])
chain = QUERY_REWRITE_PROMPT | llm
result = chain.invoke({"question": user_input})
ChatPromptTemplate 的结构化 prompt 比手动拼接字符串清晰很多,后续加变量、调整 system prompt 都很方便。
④ HumanMessage / AIMessage,统一的消息类型
在流式处理中,我需要判断每条消息是工具调用还是最终回答,靠的就是 isinstance(msg, AIMessage)。
但 LangChain 解决不了"流程怎么串"
LangChain 帮你调模型、定义工具、写 prompt,但它不管"先干啥、后干啥"。
举个例子:Data Agent 需要"先列文件 → 再检查结构 → 最后执行代码"。用纯 LangChain 的话,我得自己写 if-else 控制这串流程,多 Agent 之间的路由更得手写。
这就是 LangGraph 补上的那块拼图——它在 LangChain 之上,管编排。
| LangChain 做的事 | LangGraph 做的事 | |
|---|---|---|
| 作用 | 调 Qwen、定义 tool、写 prompt、处理消息 | 创建 ReAct Agent、Supervisor 路由、对话记忆 |
| 缺少 | 流程怎么串、多个 Agent 怎么协作 | 怎么调 LLM、怎么定义工具 |
| 缺点 | 我得手动拼接 API 请求、手写 JSON schema | 我得手写状态机、手写 Agent 循环 |
一句话:LangChain 帮我"造零件",LangGraph 帮我"画施工图"。两个一起用。
最后选了 LangGraph 的 Supervisor 模式
LangGraph 的 create_supervisor 模式恰好就是我想要的:一个用 LLM 做智能判断的路由器 + 多个独立执行的 Sub-Agent。
核心思路很简单——三个 Sub-Agent 各自封装自己的工具和逻辑,一个 Supervisor 通过 prompt 规则判断意图并转发。框架只需要几行代码就能搭起来:
# 创建子 Agent
agent_1 = create_agent_1(llm)
agent_2 = create_agent_2(llm)
agent_3 = create_agent_3(llm)
# 创建 Supervisor:指定子 Agent + 路由规则 + 对话记忆
router = create_supervisor(
agents=[agent_1, agent_2, agent_3],
model=llm,
prompt="你是任务路由器。判断问题类型,转发给对应 Agent…",
checkpointer=MemorySaver(),
).compile()
Supervisor 的 prompt 是这套架构的关键配置,但设计原则就一句话:明确告诉它哪些问题交给谁,以及禁止它自己做任何事。
执行一次请求,底层走了什么
以"上个月迟到最多的 3 个人是谁?"为例:
用户发问
↓
Supervisor 判断:"这是数据分析" → 转发给 data_agent
↓
data_agent 思考:"我需要知道有哪些文件"
→ 自己调用 list_files(),拿到考勤表
↓
data_agent 思考:"上个月是 1 月,需要检查文件结构"
→ 自己调用 inspect_file("考勤_2026-01.xlsx")
↓
data_agent 思考:"我知道列名了,生成统计代码"
→ 自己调用 execute_data_query("迟到次数排序 TOP3")
↓
拿到结果 → 生成自然语言回答 → 经由 Supervisor 返回用户
用户发起的一次请求调用了什么Agent,Agent 调了几次工具、每次的输入输出是什么,全部可以在 LangSmith 里看到。这个可观测性对调试太重要了,Agent 不按预期走的时候,能一眼看到是哪步出了问题。
多做了一件事:直调模式
Supervisor 自动路由适合"用户自由提问"的场景。但如果用户在首页明确点击了"数据统计"按钮,再让 Supervisor 判断一次不仅多余,还可能误判。
所以我额外实现了一个直调入口——当用户意图已经明确时,直接调用对应的 Agent,跳过路由环节。
两种模式各有用处:
- 自由提问 → Supervisor 自动判断
- 明确选了模式 → 直调,跳过路由
这个设计不是一开始就想到的。是做首页 UI 的时候才意识到:既然用户已经明确选择了模式,就没必要再分发一次路由了
踩坑记录
坑 1:一开始 stream 和 invoke 跑了两次
最早的代码先 stream() 收集日志,再 invoke() 拿最终答案——结果所有 LLM 调用和工具执行都重复了,每次对话慢一倍。后来改成单次 stream() 同时收集日志和提取答案,响应时间直接砍半。
一些感受
LangGraph 有一个特点我很喜欢——它不强加任何概念。你想让它怎么流转,你就怎么定义。Router 只路由、Agent 只执行、工具只做一件事。每一层的职责都很清楚。
下一篇记录:Dify ——低代码开发平台,快速搭建一个智能体
AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。
更多推荐


所有评论(0)