跳到正文
LangChain Blog·· 2 天前精选AI 评分75

LangChain 详解评测驱动开发(EDD):如何持续优化 AI 智能体

What Is Eval-Driven Development? How to Improve AI Agents

AI 导读

LangChain 提出评测驱动开发(Eval-Driven Development, EDD)框架,通过定义预期行为、在构建前编写评测集、变更后对比基线实验这三个步骤,解决非确定性 AI 智能体迭代中难以量化好坏的问题。

推荐理由

原文将传统测试驱动开发迁移至智能体工程,给出了先建评测集再迭代行为的三步流程,为非确定性系统的防回归提供了可执行规范。

正文 · AI 翻译

大多数智能体的开发起步时都大同小异:先写一段提示词,手动输入几个问题测测看,调整后再试。刚开始这套方法很管用,因为智能体犯的错误一目了然,改动带来的提升也很明显。但随着时间推移,你越来越难判断最新的一次修改究竟是让智能体变得更好,还是更差了。

评估驱动开发(Eval-driven development,简称 EDD)正是为了解决这个问题而生。它提供了一套统一的指标来衡量智能体的表现,并指导决策。在 LangChain,我们在构建最先进的智能体时一直采用 EDD(详见我们关于 IssueBench 的博文),并将其提炼为以下三步流程:

  1. 明确智能体“怎样才算做得好”。
  2. 动手构建之前,先写好评估用例。
  3. 做出改动并进行对比。

本文将一步步带你走完这一流程,方便你的团队将其应用到自己的智能体开发中。

什么是评估驱动开发?

评估驱动开发(EDD)的名称和理念脱胎于测试驱动开发(TDD)——即先写一个无法通过的测试,再去编写能让它通过的代码。但智能体与传统代码不同,它具有非确定性:

  • 输出具有随机性。同一个问题,每次运行得到的回答可能都不一样。
  • 正确答案往往不止一个。两个用词不同的自然语言结果,可能都完全正确。
  • 智能体会自主决定执行步骤。它可能会调用一个其实不需要的工具,或是跳过本来该用的工具,但最终依然给出了正确答案。

因此,智能体需要一种全新的测试方式。评估(eval)的作用就在于此:它通过一组测试用例来为智能体的多次运行打分。与传统测试相比,评估更为灵活,你不仅可以给智能体运行过程中的任何环节打分,还能借助其他大语言模型来进行评判(LLM-as-a-judge)。

在 EDD 中,与 TDD 类似,这些评估指标构成了你对“成功”的定义,整个智能体的构建过程都是围绕着达成这些评估目标来进行的。

第 1 步:明确智能体“怎样才算做得好”

EDD 的第一步是明确智能体要做什么。接下来,列出它实现该目标所必需的行为。这些行为可以是从知识库检索并回答问题、代用户执行某项操作,或是知道何时该追问更多细节。为每一种行为写明具体需求,综合起来就构成了智能体的产品需求文档(PRD)。

EDD 提倡一次只聚焦一项行为。这样能为你划定一个明确、集中的优化目标,避免多项改动相互干扰、难以分辨效果。你选择的行为通常来自即将开发的新功能,或者智能体在以往运行中暴露出的错误。在写代码之前,先制定一份简明规范会很有帮助,其中应包括:

  • 该行为何时触发
  • 智能体应该做什么
  • 智能体不应该做什么
  • PRD 中现有的哪些行为必须保持正常

这份规范应当足够明确,以便能明确判定“通过”还是“失败”。

假设我们有一个内部文档智能体,员工可以用它查询公司信息。它配有两个工具:用于查阅内部文档的 search_docs,以及处理其他事项的 web_search。我们计划新增一个 create_ticket 工具,用来提交 IT 工单。我们的规范如下:

  • 触发条件:用户反馈遇到故障,例如“我的笔记本连不上 VPN”。
  • 正确行为:调用 create_ticket。
  • 禁止行为:对操作咨询类问题(如“怎样连接 VPN?”)提工单。
  • 保持不变:search_docs 和 web_search 依然正常处理它们原本负责的问题

尽管该智能体目前还不具备这项能力,我们依然会依照这些准则来进行评估。

Docs agent tool routing: search_docs, web_search, and the planned create_ticket tool, each with an example input
这是文档智能体现有的示例实现,附带我们打算接入的工单工具。每个工具都配有能够触发它的示例输入。

第二步:动手开发前,先写评估方案

构建数据集。数据集是由一组测试用例(称为“示例”)组成的集合,每个用例都包含输入,有时还会附带参考的“标准答案”(golden outputs)。输入用例的最佳来源之一就是智能体的实际运行记录。用户的表达方式往往难以预料,提出的需求里也藏着你可能压根想不到的边界情况。测试示例越接近真实流量,评估拿到高分就越能代表线上表现稳定。在 LangSmith 中,你可以直接把智能体的真实运行记录加进数据集。如果目前还没有任何运行记录,通常可以从零开始手动编写示例。

对于我们的文档智能体来说,刚开始只需几个示例就足够了。我们在数据集中既会加入工单类请求,也会加入仍应交由 search_docs 和 web_search 处理的问题,以确保现有逻辑不受影响。

Docs agent dataset: example input questions paired with the tool the agent should call
每个示例都将一个输入问题与参考输出(即智能体应当调用的工具)配对。

你还可以扩充数据集,补足目前缺失的场景。比如我们现在缺乏反映用户沮丧情绪的样本,就可以把现有示例喂给大语言模型,让它改写成语气更愤怒的留言,以此检验智能体是否依然能调用正确的工具。

编写评估器。准备好数据集后,你就可以将 PRD 中关于“合格”的定义转化为具体的测试或评估逻辑,对智能体在各用例上的表现进行打分。在编写评估器时,要选择最适合当前测试的评分方式。如果检查逻辑是确定性的,推荐使用代码评估;如果不确定,则使用 LLM 评审员(LLM-as-a-judge)。你关注的是智能体的最终回答、达成结果所采取的行动,还是完全不同的维度?以我们的文档智能体为例,我们重点关注它调用的工具,以确认它在每种情况下都用对了工具。工具选择很容易通过代码进行判断,因此我们可以直接用代码评估来检查每个用例是否调用了参考输出中指定的工具。

Code evaluator that passes an example when the agent calls the tool in its reference output
只要智能体调用了参考输出中指定的工具,该用例即判定为通过。

我们的文档智能体只是一个功能明确的简单聊天机器人。随着智能体变得越来越复杂,你的评估体系可能也需要随之调整。如果你的智能体会对运行环境产生更改(比如在沙箱里运行的编程智能体),光检查几次工具调用和最终回复是远远不够的。你还需要检查智能体在系统中留下的最终状态,而且每次运行都必须提供干净的环境,以免相互干扰。Harbor 就是一个专门用来跑这类任务的开源智能体框架,它也是 Terminal-Bench 等行业基准背后的测试底座。其中的每个任务都在专属沙箱中执行,并配有用于给最终状态打分的测试脚本。

针对 Terminal-Bench 这类基准进行优化,流程和 EDD 完全一致:先编写任务与测试用例,跑出基准线,随后在调整智能体的过程中不断对比各项实验。我们在开发 LangSmith Engine 时,就结合真实与合成的智能体运行记录构建了专属基准,并将其作为 Harbor 评测来运行。我们还利用 Harbor 来评测 Deep Agents,借此判断能否在不降低智能体表现的前提下,精简掉测试框架中的某些模块,比如待办清单中间件或系统提示词的某些部分。

跑出基准线。无论你选择如何构建数据集或评测器,都可以让智能体跑一遍所有样本,并将结果以实验的形式记录在 LangSmith 中。一次实验就是智能体在整个数据集上的一次完整运行,其中每个样本的输入、输出以及评测得分都会保存在同一条记录里。有了集中的系统,你就能直接对比不同版本智能体的结果。在对智能体进行任何修改之前,跑一次基准实验作为对照指标至关重要。

在我们的文档智能体中,由于相关工具尚未创建,数据集中涉及工单的样本得分都是不合格的。其他样本则记录了目前已能正常工作的功能,方便你后续确认新增工具是否会破坏现有表现。

第 3 步:做出调整并进行对比

现在,我们来构建 create_ticket 工具,并运行相同的评测。

别忘了,EDD 的核心在于朝着评测目标不断“爬山”。所谓爬山,就是重复“评测、对比、调整”这套提升智能体的流程,从而建立起一套有客观证据支持的闭环迭代机制。之后对智能体所做的每一次修改都会生成独立的实验,每组实验都会与上一组进行比对,以验证是否有实质进展。在 LangSmith 中,你可以同时勾选两组实验打开对比视图,系统会并排展示每个样本的得分,哪些提升了、哪些发生了退步一目了然。

对比实验时,不仅要看平均分的变化,更要警惕能力退步或破坏原有正常行为的情况。在我们的文档智能体中,工单相关的样本现在通过了,但针对“如何连接 VPN?”这个问题,智能体却直接提交了工单,而不是去检索文档。虽然平均分提升了,但原本正常的用例却失效了。

Experiment comparison: the ticketing tool raises the average score while the VPN how-to question regresses
加入工单工具后平均分有所上升,但“如何连接 VPN?”这个用例却失败了。

想搞清楚评测为何失败,查看追踪记录(trace)是最好的办法。Trace 完整记录了智能体的一次运行过程,包括每一次模型调用和工具调用。无论你使用什么框架开发智能体,都能在 LangSmith 中使用追踪功能。欲了解详情,请参阅我们的追踪快速入门指南。

打开最新实验中失败用例的 trace 可以发现,工具描述里写着针对“VPN 和笔记本电脑问题”使用 create_ticket,因此只要提问中出现 VPN 就会命中该工具,进而破坏了基准测试中原本正常的行为。

Trace of the failing run showing a too-broad create_ticket tool description
Trace 表明工具描述写得过于宽泛,导致原本查阅文档就能解答的问题,智能体却去提交了工单。

解决办法是将工具描述的范围收窄,仅限于需要 IT 部门介入处理的请求。改好之后我们再次运行评测,这一次,所有用例全部通过。

Experiments over time: a tighter tool description gets every example passing
收窄工具描述的范围后,所有样本均顺利通过。

在小数据集上拿到满分是个好迹象,但 100% 并不总是合理的目标。我们在调试工具描述时,如果盯着手头这些具体示例反复调整智能体,直到所有用例全部通过,系统往往会开始对当前数据集过拟合,而无法真正学到你期望的行为。这样哪怕能跑通评估,一旦遇到测试集未覆盖的措辞方式,它依然会出错。要排查这种情况,最好保留一个在迭代过程中完全不看的留出集(held-out set)。如果调试用的示例得分持续上升,而留出集的表现停滞不前,那很大概率就是过拟合了。

多步智能体在任何一个环节都可能出错,因此 LangSmith 支持评估的不仅是最终答案。你可以对单步执行、完整的工具调用序列,或是归类为同一线程的多轮对话分别进行打分。

在交付过程中持续推行 EDD

实现评估自动化

随着版本迭代速度加快,团队很容易漏跑评估,或者遗忘早期的测试样本。在工作流中引入自动化评估,不仅能防止未经测试的改动直接流向用户,还能在上线前及时发现性能退化。

搭建评估套件的最佳策略取决于你的具体技术架构。快速的代码检查可以拦截有问题的代码合并,而耗时更长的 LLM 裁判评估则可以放在夜间定时任务或版本发布前运行。在迭代过程中,你可以利用数据集切分,只针对当前正在优化的行为跑用例,等到正式发布前再跑完整的测试集。

LangSmith 深度集成了 pytest 和 Vitest,让评估代码可以直接与业务代码放在一起,并在每次提交 PR 时自动执行。每次运行都会作为一次实验被记录下来,方便你与其他数据统一查看结果。

生产环境评估

在部署智能体之前,你的数据集往往只能覆盖开发阶段想到的场景。到了生产环境,你可以通过以下评估方式来捕捉并标记其余各种异常情况:

  • 在线评估器能够对实时流入的调用链路(Trace)进行打分。你可以将代码检查和 LLM 裁判绑定到链路追踪项目中,并通过流量采样来控制运行成本。
  • 标注队列支持团队手动复核被标记的运行记录。这也是在正式依赖 LLM 裁判之前,检验其评判标准是否与人类一致的必经之路。
  • 监控看板支持长期追踪评估得分、反馈、成本和延迟,直观展现某次发布究竟是带来了改进还是倒退。
  • Insights 可以将生产环境中的 Trace 自动聚类,帮助你从成千上万次运行中发现新的模式规律。
  • LangSmith Engine 则更进一步,能直接将聚合出的问题聚类转化为带有断言的数据集样本,供你人工审核。

我们还在代码仓库中公开了用于 Deep Agents 的评估套件,方便你参考真实的生产级评估体系。

常见误区

  • 对“成功”的定义过于宽泛。前期一定要下足功夫把成功的标准定义清楚,以便评估程序明确判定通过或失败。“回答很有用”就不是一个定义清晰的指标。
  • 修复问题之后才写评估。一旦看到了新的输出,很容易写出一个“专门用来通过测试”的评估。正确的做法是先写评估,并确认它在当前有问题的版本上确实会报错失败。
  • 只看平均得分。平均分的提升可能会掩盖某些样本的退化,或是忽视某些原本正常的行为被改坏。在决定保留改动之前,务必逐一审查每个测试用例的具体表现。
  • 盲目增加不必要的评测。每项评测都会在某种程度上引导智能体的行为。建议将每项评测都与具体的改动挂钩,比如针对性修复的失败案例,或是即将上线的新功能。
  • 盲信未经校准的裁判模型。务必先将 LLM 裁判的打分与人工评分进行对比校验。向裁判提问时范围要明确聚焦,并采用明确的“通过/未通过”,而非模棱两可的 1 到 10 分制。

想了解更多有关智能体评测构建的内容,不妨观看线上研讨会《智能体评测 101》,以及我们在 LangChain Academy 推出的免费 LangSmith 课程!

延伸阅读:

来源:LangChain Blog · langchain.com