我让 AI 读 PRD 写测试用例:一套真正跑通的工作流

测试 ·

先说一个可能有点反直觉的前提:写测试用例最耗时的环节,从来不是“想不出该测什么”。

一个做了几年测试的人,看完 PRD 心里大概就有数了——哪里是主流程,哪里有边界,哪个字段大概率会出问题。真正吃时间的是后面那段体力活:把脑子里的东西一条条敲成结构化的用例,编号、前置条件、步骤、预期结果,再整理成评审时能摊开讲的样子。一个中等规模的需求,七八十条用例,敲完一个下午就没了。

而这段恰好是 AI 最擅长的:把已经明确的东西,按固定结构展开。

所以我花了点时间把它做成了一条流水线。现在的状态是:在需求目录下敲一句“生成测试用例”,几分钟后 ~/Downloads/测试用例/ 里出现一个 .xmind 文件,打开就能评审。这篇文章记的是这条流水线怎么搭的,以及更重要的——跑了一段时间之后,我对“哪部分能交给它”的真实判断。

一、整条链路

PRD(Markdown)
   ↓  AI 分析、拆解、按维度生成
结构化 JSON(中间格式)
   ↓  Python 脚本
XMind 文件(.xmind)

三步,中间那步是关键,下一节专门说。

先说两头。输入端是 PRD 的 Markdown。这里有个约定值得抄:输入在 PRD 目录,输出不在。生成的用例统一归档到一个固定位置,不散落在各个需求目录里。理由很简单——PRD 目录是按需求组织的,而找用例的时候你往往只记得需求名,不记得它在哪个项目下面。一个固定的收口位置,比“逻辑上更合理的分散存放”好用得多。

输出端选 XMind 而不是 Excel 或 Markdown 表格,是因为评审场景。用例天然是树状的:模块 → 子模块 → 场景 → 用例 → 步骤。评审时需要频繁折叠展开——先看整体覆盖够不够,再展开某个模块抠细节。表格做不到这件事,一屏几十行,看第三个模块的时候已经忘了第一个模块讲了什么。

二、为什么中间要有一层 JSON

最开始我的想法很朴素:能不能让 AI 直接生成 .xmind 文件?

不能,而且原因挺有意思。.xmind 本质上是个 zip 压缩包,里面装着 content.json、样式、缩略图等一堆东西。让语言模型直接吐二进制压缩包,这事从原理上就不成立。

那让它生成 Markdown,我再手工转?那等于把体力活从“敲用例”换成了“转格式”,没解决问题。

所以正确的切法是:让 AI 只负责它擅长的部分——把内容整理成规定结构的 JSON;剩下的确定性工作交给脚本。

{
  "project_name": "需求名称",
  "modules": [
    {
      "name": "Web 管理端",
      "sub_modules": [
        {
          "name": "创建模板",
          "scenarios": [
            {
              "name": "正常流程",
              "cases": [
                {
                  "id": "TC-001",
                  "title": "使用合法参数创建模板",
                  "precondition": "已登录管理员账号\n所在团队有可用模板额度",
                  "step_list": [
                    { "action": "进入模板管理页,点击新建", "expected": "弹出创建弹窗" },
                    { "action": "填写名称、选择类型", "expected": "" },
                    { "action": "点击确定", "expected": "提示创建成功,列表出现该模板" }
                  ],
                  "priority": "高",
                  "type": "功能"
                }
              ]
            }
          ]
        }
      ]
    }
  ],
  "common_cases": []
}

脚本那边是纯 Python 标准库,读 JSON,拼出 XMind 要的 content.json 结构,打包成 zip:

python3 xmind_exporter.py \
  --input /tmp/cases_xxx.json \
  --output ~/Downloads/测试用例/ \
  --name "需求名_测试用例"

这个分工带来一个额外好处:格式改动和内容生成解耦了。 后来我想给用例加优先级配色、想让前置条件展开成可见的子节点而不是藏在 notes 弹窗里——改的都只是脚本,一行提示词都没动。

有个细节值得单独拎出来:JSON 字符串里不能出现中文引号(" ")。AI 写中文的时候会很自然地用它们,而它们会直接让 JSON 解析失败。这条得明确写进约定里,否则每隔几次就会遇到一次。

三、维度怎么切

我固定用四个维度加一组通用场景:

功能测试——正常流程,参数合法、路径顺畅的情况。这部分 AI 生成得最好,因为 PRD 里写得最清楚。

边界条件——PRD 里凡是出现数字的地方,都要生成对应用例。这条可以写成硬规则:需求写“最多上传 30 张”,就必须有 29 / 30 / 31 三条。写“名称限 50 字符”,就要有 49 / 50 / 51。AI 执行这类规则非常可靠,比人可靠——人写到第七个模块的时候是会累的,会想“这个边界应该没问题吧”,然后跳过去。

异常与负面——必填项缺失、类型错误、鉴权失败、状态不允许操作、并发冲突。接口类需求这块可以模板化,每个接口固定那六种:正常请求、必填缺失(逐个测)、类型错误、边界值、鉴权失败、业务异常。

集成场景——跨模块的串联,A 改了之后 B 是否同步。这部分 AI 生成的质量明显下滑,后面细说。

外加一组通用场景,移动端需求必带:弱网和断网、切后台再回来、系统权限被拒、横竖屏、来电打断、机型兼容。这些 PRD 里永远不会写,但永远要测。放进固定清单,就不会漏。

最后如果有埋点变更,追加一段埋点验证。

四、跑了几个月之后,我的真实判断

这一节才是我想写这篇文章的原因。

先说结论:AI 能稳定接管的是“PRD 里写了的东西”,接不了的是“PRD 里没写但你知道的东西”。 而后者恰恰是一个测试的价值所在。

它做得比我好的

结构一致性。 七十条用例,编号连续、字段齐全、格式统一。人做不到——人写到后面会开始偷懒,前置条件从三行变成一行,步骤从五步压成两步。

规则的机械执行。 前面说的边界值、权限矩阵、流程分支,只要在提示词里写成硬规则,它就是不折不扣地展开。PRD 里有 A/B/C 三种权限,它会老老实实给每种权限都生成一遍,不会想“C 权限跟 B 差不多吧”。

覆盖面的兜底。 那组移动端通用场景,我自己写用例时漏过不止一次,尤其是赶版本的时候。清单化之后就再也没漏过。

它做不了的

业务的历史包袱。 PRD 写的是“这次要做什么”,不会写“上次为什么改成这样”。比如某个功能有个奇怪的降级逻辑,是因为半年前线上出过一次问题才加的——这条信息只存在于当时的复盘文档和几个人的记忆里。AI 读不到,它生成的用例就默认这个逻辑不存在。

跨需求的相互影响。 这次改的是 A 模块,但 A 的数据下游有 B 和 C 在消费。PRD 只描述 A。这种影响面判断,目前只能靠人。我的做法是把它当成一道固定的自查题:这次改动的数据,还有谁在用?

“哪里最可能出问题”的直觉。 AI 生成的用例,优先级分布是均匀的——它按规则给每条打 P0/P1/P2,但不知道这个团队的某个模块历史上就是 bug 高发区。回归时间不够要砍用例,砍哪些、留哪些,这个判断它给不了。

模糊需求的追问。 PRD 写得含糊的地方,AI 会顺着含糊往下写,生成一条同样含糊的用例。人看到含糊的地方会去问产品——而“发现这里需要问”本身就是测试工作的一部分。

所以现在的分工

我把它理解成:AI 出初稿,人做增删和定优先级。

初稿拿到手之后,我固定做三件事:

  1. 从头到尾扫一遍,删掉明显重复和没意义的用例(它有时会为了“覆盖全”而生成一些同质的条目)
  2. 补业务上下文相关的——历史逻辑、跨模块影响、这个模块的老毛病
  3. 重新调优先级,把真正的核心路径拎成 P0

这三件事加起来大概二十分钟,而原来敲用例要一个下午。省下来的不是“思考”的时间,是“敲字”的时间——这个区分很重要,它决定了你该期待 AI 帮你到什么程度。

五、固化成一句话

链路跑通之后,最后一步是别让自己每次都重复描述一遍。

我把整套约定写进了项目的 CLAUDE.md:默认读当前目录的 prd.md,输出 XMind,归档到固定目录,命名 {需求名}_测试用例.xmind,四个维度加埋点验证。格式转换那部分单独做成一个 skill,脚本跟着 skill 一起走。

于是现在的完整操作是:在需求目录下敲一句「生成测试用例」。

约定沉淀下来之后,最大的变化其实不是快,是稳定——每次的产出格式一样、维度一样、归档位置一样。评审的人不用每次重新适应一份新排版,我自己找历史用例也不用回忆当时放哪了。

六、几个具体的坑

一次性喂一个大 PRD,后半段会明显变水。 前两个模块的用例又细又具体,到第五个模块开始出现“验证功能正常”这种废话。解决办法是按模块分批生成,一次一个模块,最后合并。

预期结果必须逼它写具体。 默认它很爱写“上传成功”。这种预期等于没写——测试执行的人不知道该看什么算成功。要在规则里明确要求写到可判断的程度:「提示上传成功,图片出现在列表首位,数量角标 +1」。这条规则的收益极高,几乎是所有约定里最值的一条。

用例编号要求全局递增。 不加约束的话它会在每个模块内从 TC-001 重新开始,合并之后满屏重复编号,评审时根本没法引用。

别指望它读懂表格化的 PRD。 复杂的合并单元格表格、纯图片的流程图,转成 Markdown 之后信息丢得很厉害。遇到这种,我会先手工把关键规则摘成几行文字补在 PRD 后面,再让它读。

写在最后

这套东西做完之后,我有一个感受:AI 提效最实在的地方,往往不在“它替你想”,而在“它替你敲”。

网上很多“AI 提效”的说法,隐含的承诺是它能替你思考。至少在测试这件事上,我没体验到——它替我完成的是那些我早就想清楚、只是懒得写下来的部分。而正因为写下来的成本降到接近零,我反而更愿意把想到的东西都写出来了:以前觉得“这个边界不太可能出问题,不值得单开一条用例”,现在既然不花时间,那就都写上。

覆盖率的提升是从这儿来的,不是从“AI 比我想得全”来的。