持久化与断点
LangGraph 相对普通 agent 循环的核心差异:每次节点执行后自动保存状态(checkpoint)。面试主线:checkpoint 机制、断点续跑、两种持久化的分工。
checkpoint:每个节点后存档
每步存档, 失败从最近存档续跑
from langgraph.checkpoint.memory import InMemorySaver
from langgraph.checkpoint.sqlite import SqliteSaver
graph = builder.compile(checkpointer=SqliteSaver.from_conn_string("graph.db"))
config = {"configurable": {"thread_id": "order-123"}}
graph.invoke({"messages": "处理订单"}, config=config)- checkpointer:节点执行后自动写入图状态快照,按 thread_id 组织
- thread_id 是状态指针:同 id 续跑(继续对话、恢复中断)、查历史、回放
- 后端:InMemorySaver(测试)、SqliteSaver/PostgresSaver(生产)
durable execution:可靠执行
checkpoint 带来的能力:
| 能力 | 说明 |
|---|---|
| 故障恢复 | 进程崩溃后从最近 checkpoint 续跑,不从头开始 |
| 断点续跑 | 中断(见人机协同篇)后带结果恢复 |
| 时间旅行 | 回放任意历史状态(调试、审计) |
| 对话连续 | 跨调用保持状态(见 LangChain 记忆篇) |
面试话术:durable execution = 状态每步落盘 + 失败可续跑。长任务(多轮工具调用、小时级任务)没有持久化就是纸糊的。
静态断点:调试与审核
graph = builder.compile(
checkpointer=checkpointer,
interrupt_before=["tools"], # 进入工具节点前暂停
# interrupt_after=["model"], # 模型节点后暂停
)- 静态断点:编译时指定,在特定节点前后暂停(
interrupt_before/interrupt_after) - 用途:调试逐步执行、审核流(工具执行前人工确认)、演示
- 与动态 interrupt 的区别:静态断点固定位置,动态中断在代码里任意位置(见人机协同篇)
checkpointer 与 store 的分工
| checkpointer | store | |
|---|---|---|
| 存什么 | 图状态快照(线程内) | 应用定义的键值数据(跨线程) |
| 作用域 | 单个 thread | 全局 |
| 记忆类型 | 短期(会话) | 长期(用户偏好、事实) |
| 场景 | 续跑、回放、故障恢复 | 跨会话记忆、共享知识 |
两者可同时挂载(compile(checkpointer=..., store=...))。生产部署(LangSmith Deployments / Agent Server)会自动管理持久化基础设施,不用手配。
面试追问
- checkpoint 是什么? 节点执行后自动保存的状态快照,按 thread_id 组织。崩溃后从最近存档续跑
- durable execution 什么意思? 状态每步落盘,失败/中断可续跑。长任务可靠性的基础
- thread_id 有什么用? 状态指针:续跑、回放、对话连续。换 id 就是新状态
- 静态断点和动态中断的区别? 静态断点编译时指定节点前后暂停;动态 interrupt 在代码任意位置,可带条件
- checkpointer 和 store 怎么分工? checkpoint 管线程内短期状态(续跑/回放),store 管跨线程长期记忆(偏好/事实)