Agent 编排升级:从“能跑”到“能持续演化”
Agent 编排升级:从“能跑”到“能持续演化”
wwxdsg这篇文章想复盘的,不是某一个 bug 的修复过程。
我更想讨论一个更底层的问题:
当一个企业智能助手同时要处理聊天、知识问答、数据分析和混合查询时,Agent 编排层到底应该承担什么责任?
在这次升级之前,OpsMind 的很多链路其实已经“能跑”了。
它能回答问题。
它能调用工具。
它能画图。
它也能勉强处理一些混合流程。
但我后来越来越确定:
能跑和能持续演化之间,隔着一整层架构能力。
为什么这次升级不是“修几个 bug”那么简单
最容易让人产生错觉的一件事,就是系统看起来已经能工作。
可当我重新审视这套 Agent 编排时,看到的不是几个孤立问题,而是一组高度相关的系统性信号:
- Router 已经识别出的能力,在 Workflow 层被静默吞掉
- 工具执行阶段产出的状态,没有进入跨轮可复用记忆
- 某些失败没有显式暴露,只伪装成“看似成功但内容空洞”
- 某些请求链路最危险的问题不是报错,而是无期限挂起
如果拆开看,每个都像普通缺陷。
但合起来看,它们指向的是同一个事实:
Agent 编排不是把模型和工具连起来就结束了,它本质上是在维护一个有状态、有预算、有退路的执行系统。
我重新定义了 Agent 编排层的职责
在更早的实现里,编排层更像“调用顺序的胶水层”:
- Router 决定
primary intent - Workflow 按 intent 选分支
- Agent 在需要时做 ReAct
- Tool 返回结果,模型再做总结
这样的结构当然能跑。
但它有一个很大的隐患:
编排层只知道“下一步调用谁”,却没有真正管理“当前系统处于什么状态”。
这次升级之后,我更倾向于把 Agent 编排层看成六类责任的组合:
- 路由解释责任:Router 给出的不是命令,而是建议
- 状态承接责任:一轮分析里产出的关键状态要能跨轮复用
- 执行预算责任:调用多久、循环多久、整条链路多久,都要显式管理
- 失败显性化责任:真失败就应该返回失败,而不是伪装成空结果
- 路径选择责任:混合请求不该被硬编码顺序静默压平
- 语义保真责任:知识库、上下文和计划都要以语义友好的方式保存
这六个职责,基本也对应了这次升级里最关键的六个问题。
六个问题,其实对应六个编排原则
1. 多轮数据分析无记忆
原来的系统里,如果用户接着上一轮说:
- “换成折线图”
- “沿用上次分析”
- “加上环比”
Agent 其实并不知道“上次分析”具体是什么。
因为会话历史里虽然保留了自然语言回答,但真正关键的分析状态并没有被当作资产保存下来,比如:
chart_plantable_plan- 列映射
- 数据形状
- 领域与分析逻辑
这件事暴露了一个很核心的原则:
在 Agent 系统里,可复用的不是上一轮说过的话,而是上一轮形成的结构化执行状态。
所以这次我做的不是“给 Agent 更多聊天历史”。
而是把最近一次分析配置从执行结果里透传出来,保存进会话消息 metadata,再在下一轮进入 Agent 时注入成一条 system memory。
这样系统获得的就不是“对话连续”,而是“任务连续”。
2. agent_decides 被静默吞掉
Router 其实已经能识别出某些混合请求不是固定顺序的。
比如:
- 先看数据再核规则
- 先查规则再看数据
- 顺序不明,交给 Agent 自主判断
问题在于,如果 Workflow 只支持固定分支,那么 agent_decides 这种信号就会在中途被压平成某个硬编码路径。
这说明一件很典型的事:
如果 Router 给出的能力不能被下游消费,Router 越聪明,系统的“假智能”就越重。
所以这次我把原则收得很明确:
- 显式顺序,交给显式编排
- 不确定顺序,交给 Agent ReAct
这不是多写一个 if 那么简单。
它意味着编排系统必须承认一件事:
某些问题的最优执行顺序,只有在运行期才会被确定。
3. Router confidence 原来几乎没意义
如果一个带 confidence 的路由结果,不管是 0.95 还是 0.50 都走一样的路径,那这个字段本质上就只是日志装饰。
这次我没有把它做成一套复杂的交互式追问。
我先做了最保守也最实用的一步:
当模型给出低置信 CHAT,但当前会话里已经有文件,query 又明显带数据词时,就自动把它从 CHAT 降级成 DATA。
为什么先做这个?
因为真实系统里最危险的低置信误判,不是“错了一点点”,而是:
它把请求送进了一个能力明显不足的分支。
所以我现在越来越认同,confidence 的作用不一定是让系统更复杂。
它首先应该让系统更保守。
4. execute_analysis 空 plan 静默成功
这是一个非常典型的工程问题:
plan_analysis生成了空图表计划execute_analysis没报错- 后面的 LLM 依然吐出一段“分析完成”的话
- 用户最终看到的是“像成功一样的失败”
比直接报错更糟糕的,往往就是这种假成功。
它会让系统表面稳定,实际却在持续输出低可信结果。
所以这里对应的原则很清楚:
中间态如果已经失去执行前提,就必须在中间层显式失败,不能把脏状态继续往后传。
编排层不仅要会“衔接成功路径”。
它还要会“阻断无意义路径”。
5. 所有 LLM 调用都没有超时
这类问题一开始很容易被忽略。
因为大多数时候模型都能在可接受时间内返回。
但只要链路复杂一点:
- Router 一次
- Agent 多轮 ReAct
- KB 改写一次
- RAG 回答一次
- Data engine 再调用若干次
就会发现“单次调用没问题”不等于“整条链路安全”。
这次我把超时拆成了三层:
- 单次模型调用超时
- Agent 总预算
- API 总请求超时
这样做的关键,不是为了显得严谨,而是为了让系统始终知道自己还剩多少时间可以花。
一个没有时间预算概念的 Agent,本质上不是智能体,而是概率性阻塞源。
6. KB 纯字符分块会截断语义
很多 RAG 系统一开始都会先用字符滑窗。
实现简单,性能也直接。
但对制度、流程、规则文档来说,这种方式有个很明显的问题:
- 一条审批规则可能被从中间切断
- 一个条件句可能和结果句分离
- 一个列表项可能只剩半句
这会带来一种非常难排查的质量退化:
检索看起来命中了,但命中的其实是语义残片。
所以这次我把分块策略换成了:
- 段落优先
- 超长段落按句子聚合
- 仍然过长才退回字符滑窗
背后的原则很朴素:
RAG 质量不只取决于 embedding 和 rerank,还取决于你有没有先把文档切成“人类还能理解的最小单元”。
这次升级后,我对 Agent 编排有了三个更稳定的判断
判断一:状态比过程更重要
很多系统会把大量精力花在“让 Agent 更会推理”上。
但更基础的问题其实是:
系统有没有把高价值状态留下来。
如果没有,每轮都在重新规划、重新读环境、重新猜上一次做了什么。
这不是智能。
这是昂贵的失忆。
判断二:编排系统要允许“不确定”
很多工程实现喜欢把所有路径在设计期写死:
- 这种走 A
- 那种走 B
- 混合就是 A 再 B
但真实请求经常不是这样。
有些问题最合理的顺序,本来就应该由 Agent 在看到局部结果后再决定。
所以一个成熟的编排层,至少应该允许三种模式并存:
- 静态路径
- 半静态路径
- 运行时决策路径
agent_decides 的价值就在这里。
它不是放弃架构设计。
它是承认:某些问题的最优流程,只能在执行期被确定。
判断三:失败设计是编排设计的一部分
如果一个系统只设计 happy path,它就不是真的编排系统。
它只是一串乐观调用。
真正的编排层,必须回答这些问题:
- 哪些失败应该立即中断
- 哪些失败可以降级继续
- 哪些失败必须向用户暴露
- 哪些失败应该转成 Agent 的反思上下文
从这个角度看:
- 空 plan 早失败
- KB 查询失败但保留数据结果
- ReAct 超时后阶段性收尾
- API 超时后显式 SSE
error
这些都不是边角料。
它们构成的是系统的可恢复性。
我现在更认同的一种 Agent 编排观
如果要用一句话总结这次升级后的思考,我会说:
Agent 编排层不是“提示词 + 工具调用”的包装层,而是一个负责管理状态、预算、置信度和语义边界的执行控制层。
它至少应该做到四件事:
- 把有价值的中间结果变成长期可复用状态
- 把不确定的路由结果变成显式策略选择
- 把模糊失败变成可诊断、可恢复的失败
- 把所有外部依赖纳入统一的时间预算体系
只有做到这些,Agent 才不是“偶尔表现得像个智能体”。
它才开始具备稳定的工程行为。
这次升级后,系统真正变强的地方是什么
如果只从 diff 看,这次改动里有很多具体点:
chart_plan / table_plan持久化agent_decides回到 Agent- 低置信路由降级
- 空 plan early return
- LLM timeout + budget
- 段落级 KB chunking
但从架构层面看,真正变强的是另一件事:
OpsMind 的 Agent 编排开始从“流程驱动”转向“状态驱动”。
这意味着之后系统更容易承接的会是:
- 多轮分析迭代
- 混合查询的动态策略选择
- 会话级任务恢复
- 更细粒度的失败恢复
- 更稳的长期记忆与知识边界
这也是我觉得这次升级最值得记录的地方。
不是因为它修了六个问题。
而是因为它让系统往“可持续演化的 Agent 架构”迈进了一步。
一个仍然需要记住的后续动作
这次 KB 分块策略虽然已经改成段落优先,但旧文档数据不会自动重切分。
所以如果要让知识库检索质量真正受益,后续还需要:
- 清理旧的向量数据
- 对文档重新 ingest
- 观察召回质量和答案稳定性变化
这类动作很容易在“代码改完以后”被忘掉。
但它其实是架构升级真正闭环的一部分。
结语
如果说之前的系统是在证明“Agent 编排能跑起来”。
那这次升级更像是在回答另一个问题:
当系统开始变复杂时,我们怎样让 Agent 编排继续保持可信、可控、可演化。
这比把一次回答做对更难。
但它决定了一个 Agent 系统到底只是 demo,还是能变成长期产品。