覆盖率报告别只看百分比:真正有价值的是增量风险

2 阅读4分钟

开头

很多团队都有覆盖率报告。

每次测试结束后,平台会生成一个数字:

行覆盖率:78%
分支覆盖率:52%
方法覆盖率:81%

这些数字看起来很专业,但一到发版决策时,测试负责人真正想问的是:

这次改动有没有测到?没测到的地方风险大不大?

如果覆盖率报告回答不了这个问题,它就只是统计结果,而不是测试决策依据。

1. 总量覆盖率的问题

总量覆盖率最大的问题是太粗。

一个系统有 10000 行代码,本次只改了 20 行。总覆盖率从 76% 变成 77%,对本次发版决策的帮助非常有限。

因为你不知道:

  • 本次修改的 20 行有没有被覆盖。
  • 核心分支有没有被执行。
  • 高风险链路有没有被回归。
  • 未覆盖代码是不是本次变更相关。

总量覆盖率适合看长期趋势,不适合直接指导一次发布。

2. 增量覆盖率更接近发版决策

精准测试更关注增量覆盖率。

也就是:只看本次变更相关代码有没有被测试覆盖。

示例:

本次变更方法:5 个
已覆盖方法:3 个
未覆盖方法:2 个
增量方法覆盖率:60%

这比“系统总体覆盖率 78%”更有价值。

如果未覆盖的两个方法都只是后台查询的小分支,风险可能可接受。

如果未覆盖的是支付回调、库存扣减、订单状态流转,那即使总覆盖率很高,也不能放心上线。

3. 覆盖率要和 Diff 关联

覆盖率本身没有方向,Diff 才给它方向。

一个好的报告应该这样展示:

变更方法:PaymentCallbackService#handleCallback
覆盖状态:已覆盖
未覆盖分支:重复回调异常分支
关联入口:POST /pay/callback
历史缺陷:重复回调导致订单状态异常
风险等级:中
建议:补充重复回调场景

注意,这里不是只展示数字,而是解释风险。

覆盖率一旦和 Diff、入口、历史缺陷关联起来,就会变成测试决策工具。

4. 未覆盖不一定都是问题

很多团队看到未覆盖就焦虑,其实未覆盖要分类。

可接受未覆盖

例如:

  • 防御性代码。
  • 废弃路径。
  • 非本次变更相关代码。
  • 低风险后台查询。
  • 很难构造且已有其他监控兜底的异常分支。

这些可以记录原因,不一定必须补测。

必须补测未覆盖

例如:

  • 本次变更核心方法。
  • 核心交易链路。
  • 历史缺陷相关路径。
  • 支付、库存、权限、资金相关逻辑。
  • 异常分支可能导致数据不一致。

这些未覆盖就应该进入补测清单。

精准测试不是追求 100% 覆盖,而是让未覆盖风险可解释、可关闭。

5. AI 如何解释覆盖率

AI 很适合做覆盖率解释,但前提是输入要结构化。

不要只给 AI:

覆盖率 78%,帮我分析风险。

这没有意义。

应该给它:

本次变更方法:OrderService#cancelOrder
影响入口:POST /order/cancel, Job: close-timeout-order
覆盖情况:接口取消订单已覆盖,定时关闭订单未覆盖
历史缺陷:超时关闭订单曾出现库存未释放
业务风险:订单状态和库存一致性

然后让 AI 输出:

  • 已覆盖风险。
  • 未覆盖风险。
  • 是否可接受。
  • 补测建议。
  • 需要研发确认的问题。

AI 的作用是把覆盖率数字翻译成测试能执行的建议。

6. 覆盖率报告应该长什么样

一个更有价值的覆盖率报告,可以包含这些字段:

版本:v1.2.3
变更方法数:12
已覆盖变更方法数:9
未覆盖变更方法数:3
高风险未覆盖:1
中风险未覆盖:2
关联入口:5 个
建议补测场景:4 个

再往下展开每个风险项:

风险项:InventoryService#releaseStock 未覆盖
影响入口:POST /order/cancel, Job: close-timeout-order
风险原因:库存释放失败会导致库存数据不一致
建议补测:取消订单、超时关闭订单、重复取消订单
责任确认:研发确认是否修改库存幂等逻辑

这样的报告才会被测试和研发真正使用。

7. 总结

覆盖率不是越高越好,而是越能解释风险越好。

对一次发版来说,最重要的不是系统总体覆盖率,而是:

  • 本次变更有没有被覆盖。
  • 未覆盖部分是不是高风险。
  • 未覆盖原因能不能解释。
  • 补测建议能不能执行。
  • 测试结论能不能复盘。

下一篇我会讲:让 AI 推荐回归范围前,必须先给它哪些上下文。