使用LangGraph在Python中构建智能体工作流
本文详细介绍了如何使用LangGraph在Python中构建完整的智能体工作流,从单次模型调用到具有持久对话记忆的工具使用智能体。涵盖了状态、节点、边的定义,消息历史管理,模型调用,工具注册与路由,以及推理循环追踪。
本文详细介绍了如何使用LangGraph在Python中构建完整的智能体工作流,从单次模型调用到具有持久对话记忆的工具使用智能体。
引言
大多数AI智能体设置能良好处理单轮问答:接收问题,调用模型,返回答案。但更困难的问题很快出现:智能体可能需要查询数据库、记住之前消息的上下文,或让用户清楚了解模型的决定过程。如果不为每个用例构建自定义管道,解决这些挑战往往会让实现变得复杂。
LangGraph为处理这些问题提供了清晰的结构。智能体被表示为图,节点是工作单元,边定义下一步执行什么,共享状态对象在每个步骤中携带完整消息历史。模型在节点内运行,因此每个推理步骤、工具调用和响应都成为图状态的一部分。这使得整个执行流程可见、可检查,并可供后续任何节点使用。
理解状态、节点和边
每个LangGraph图由三个组件构建:
- 状态(State):一个TypedDict,作为整个图的共享内存。每个节点从中读取并写入更新。字段如果不更新则保持不变。
- 节点(Nodes):普通的Python函数。节点接收当前状态作为参数,并返回要更新的字段字典。使用
add_node注册。 - 边(Edges):定义执行顺序。
add_edge(A, B)表示A完成后运行B。add_conditional_edges允许基于路由函数分支。
通过归约器(reducer)可以处理字段的累积。例如,使用operator.add可以使列表字段追加而非替换。LangGraph的MessagesState使用add_messages归约器,支持消息去重和排序。
管理对话历史
MessagesState是一个内置状态类型,包含一个messages字段,使用add_messages归约器。每次节点返回新消息时,它们会被追加到现有列表。我们可以扩展该状态以添加其他字段(如客户ID)。
在节点中调用模型
核心节点函数将当前消息列表传递给模型并附加其响应。使用ChatOpenAI(或任何LangChain聊天模型)并返回AIMessage。系统消息可以在每次调用时设置而不存储在状态中。
注册工具并路由工具调用
使用@tool装饰器定义工具,然后用bind_tools绑定到模型。ToolNode负责执行工具调用,tools_condition作为条件边,根据模型输出是否有tool_calls路由到工具节点或结束。从工具节点返回模型节点的边形成闭环,使模型能根据工具结果生成最终答案。
追踪推理循环
当模型使用工具时,实际过程比最终输出更复杂:模型先产生带有tool_calls的AIMessage,工具节点执行并返回ToolMessage,模型再次调用后生成最终回答。这是标准的ReAct模式,每次工具使用需要两次模型调用。
设置与安装
安装所需包:pip install langgraph langchain-openai python-dotenv,创建.env文件存放OpenAI API密钥。
本文从零开始构建图,涵盖所有步骤,为构建更复杂的智能体工作流奠定基础。