做 AI Agent 时,我终于搞懂了 Tracker 的真正作用

大家好,我是大煊,一个写了几年 Java,最近在啃 AI Agent 的后端。

相信很多朋友都听过 Memory、RAG,今天来聊聊 Tracker(追踪器)。它的作用也和"记忆"有关,但不是怎么让模型多记几句话,而是一个更工程化的场景:当 Agent 开始接业务任务时,怎么保存它执行到哪一步了?

记忆不是只有 Memory 和 RAG

我刚开始看 Agent 记忆这块,也有一个很自然的误解:

是不是加一个 Memory,把历史上下文存起来,就算 Agent 有记忆了?

再往后看 RAG,又会觉得:

那我把历史对话、用户资料、业务知识都丢进向量库,需要的时候检索一下,不就解决了吗?

后来按客服 Agent 的业务链路拆开看,才发现这事没那么简单。

Memory 更像"长期印象"。

RAG 更像"查资料"。

但 Tracker 解决的是另一件事:当前这件事进行到哪一步了。

所以这篇真正想聊的不是"怎么让模型多记几句话"。

而是:当 Agent 开始接业务任务时,系统里有没有一个地方,专门保存它执行到哪一步了?

这就是 DialogueStateTracker 的价值:它不是让模型更聪明,而是让系统自己别忘事。

我更愿意把它理解成:Agent 的运行时状态中心。

这张图是这篇的核心:LLM 不是状态中心,Tracker 才是。LLM 负责理解和表达,业务动作交给 Tool,状态交给 Tracker。

一个客服请求,背后其实是一串状态变化

拿"查订单"举例。

text 复制代码
用户:我要查订单
Agent:请提供订单号
用户:123456
Agent:您的订单已发货

但系统背后发生的是:

sequenceDiagram participant User as 用户 participant Agent as Agent Runtime participant Tracker as Tracker participant LLM as LLM participant Tool as 订单系统 User->>Agent: 我要查订单 Agent->>Tracker: 记录用户消息 Agent->>LLM: 判断意图 LLM-->>Agent: query_order Agent->>Tracker: 开启查订单流程 Agent-->>User: 请提供订单号 User->>Agent: 123456 Agent->>Tracker: 记录订单号 Agent->>Tool: 查询订单 Tool-->>Agent: 已发货 Agent->>Tracker: 写入订单状态 Agent-->>User: 您的订单已发货

这张图里,LLM 只负责理解和表达。

真正让系统跑起来的,是 Tracker 在旁边不断记录:

text 复制代码
当前意图是什么
当前流程是什么
哪些信息已经收集
哪个工具已经调用
工具结果是什么
下一步应该做什么

没有这些状态,Agent 就会变成一个"每轮都像第一次见你"的聊天窗口。

Tracker 到底存什么?

我现在会把 Tracker 拆成五类东西。

Tracker 里的东西 白话解释 客服例子
对话历史 用户和 Agent 说过什么 "我要查订单""请提供订单号"
槽位 Slots 业务字段 order_id=123456
流程 Flow 任务走到哪一步 正在查订单 / 正在退款
最近动作 上一步执行了什么 刚调用订单查询
序列化状态 能不能保存和恢复 服务重启后继续处理

Tracker 不像"记忆力",更像一个带生命周期的对话上下文。

Controller、Service、Action、LLM 不要各自记一份状态。

大家都读写同一个 Tracker。

这就是统一状态源的价值:别让每个模块各记各的,不然一复杂就会互相打架。

还有一个小点也挺关键:Tracker 不是把所有历史都塞给 LLM。

它可以保存完整状态,但真正喂给模型的,通常只是一部分对话历史和必要业务信息。剩下的槽位、工具结果、流程状态,更多是给程序自己判断下一步用的。

Slot(槽位):把聊天里的关键信息变成业务字段

客服 Agent 最怕一件事:

用户明明说了订单号,系统后面却用不上。

原因很简单:自然语言历史不是业务字段。

用户说:

text 复制代码
我的订单号是 123456

系统真正需要的是:

text 复制代码
order_id = 123456

这就是 Slot(槽位)。

Slot 有点像表单字段。

退款要订单号,改地址要新地址,贷款要金额,人工转接要问题类型。

这些都应该从聊天里沉淀成结构化字段。

但这里有个边界很重要:

信息来源 谁来写入 例子
用户说出来的信息 LLM 可以提取 订单号、地址、退款原因
系统查出来的信息 Action 写入 订单状态、退款结果、会员等级

这件事不能混。

LLM 可以帮你理解"用户说了什么",但不要让它凭感觉决定"订单是否发货"。

订单状态必须来自订单系统。

这张图的重点是边界:理解归 LLM,事实归业务系统。

到这里,Tracker 已经不只是"聊天记录"了。它开始变成当前任务状态的容器。

Tracker 和 Memory 不是一回事

前面已经说了 Memory / RAG / Tracker 的区别,这里再从生命周期看一眼。

模块 解决的问题 例子
Tracker 当前这件事做到哪了 正在退款,已收集订单号
Memory 这个用户长期是什么样 喜欢中文、偏好某品牌
Knowledge Base 企业知道什么 退款规则、商品说明

这三类东西生命周期完全不同。

Tracker 里的"当前退款到确认金额"可能 10 分钟后就没用了。

Memory 里的"用户喜欢中文回复"可能几个月后还有效。

Knowledge Base 里的"退款政策"属于企业公共知识,不应该混进某个用户会话。

边界不清,Agent 项目越做越乱。

这张图我会贴在所有 Agent 状态设计文档最前面:生命周期不同,存储位置就不该一样。

Tracker 解决的三个生产问题

第一个:上下文丢失

用户说完订单号后,Agent 要知道这个数字属于刚才的"查订单任务"。

这靠的不是模型玄学,而是 Tracker 记录:

text 复制代码
active_flow = query_order
order_id = 123456

第二个:任务无法恢复

用户退款到一半,页面关了。

下次回来,系统要知道:

text 复制代码
退款流程已经走到确认金额
订单号已经收集
身份已经验证

如果 Tracker 能序列化,就可以保存到 Redis 或数据库里,后面再恢复。

sequenceDiagram participant Agent as Agent participant Tracker as Tracker participant Storage as 状态存储 Agent->>Tracker: 更新退款流程状态 Tracker->>Storage: 保存状态快照 Note over Agent: 服务重启 / 用户离开 Agent->>Storage: 读取状态快照 Storage-->>Tracker: 恢复 Tracker Agent-->>Agent: 从上次步骤继续

第三个:多模块状态不一致

没有统一 Tracker 时,很容易出现:

text 复制代码
LLM 以为在退款
Action 以为在查订单
前端显示人工接管
数据库里还是旧状态

这就是状态中心的价值。

不是为了"架构好看",而是为了避免业务系统各说各话。

一个系统越像"能办事的人",越要有清楚的状态中心。

这次对我最大的提醒是:看 Agent 架构时,不要只问"模型能不能理解",还要问"系统有没有地方保存当前任务状态"。

如果这个问题没想清楚,后面接多少 Memory、RAG、Tool,都会越做越乱。

相关推荐
Devlive 开源社区几秒前
AuthX 正式更名 GrantForge:我们重新做了一遍权限管理系统
大数据·人工智能·架构
微三云生态系统架构师-彭丹2 小时前
抖店OPC智能选品与铺货架构:多店差异化与频率风控设计
架构
集智飞行2 小时前
无人机集群通信架构剖析,以及对未来发展的几点判断
架构·无人机
想要打 Acm 的小周同学呀2 小时前
无需自己设计Agent架构的业务系统,依赖第三方Agent,基于SKILL和MCP服务实现企业级内部提效工具开发
架构·agent
Dawson Zhu4 小时前
《Agentic Design Patterns》第 4 章导读:反思(Reflection)
人工智能·语言模型·架构·aigc·agi
码云之上5 小时前
把网页变成可引用知识——Chatbot 联网工具
人工智能·架构·agent
独孤九剑打醒他5 小时前
【原创开源】【概念设计】源 - 栅 - 漏 - 栅 - 源 横向双栅 MOS,低压交流多值逻辑芯片探索
前端·其他·架构·开源·硬件工程
十六宿舍8 小时前
【软件设计模式-第一课:基础知识了解】
设计模式·架构·面向对象·软件架构
Layer8 小时前
即时通讯系统的关键设计
后端·架构
I Am a robert girl9 小时前
从科学代码库到智能体训练场:ScienceIDE 的架构拆解与工程启示
架构·强化学习·代码仓库·科学计算·监督微调·智能体训练·可编程环境