1. 为什么“代码写完”只是智能体开发的一半工作量
过去一年多,我给不少团队做过智能体相关的技术咨询和方案评审,发现大家普遍卡在同一个问题上:用Prompt接一个大模型API,搭一个看起来能跑通的Demo,可能只需要一两天。但一旦这个智能体要真正进入业务、面对真实用户、持续迭代,整个开发模式就会变得跟传统软件工程完全不一样。
这里的核心矛盾在于:传统软件开发的对象是代码,代码是确定性的——同样的输入,同样的逻辑,必然产生同样的输出。而智能体开发的对象是模型行为外加代码编排,模型行为是非确定性的。你精心调试好的Prompt,换了一批用户输入、换了一个模型版本、甚至换了服务端的随机种子,结果就可能完全不一样。
Anthropic的工程师们把这种新的工程范式叫作Harness Engineering,这个词里的Harness,本意是“马具、挽具”,引申过来就是“给智能体套上缰绳”。这个比喻我觉得特别精准:智能体本身像一匹有自己想法的马,你要做的不是把它当机器零件一样精确控制,而是给它设计一套合适的缰绳和驾驭方式,让它在你设定的路线上跑,同时保留它作为“马”的灵活性。
从工程实践的角度看,Harness engineering要解决的核心问题可以拆成几个层次:
- 如何定义“智能体表现好”:传统开发有明确的函数输出断言,智能体没有标准答案,你需要建设一套贴合业务的评估体系。
- 如何定位“智能体为什么表现差”:智能体的每次运行都涉及模型推理、工具调用、上下文拼接,问题可能出在任何一个环节,需要可观测的链路追踪。
- 如何让智能体稳定迭代:Prompt和代码改动的回归影响面不可控,需要有持续的离线评估和线上监控体系。
我个人的判断是,未来两三年,懂模型的人会很多,但能把“模型+工具+评估+观测+迭代”这一整条链路工程化的人,才是真正稀缺的。这篇文章就围绕这套方法论,把我踩过的坑、验证过可行的方案,以及我对这个方向的思考,完整梳理一遍。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 从“代码为中心”到“智能体为中心”:四个最关键的认知切换
2.1 正确性评估:从单元测试到评估集与评分器
传统软件开发里,单元测试是最基础的保障。你写一个函数,给定输入,断言输出符合预期。这个模式在智能体开发里几乎不成立,因为智能体的输出是自然语言,同一个意图可以有千百种合法表达方式,你没法写一个硬性的断言。
我见过很多团队犯的第一个错误,就是把传统的那套测试思路生搬硬套过来:给智能体写了十几个固定问题,看它能不能回答出“预设答案”,能就认为开发完成。结果一上线,真实用户的问题跟那十几个测试问题稍微换个说法,智能体就完全跑偏。
正确的做法是搭建一套**评估集+评分器(Eval Set + Grader)**的体系:
- 评估集不是随便收集几个问题,而是要从真实业务场景中选取,并且分层覆盖。比如一个客服智能体,评估集里应该有高频简单问题、低频复杂问题、边界模糊问题、需要多轮对话才能解决的问题、明确超出能力范围应拒答的问题。
- 评分器也不应该是一个固定答案的字符串匹配。实务中常用两种方式:规则评分器适合结果结构化的场景,比如工具调用参数是否合法、是否成功触发某个分支;模型评分器(LLM-as-judge)适合开放式回答,用一个更强或同级的模型,按照你定义的评分标准,给智能体的回答质量打分。
这里要特别提醒,LLM-as-judge不是拿过来就能用的。它自己也是一个模型,也会有偏见和误判。我后面的章节会专门讲这个坑。
2.2 调试方式:从断点与日志到链路追踪与状态快照
传统开发调试,你在关键位置打断点,看变量值,很容易定位问题。智能体调试最大的麻烦在于:你看到的只是最终的回复内容,但智能体为什么这样回复,中间经历了什么推理过程,调用了哪些工具,拿到了什么结果,这些如果不记录下来,出了问题你只能靠猜。
举个实际例子,一个基于RAG的问答智能体,用户问“我们公司年假政策是什么”,它回答了一个错误信息。这个错误可能来自几个完全不同的环节:可能是意图识别把问题分错了类,可能是检索阶段没召回相关文档,可能是重排阶段把不相关的文档排到了前面,可能是大模型在生成时没有严格遵循给定的文档内容而是自己发挥了。如果没有完整的链路追踪,你根本无从知道该优化哪里。
所以在Harness engineering的体系里,可观测性不是可选项,而是基础设施。至少要记录和展示以下信息:
- 用户输入的原始内容
- 每个工作流节点的输入和输出
- 每次大模型调用的完整Prompt、温度、模型版本、Token消耗
- 每次工具调用的名称、参数、返回结果、耗时
- 最终回复内容
- 如果是多轮对话,还需要保留上下文摘要和触发上下文更新的动作
有了这些,一次线上失败请求就能完整拆解成一条“因果链”,问题出在哪个环节一目了然。这比传统日志要丰富得多,本质上你是在给智能体的每次“思考过程”做快照。
2.3 回归保障:从CI回归到持续离线评估
传统开发中,代码合并之前跑一遍CI,所有测试通过就敢上线。智能体开发最大的噩梦就是:你只是改了一句Prompt,或者调整了一个RAG的检索Top K,原本正常的100个场景里,有95个依然正常,但有5个莫名其妙变差了,而且这5个可能还都是之前正常过的场景。
这就是智能体开发的另一个显著特征:回归无处不在,而且不总是因为你改了代码。模型服务端更新了版本、某个在线文档内容做了调整、甚至一个工具的返回结构有了细小的变化,都可能导致智能体行为的漂移。
应对这个问题的思路,是把评估做成一个持续运行的管道,而不是上线前的一次性动作。我们团队现在的做法是:
- 维护一份覆盖核心业务场景的离线评估集,数量不一定求多,但场景要全,通常几百条到一千条就够了。
- 每次改动Prompt、工作流配置或相关代码,都先跑一遍完整的离线评估,对比改动前后的通过率和关键指标。
- 线上跑一段时间后,把实际用户的典型成功和失败案例,定期回流到评估集中,让评估集始终接近真实的业务分布。
这个过程非常像传统软件工程里“先把测试写好,再写实现代码”的思路。我们内部叫它“评估驱动开发”,后面我会单独展开讲。
2.4 版本管理:从单一代码版本到多要素组合版本
做智能体开发,你要是只把代码放进Git,那几乎等于没管版本。因为一个智能体的行为,是由好几个独立变体共同决定的:代码逻辑、工作流配置、Prompt模板、所用的大模型版本、知识库数据快照、甚至推理参数。
同一个工作流,GPT-4o和Claude 3.5 Sonnet的表现可能天差地别;同一个Prompt,模型版本从V1升到V2,行为也会有细微变化。这意味着你无法只说“当前线上跑的智能体是哪个版本”,你必须记录完整的“组合指纹”。
在一个稍大规模的智能体项目里,我建议你为每次发布都生成一份“运行配置清单”,至少包含以下内容:
| 配置要素 | 说明 | 是否必需 |
|---|---|---|
| 代码版本 | 编排逻辑、工具实现的Git Commit ID | 是 |
| 工作流配置 | 节点连接、分支条件、循环设置 | 是 |
| Prompt版本 | 每个节点的Prompt模板ID和内容哈希 | 是 |
| 模型配置 | 模型供应商、模型名称、版本标识、温度参数 | 是 |
| 知识库版本 | RAG数据集的快照ID或文档更新时间点 | 视情况 |
| 工具版本 | 外部API接口的版本和返回结构Schema | 是 |
这套清单在你排查线上问题时价值极大。否则一旦线上出问题,你连“现在跑的是什么”都说不清楚,后面的排查和回滚都无从谈起。
3. 工具选型:平台型工具和自研评估管线,各解决什么问题
3.1 智能体开发平台能帮你搞定的部分
目前市面上已经有一批成熟的智能体应用开发平台,比如Dify、Coze(扣子)这类,搜“智能体开发”相关的内容时它们出现的频率很高。这些平台解决的是“从0到1跑通”的问题,它们的核心价值体现在三个方面:
- 可视化工作流编排:把Prompt提示、知识库检索、工具调用、多模型并行等节点以拖拽方式串联起来,大幅降低对代码能力的要求。
- 内置基础观测能力:日志列表、Token消耗统计、简单的会话回放,能满足中小型项目的调试需求。
- 开箱即用的组件生态:文本处理、知识库接入、各类插件,省去了很多重复开发。
如果你要快速验证一个智能体想法,或者业务规模不大、定制需求不复杂,这些平台是效率最高的选择。Dify在开源社区活跃度很高,部署灵活,适合有工程能力的团队基于它做二次开发;Coze对非技术用户更友好,更适合快速做一些轻量级应用。
3.2 平台工具覆盖不到的地方才是关键
但是当你进入真实的业务深水区,问题就来了。我遇到过的典型场景是这样的:工作流有十来个节点,涉及知识库检索、多个工具调用、好几轮条件分支,线上每天几千次对话,偶尔出现几个回答错误的情况。你想要针对这些错误案例优化Prompt,却发现平台只给了你一个日志列表,看不到每一步的中间结果;你想对比两版Prompt在全部历史案例上的表现,平台只能让你手动一条条试;你想把线上失败的案例导出来整理成回归测试集,平台根本不支持这种操作。
这些恰恰是Harness engineering最核心的地带:离线评估、批量回归、细粒度追踪、反馈回路。目前来说,大部分智能体平台对“上线后持续优化”的支持都还很初级。
3.3 一个自研轻量评估管线的思路参考
如果你的团队有基本的工程能力,我强烈建议在平台或框架之上,搭建一套轻量的自研评估管线。不用一开始就做得很宏大,我分享一个我们实践下来性价比最高的最小闭环方案:
- 评测集存储:用一份结构化的数据集(比如JSONL文件或数据库表)保存评估用例,每条用例包含用户输入、期望行为描述、难度标签、场景分类。不需要预设具体标准答案,但期望行为描述一定要清晰,否则没法评分。
- 批量回放器:写一个脚本,能够把评测集中的用例逐条提交给被测智能体,收集回答结果和完整运行轨迹。这一步要求你的智能体有一个可以被脚本调用的接口,所以从一开始就别把逻辑全写在UI里,给核心引擎封装一个API接口是值得的。
- 评分器对接:跑完之后,把输出结果丢给评分模块。可以用规则,也可以用模型评分。模型评分的Prompt模板建议单独维护,评分标准写得越细,评分结果越稳定。
- 报告对比:每次跑完评估,自动生成一份报告,包括整体通过率、各场景通过率、失败案例详情、Token消耗和平均延迟。更理想的是能把当前版本的结果和历史基线做对比,直接标出哪些场景变好了、哪些变差了。
这套管线的开发成本其实不高,一个熟悉Python的后端工程师两三天就能搭出原型,但它的价值是巨大的。它把你从“感觉智能体好像还行”变成了“我知道它哪里行、哪里不行,以及这次改动到底改好了什么、改坏了什么”。
4. 多智能体协作时,工程化难度为什么是几何级上升
4.1 从“一个智能体”到“一群智能体”的变化
搜索热词里出现了很多多智能体相关的内容,比如多智能体框架、多智能体系统、能预测多智能体交互的世界模型。这类内容之所以热度高,是因为大家已经意识到:单智能体能力始终有限,真正复杂的任务需要多个智能体各司其职、相互协作。比如一个完整的电商智能体体系,可能是这样的:
- 意图识别智能体:判断用户想退货、想查物流、还是想投诉
- 知识检索智能体:从售后政策、订单数据、物流接口中取回事实依据
- 话术生成智能体:基于意图和事实生成亲和、合规的回复草稿
- 质检智能体:检查生成的回复是否包含风险承诺、是否违反客服规范
多智能体系统确实能解决更复杂的问题,但它也带来了一个之前不存在的新问题:你不仅要保证单个智能体可靠,还要保证它们之间的交互可靠。
4.2 多智能体调试为什么更难
单智能体出问题,链路是可追溯的——你总能在一条技术路径上找到断点。多智能体出问题,问题往往出在“信息传递”上:A智能体输出的结论,B智能体根本没法理解;A智能体把关键信息放在第5行,B智能体的Prompt只让它看前3行;A智能体和B智能体对同一个字段的理解不一致,导致下游数据错乱。
我调试过一个具体案例:一个多智能体的客服系统里,意图识别智能体明明正确识别出了“退货”意图,质检智能体却判定最终回复“与用户意图不符”,打了低分。排查了很久才发现,是意图识别智能体向话术生成智能体传递数据时,把“return_reason”键拼写成了“reson”,话术生成智能体拿不到退货原因,只能生成一个泛泛的话术,质检智能体基于不完整的话术给出了差评。这种问题在单智能体时代根本不会出现,但在多智能体里,它就是家常便饭。
4.3 接口契约和全局观测,多智能体工程的必修课
所以我个人的强烈建议是:在设计多智能体系统时,先用定义接口的方式把智能体之间的通信契约定死。每个智能体的输出都应有明确的结构化Schema,什么字段、什么类型、什么语义。上线前,重点不只是测每个智能体单独的表现,还要测数据在智能体之间传递的完整性和语义一致性。
同时,可观测性的设计也必须升级为全局视角。单智能体的追踪是一条线,多智能体的追踪是一张网。你需要能按一次完整任务,查看所有智能体的调用时序、交互内容、每个节点上的输入输出快照,以及在哪个环节数据开始走样。没有这个能力,多智能体系统的线上问题基本只能靠猜,而靠猜的成本,做过的团队都懂。
5. 大模型评审的可靠性问题:LLM-as-Judge需要你这样校准
5.1 Judge模型为什么不能“开箱即用”
我在前面提到了可以用大模型来当评分器,评估另一个智能体的回答质量。这是目前做智能体离线评估最主流的方式,但它有一个绕不开的问题:Judge模型也是模型,它有自己的偏好、盲区和不稳定性。
我最早用Judge模型的时候,踩过一个大坑。我们给评分器写了一个评分标准,要求它从“准确性、完整性、友好度”三个维度给客服智能体的回答打分。结果跑了一批历史数据,发现它给某些回答打了高分,但我们人工一眼就能看出这些回答其实是有问题的——它把用户的一个核心问题漏掉了,只是话术写得很客气,Judge模型就被“友好度”带着走了。
后来检讨原因:评分Prompt里没有明确告诉它,在“准确性”和“完整性”不达标时,友好度不应该作为加分项。评分器真的会像人一样被“印象分”影响,而这个印象分又恰恰是模型训练时学到的语言风格模式。
5.2 一份稳定的评分Prompt需要做到的事
经过反复验证,我总结了一份可靠的评分Prompt至少要包含的几个要素:
- 任务边界:明确告诉Judge模型它的职责是评估回答质量,而不是回答问题本身。
- 分维度定义:每个评分维度要给出解释和正反例。比如“完整性:指回答是否覆盖了用户问题中的所有子问题。反例:用户问退换货流程和退款时间,回答只讲了流程,没讲退款时间。”
- 优先级规则:明确维度之间的优先级。比如“如果回答存在事实性错误,准确性得分上限为2分(满分5分),不论话术多么友好。”
- 输出格式约束:要求先输出每个维度的分数和简要理由,最后再给总分。这能促使Judge模型进行推理,而不是凭感觉给分。
- 自我检查要求:在评分Prompt最后加一个问题:“请再次确认你的评分是否严格依据了上述评分标准,是否存在被用户回复风格影响的情况?”实测这个简单的提示能显著提升评分稳定性。
5.3 跟人工标注结果做一致性对齐
这是最容易被忽略、也最重要的一步。Judge模型不是配置好了就一劳永逸,必须定期跟人工判断做对齐校准。我们的做法是:
- 每次抽50到100条典型的线上回答,先让人工按照同一套评分标准打分,再让Judge模型打分,计算它们之间的一致率。
- 如果一致率低于85%,说明评分标准或Prompt还需要调优。常见的情况是评分标准里的某条描述有歧义,人工和模型理解不一致。
- 每次调整评分标准后,都要重新对齐一次。这不是一锤子买卖,而是持续的过程,因为随着业务演进,回答质量的侧重点也在变化。
6. 这篇关于智能体持续迭代的实战踩坑记录,建议反复看
6.1 坑一:评测集都是在“自嗨”,跟线上真实分布完全脱节
我相信很多人都有过这种经历:自己精心准备了50个测试用例,每个问题都很有代表性,智能体也都能完美回答。结果一上线就被真实用户“教做人”。原因是,你准备的测试问题大多是自己一个人拍脑袋想的,不是你从真实对话日志里挖出来的。
我的建议是:评测集的种子必须来自真实数据。如果你已经上线,直接拉线上会话日志,按场景聚类,把典型的高频问题、失败问题、复杂问题挑出来,整理成评测集。如果你还没上线,至少要让业务人员参与整理,他们会告诉你用户真实会怎么问,而不是你自己想象用户怎么问。
6.2 坑二:只测“最终回复”,不测“过程行为”
很多团队对智能体做离线评估时,只看最后生成的回复好不好,完全不看中间的Tool调用是否合理、检索动作是否恰当、分支选择是否符合预期。这就导致一个非常隐蔽的问题:有时候智能体中间步骤完全错了,但碰巧最后输出是对的。你根本不知道它的错误过程未来会以什么形式爆发。
解决思路是给评估集里的关键用例,不只定义“好的最终结果”,还要定义“好的过程”。例如对于客服智能体的某个用例,过程要求是“必须调用订单查询工具,且查询参数正确”。对过程的校验可以用规则,也可以让Judge模型在评分时参考运行轨迹。我们团队现在把运行轨迹的关键节点摘要直接拼进评分Prompt,让评分器基于“过程+结果”做综合判断,效果比只看结果要可靠得多。
6.3 坑三:过度设计工作流,评估体系却跟不上
有一个现象在Dify这类可视化平台上特别常见:开发者搭建了一个非常复杂的工作流,节点十几二十个,条件分支绕来绕去,看起来很高级。但问他“为什么这里要加一个代码转换节点”,他说“上一步输出是一个字符串,我想转成数组”,再问他“上一个节点为什么不直接输出数组”,他就答不上来了。
实际上很多工作流的复杂分支,都是在掩盖底层设计不清晰的问题。我见过一个团队,为了应对几种特定问题,不断往工作流里加IF-ELSE分支,最后20多个节点,维护成本很高,稍微调整一个节点就导致其他分支出问题。
我的看法是:除非某个分支逻辑有明确的业务规则支撑(比如VIP用户走专属服务链路),否则优先让大模型通过Prompt灵活判断,而不是通过流程硬编码分支。工作流的复杂度和可控性不是正相关的。一个清晰的骨架加完善的评估体系,比一个庞杂的流程加薄弱的验证要可靠得多。
6.4 坑四:忽略成本和延迟这两个“隐形指标”
做智能体,大家容易只盯着回答质量,忽略了每次调用的Token成本和响应耗时。一个看似完美的智能体,如果每轮对话要调动两个大模型加上多轮工具调用,平均延迟8秒,每次成本0.3元,在真实业务里几乎是没法用的。
所以在Harness engineering里,我的建议是把成本和延迟写进评估报告,和准确率并列。每次改动Prompt或调整工作流,都要对比成本和延迟的变化,因为Prompt变长了、上下文变多了、多跳次数增加了,都会直接反映在成本上。不少时候我们最终会选择牺牲一点点准确率来换取成本和延迟的大幅下降,这需要在完整数据的支撑下判断。
7. 未来半年到一年,我认为值得重点投入的几个方向
7.1 评估驱动开发:从“写Prompt”到“写评测”
我越来越觉得,智能体开发未来的主流模式,不是“改Prompt上线看效果”,而是“先把评测写好,再改Prompt或调流程,跑评估看分数变化”。这就像传统开发里TDD(测试驱动开发)对行业的影响一样,评估集就是智能体开发者的测试,评审就是一个跑分工具,评测集越来越完善的过程,就是智能体质量越来越靠谱的过程。
团队里迟早会出现一个角色,专门负责维护评测集和评分标准而不是写业务代码。这个角色要很懂业务,知道哪些客户问题应该被高权重覆盖,也要很懂大模型能力边界,知道什么情况下智能体表现是可接受的,什么情况下是不可接受的。
7.2 智能体原生开发环境
现在的智能体调试工具普遍还很原始。虽然你可以用链路追踪看到智能体每一步的输入输出,但你想进一步尝试换一个Prompt、换一个工具看看效果,操作链路还是很笨重。未来一定会有更智能的开发环境出现,它应该具备把一次线上失败请求直接拉回本地沙箱的能力,允许你修改Prompt、参数、甚至工具返回结果后,立即回放整条链路,对比不同版本之间的行为差异。这类体验会大幅提升智能体开发的迭代效率。
7.3 护栏(Guardrails)的工程化
关于安全与合规,智能体的应用一直在受限制地拓展,合规的企业一定会给智能体加护栏。目前常见的做法是在Prompt里写“不要回答敏感问题”“不要泄露系统Prompt”,这类软约束的表现并不稳定。更可靠的方案是增加系统级护栏:在智能体输出前,用独立的规则过滤器或另一个审查模型对输出内容做校验,校验不通过就拦截。把护栏做成独立组件、可配置、可测试,就是工程化的方向。你不可能靠市场主体自觉完成这一步,企业如果要落地智能体,护栏体系的建设是绕不开的投入。
最后分享一个我个人的体会:做了这么久的智能体开发,我发现最大的进步不是来自某个Prompt技巧或者某个框架,而是来自把“评估”这件事当成整个开发流程的中心。以前我拿到一个智能体任务,第一反应是“这个Prompt怎么写”,现在第一反应变成了“这个任务怎么才算做好,我怎么评估”。这个转变,本质上就是把智能体从一个“有趣的实验品”变成了“一个值得严肃对待的工程对象”。这套方法论我还在持续沉淀,后续有新的实践我会再整理出来,跟大家一起交流。
