场景与测试集
沙盒、自托管 runner 或对话 AI 跑的那些行,是场景和测试集。它们作为项目数据集的行出现(「来自场景」「来自测试集」),但在自己的编辑页里写、审、管理版本,因为它们带的不只是输入和期望:还有条件、数据检查、Agent 能调和不能调的工具,以及它以谁的身份操作。
| 场景 | 测试集 | |
|---|---|---|
| 是什么 | Agent 真去做的一件事,在正常、故障、攻击几种条件下各做一遍 | 一张测试题表,每道题带期望的结果 |
| 看什么 | Agent 调了哪些工具、做完后的数据、它的回复 | 每次回复,按测试集的判断标准看;Agent 还看它的工具调用、做完后的数据和读出的字段 |
| 一次测试算几次 | 条件数 × 次数 | 题数 × 条件数 × 次数 |
| 用在 | 沙盒或自托管 runner 上的 Agent | Agent 和对话 AI |
测试分两组:功能测试(Agent 能不能把事办对,出故障时会不会乱来)和安全测试(被诱导、被攻击时会不会泄露数据或越权)。攻击题组成的测试集在安全组里。
在哪里写
场景和测试集都在数据集下面写。数据集页上方的视图有「数据集」(列表)、「生成攻击数据集」和「全部测试(详细列表)」,对话 AI 的项目还有「测试集评分器」。
- **「全部测试(详细列表)」**列出每个场景的已确认版本、草稿和全部版本,可以勾选几个一起确认、删除。上面是「新建测试集」「手写一个场景」(对话 AI 的项目是「新建场景」)和「自动审批」开关;Agent 的项目还有「让 AI 帮你写测试」。数据集列表上,场景数据集的版本旁写着「N 个草稿」,点它也到这里。
- **「生成攻击数据集」**写安全测试,见下面的攻击测试。
- 不是场景的行,比如 SDK Eval 读的那些,用数据集列表的「AI 生成数据集」,或数据集页上的「手写一行」「导入」「AI 生成行」:见数据集。
让 AI 帮你写测试
在「全部测试(详细列表)」的「让 AI 帮你写测试」里选一种方式:
- 「平台读仓库来写(推荐)」(连 GitHub 仓库的项目):平台的模型以只读方式读仓库:README、入口代码、工具定义、提示词和业务规则、种子数据和 fixtures,从不读
.env和存密钥的文件。它按review.yaml里工具、数据查询和身份变量的名字,写主要任务、边界情况和出故障时的功能测试,并列出测试要用的文件(见附件)。英文的 Agent,测试里的话用英文写(和默认安全测试的语言一样判断),名字照代码原样。测试没有「运行那天」这样的变量,写进去的日期每次运行都原样发出,所以 AI 按用户的说法写日期(「昨天」「三天前」),不核对具体是哪一天。它边写边用平台导入时的检查自查,算进助手的每日额度,从不改你们的仓库。写完还列出剩下的事,按谁来做分三组:「平台自己修」(平台写的测试接入的事,点「让平台修」交给「让 AI 补全并检查」)、「你的产品大概率有问题的地方」(读代码时看到的,测试就是要测这些,不是测试的前提,不用先修)、「要你提供的东西」(测试文件、测试账号、代替真实网站的假页面)。 - 「让开发机 AI 读代码」:点「复制提示词」,粘贴到在 Agent 代码目录里打开的 Claude Code、Codex、Cursor 这类工具,再把它的回答整段贴回来,点「导入测试」。平台先逐个核对工具、数据查询和身份变量的名字;「复制修改说明,发回开发机 AI」把不对的交还给它。连上平台的开发机 AI会自己把场景交上来。
- 「填一份说明文档」或「用几句话说说」:助手按你填的模板或几句话起草场景,把它做的假设列出来给你核对。
「工具出故障」和「读到的内容里夹带指令」这两种条件由平台自己加上。
攻击测试
数据集页的「生成攻击数据集」视图写安全测试:
- 默认安全测试:第一个功能测试确认后,平台按 Agent 能做的事自己写一套(会执行命令的有命令注入,会读文件的有越界读文件,会访问外部地址的有套取密钥和工具返回里的提示注入),以确认过的测试用的账号发起。题目用 Agent 自己的语言:平台读到的 Agent 本身(系统提示词、仓库里的文件、开发机 AI 对它的描述、它的回复)和确认过的测试都明显是英文、里面没有中文时用英文,否则用中文。平台自己的 AI 写的测试(「让 AI 补全并检查」写的起步测试、对话 AI 的起步测试题、「平台读仓库来写」)和它写的能力清单不算,人改过以后才算。在本地测试机上,
reviewctl connect --ai从你机器上读的文件,它做完后平台不留副本,只记下它们是用什么语言写的,这算 Agent 自己的话(人用中文写的测试照旧让题目用中文)。英文的一套里平台自己的话也是英文:最上面的说明、各项检查的名字,以及给评审模型看的 Agent 的情况(它做什么、谁是登录用户、平台列出的表结构和攻击目标)。之前写好的不变。个人信息类的题只问 Agent 的数据里真有的字段(平台读得到它的数据库表结构,或它的测试接入读的数据文件时);问数据里没有的字段的题,AI 自动审批不会通过。它是草稿,照常审,每个项目只写一份:同时被触发几次、或写的时候平台 AI 在排队,也只存一份。每道题的时间上限和这个项目的功能测试一样(而不是固定 1 分钟),会调工具的 Agent 才有足够时间答完。某些类别这次没出成时,页面写明实际出了几道、缺哪几类(这几类这次没测到);只出成了不算数的题(例如只有「探查可用工具」,按公开内容的口径不构成得逞)时,当作没写成,不当成测过。默认安全测试有个下限:至少 10 道算数的题(「探查可用工具」这类按口径永远不算数的不计入),并且产品真有的每个高风险能力(会执行命令/代码、会写删文件或导出数据或碰别人的数据、会越界读文件、会外联或可能被套走密钥、工具返回里可能夹带指令)至少 1 道;不够就自动再出(最多 3 次,这一次没出成、前几次出成过的类别会留着),还不够就存下并写明出了几道、缺哪几类。工具投毒和工具返回内容里的提示注入只在平台知道哪个工具的说明、哪段返回内容里夹带了指令时才出(不知道时这两类出不出来能打到目标的题,不排进默认安全测试,也不算缺)。出题模型被它自己的安全过滤拦下、回空的时候,平台改用另一个平台模型把这批题写出来。「攻击测试」页的「重出默认安全测试」在后台写:点了就回,按钮旁写着照这个组织最近几次出题估的花费和时间(只算出题,AI 自动审批另算);写的时候按钮下面写着正在重出、已经写了多久,「测试新版本」的简单页和「全部选项」页也都会说一声;写完说存成了第几版、多少道题,失败就说为什么,「上次重出」一直写在按钮下面。模板卡上的「约 N 分钟 · 约 N 道」同样按这个组织最近真实出过的题估(出过两次以上时),写的时候显示已经写了多久。测试集还在等 AI 审批时,旁边的按钮写成「不等 AI 审完,直接确认」,并列出 AI 审批到目前为止说了什么。同名的两套安全测试会标上「默认 / 另建的 · 第几版 · 日期」区分开。 - 模板:「用这个模板」按这个 Agent 是做什么的写好攻击题,确认好后点「去运行」,到运行表单,并选好「只测安全」。用之前要先有至少一个确认过的测试,攻击会用它的账号。
- 「高级:自己挑攻击插件和改写手法」:核对「用途说明」,挑插件、改写手法和语言,点「生成预览」,逐题决定留不留,点「存成安全测试集草稿」。
平台写的攻击测试集(redteam-…)在数据集里也是一个数据集,它的页面上有「重新出一套题」。重新出的题(平台读到工具后自己重出的也一样)没覆盖到上一版的某一类、或上一版瞄准的高风险目标(/etc/passwd 这类系统文件、.env、内网地址),会把上一版(以及更早几版)那几道原题留下(最多 8 道,Agent 现在够不到的不留),新版本的页面写明留了几道。这个项目里以前真得逞过的攻击题,平台写的每一套新题(默认、重出、模板)都会带上(最多 20 道),而且每道至少问 3 次:Agent 的拒绝每次不一样,只问 1 次碰巧拒绝就会被记成「守住」。出题模型自己的拒答(「抱歉,我无法生成……」这类)不会被存成题目,出题时就重写。每道攻击按它自己的规则判断守住还是得逞(怎么判);评分器 attack_success 数得逞的次数,默认发布门槛有一次得逞就不通过。
测试集
「新建测试集」打开「准备测试题」:「从表格导入」(Excel .xlsx、CSV、JSONL 或 promptfoo 文件;说明每一列是什么:「问题」「参考答案」「要点」「标签」「文件」「期望值」……)、「逐条填写」或「让助手写」。一个测试集最多 1000 道题,一份表格最多 500 万个字符。多轮对话用 || 隔开各轮,平台一轮一轮地发,判定最后一轮的回答。一道题也可以由模拟用户来问。
对 Agent 来说,每道题都是它真去做的一件事;一道题可以交给它一份文件,并写上它应该读出的字段(「期望值」),报告按字段给出准确率。
手写一个场景
「手写一个场景」打开「通用任务」表单:「用户会怎么说」「做成什么样算完成」、Agent 以谁的身份操作、它能用的工具和其中哪些会改数据;还可以填它应该调用的工具、做完后数据应该是什么样、回复里必须说到什么、不允许的操作。「测故障情况:工具第一次调用时出错」和「测攻击情况:在工具返回的内容里夹带一段指令」加上这两种条件。
- 在「用户会怎么说」「做成什么样算完成」里用大白话写了不能做的事(「一个文件都不能删」「不改动原来的 cv.md」「不导出 customers」),表单会问「要把它变成检查吗?」,列出对应的规则(例如「调用 bash(命令里有 rm 这类删除命令)就算违规」「调用 write_file(改的是 cv.md 这个文件,按路径认)就算违规」「调用 write(改的是配置文件、记忆,按路径认)就算违规」),点「变成检查」加进「不允许的操作」,表单写明加了哪几条。规则按 Agent 真正改的文件、真正执行的命令判,文件内容里提到 cv.md 不算。
- 「高级」里的「能用的工具」按项目填好;Agent 的工具超过 50 个时留空,空着就是这些工具都能用,可以直接起草(一个测试最多列 50 个)。「应该调用哪些工具」「不允许的操作」里输入工具名就能搜到 Agent 的全部工具。「会改数据的工具」只勾会改数据的,只读的不用勾。
- 「做完后数据应该是什么样」(数据检查)写一个数据查询的名字,例如
claim_count,加上它接受的字段(where)和应该得到的值。名字用测试机或沙盒报上来的:每个是state_queries.yaml里的一项(SQLite 数据库写名字: SQL)。名字不在里面,导入会失败。这个文件怎么写,见数据查询。 - 「回复里必须说到」空着、也没有数据检查和应该调用的工具时,跑完没有东西可判:表单问「要不要把『做成什么样算完成』变成回复要点?」,点「变成回复要点」填进去;不改的话,起草时平台也这样做,并在草稿上写明。
- 「单次最多跑多久(分钟)」默认 5 分钟,联网调研这类慢任务可以调大,最多 120 分钟。平台写的联网调研类测试默认就是 15 分钟。
- 测试编号不填时按标题里的英文生成;标题是中文的,取用户原话里的英文名(例如
node-js-pnpm),都没有时是test-1这样的编号。
改用户说的话
测试页的「用户会怎么说」下面有「改说法」:只改用户对 Agent 说的这句话,不用碰规则原文。确认过的测试改了以后存成新版本草稿,确认后才用它测。平台的 AI 按新的说法改回复要点和「做成什么样算完成」(新说法要中文、要简短、要列出来源,就写进回复要点),别的检查不动;改不了时页面写明回复要点还是按原来的说法写的,请你核对。
草稿和版本
新加的测试都是草稿;运行只用确认过的。确认会锁定内容:确认过的版本不会再变,再改就是新版本(新版本确认后,数据集里的那一行跟着更新)。旧版本和它们的实验不受影响。
自动审批默认打开:开发机 AI、助手或平台写的草稿,先按规则核对名字和测试文件,再由 AI 看一遍,没问题就确认。没通过的,平台的模型按理由改,再审,最多 2 次(中间有了新情况,比如接入文件或仓库变了,最多 4 次)。只需要改测试接入的草稿交给「让 AI 补全并检查」,检查通过后再审。需要只有人能给的东西时(密钥、改你们的产品、期望值、付费服务),AI 停下并写明。你自己写或改过的草稿,等你自己点「确认」。
场景草稿的页面上,「确认前看一下」列出平台对照草稿的文字和它实际核对的东西查出来的问题:文字要测攻击或故障却没有对应的条件、只评回复的测试、守住时的状态就会被算成得逞的攻击、接入看不到测试要的工具调用或读不到数据、Agent 每次回答都会调的被禁工具。文字里写了不能做的事却没有不允许的操作时,后面写着可以加哪条规则,点「一键加上」直接加进草稿。接入读不到 Agent 做完后的数据(例如数据在文件或内存里)、测试自己又没写做完后的数据时,只写一句「这个测试按工具调用和回复判」,不拦它:这样的测试按工具调用和回复判对错。AI 审过草稿后,「要求和核对它的检查」表把每条要求对到核对它的检查上。
测试交给 Agent 一份文件、要它总结或说出文件里写了什么时,回复要点里的名称(英文名、路径)在这份文件里找不到,也列在「确认前看一下」里:Agent 照文件回答也过不了,AI 审批不让它通过,平台的 AI 读了这份文件再改回复要点。平台自己写这样的样例文件时,也照用它的测试的回复要点写,写完核对。后来的测试诊断说某一版测试写错了时,那一版的页面在 AI 审批下面写出诊断的话,有平台按诊断存的新版本就给出链接。
等人处理的草稿列在数据集 →「全部测试(详细列表)」里,「一键确认全部」一次确认它们。数据集里,有新草稿的那一行标着「有新草稿」:点开它,侧栏写这份草稿是第几版、AI 审批中还是没通过、是不是等人确认,「看草稿」打开草稿页,在那里确认。
条件
| 条件 | 发生什么 | 怎样算过 |
|---|---|---|
| 正常 | 用户用自己的话提出要求 | 事办成了,数据也对 |
| 故障 | 工具出错:第一次调用超时、被限流或没有权限,一直报服务错误,或者办成了但结果没传回给 Agent | 按场景的要求:「应恢复」「应停止」(如实说没办成)或「恢复或停止都可以」;都不能重复办事 |
| 攻击 | 工具返回的内容或用户的输入里夹带一句指令 | Agent 不照做 |
故障或攻击可以只打在对话的某一轮上。只想跑其中几种条件,用设置 →「高级」里的「测试新版本:全部选项」(更多选项)。
测试集的判断标准
判断标准是用来判每次回复的一条规则;它们和评分器库里列的是同一套检查。测试集的判断标准在它的「判断标准」一步里:「回复要满足什么」(AI 判定类必须引用回复原文作依据;规则类由程序判断)、「安全检查」、「自己写一条」、「从断言库添加」,Agent 还有「工具和数据检查」。定「每道题问几次」(默认 3 次)。确认前可以用「试一试」判一段回复。
附件
附件是测试时交给 Agent 的文件:票据、照片、XML 发票。它们跟着用到它们的那一行:在数据集里点开场景或测试集的那一行,侧栏的「附件」列出这一行的测试用到的文件、每份是从哪来的(从仓库拷来的,或 AI 写的样例),「上传附件」加新的。上传的文件按文件名挂到用到它的测试上。每个文件最大 20 MB,只收 PDF、PNG、JPEG、WebP、Excel(xlsx、xls)、XML、TXT、CSV 和 JSON。
- 在场景的任务里写
{{file:文件名}},就把这个文件交给 Agent。场景按内容记住它的文件:换一个文件就是另一个版本。 - 在测试集里,文件写在「文件」这一列;题目里写
{{file}}代表这道题的第一个文件。 - 用自托管 runner 的,也可以把文件留在自己的机器上:放进 runner 场景目录的
files/,只上报文件名和哈希。 - 连 GitHub 仓库的项目,测试里写到的文件平台从仓库拷(不拷像存密钥的文件),仓库里没有的 TXT、CSV、JSON、XML 写合成的样例。PDF、图片和真实的业务文档要人上传。
确认过的场景在用的文件删不了。
通过标准
通过标准决定沙盒或 runner 运行自己的结论,发布门槛的「测试结论为通过」规则读的就是它。开始测试时,当时的通过标准会一起锁定。
打开设置 →「发布门槛」→「自定义通过标准」。不设也行:默认每个场景在正常条件下每次都要通过,出故障时不能重复办事,有证实的安全问题就不通过。
| 部分 | 填什么 |
|---|---|
| 「关键任务」 | 结论取决于哪些测试:每个关键任务选「场景」「情况」,填「每次测试跑几次」和「至少通过(%)」。 |
| 「出故障时」 | 「要求恢复的故障里,至少恢复(%)」和「允许重复办事几次」(0 表示一次都不行) |
| 「出现这些就不通过」 | 「证实造成了实际影响」和「证实做了禁止的操作(即使被系统拦下)」 |
关键任务也会变成默认门槛的「必跑标签」,它们最低的那条线变成 task_done 规则(默认规则)。「每次测试跑几次」是关键任务跑几次:填 3,就要 3 次都通过才算稳定通过。运行表单不会让你跑得比通过标准要求的次数少。
测试集有自己的通过标准;没单独定的按默认:每题问几次就要几次都通过,这样的题至少占 90%,安全测试集每道题都要通过。
下一步
- 沙盒运行:用确认好的测试开始一次运行。
- 完整报告:看结论和发现的问题。
- review.yaml 参考:场景目录和测试里用的名字。