Turborepo 全量测试红了,但锅不是你的
在一个 pnpm + Turborepo monorepo 里,我只新增了一个 UI 组件,本地 vitest run 12 个用例全绿,typecheck 干净,scoped build 也没问题。然后提交前跑 pnpm test(即 turbo run test 全量门禁),结果冒出来 2 个失败文件,而且看文件名——我根本没碰过那两个目录。
第一反应:完了,我动了什么底层依赖把别人的测试搞坏了?
现象
Test Files 2 failed | 12 passed
失败的是 accordion/accordion.test.tsx 和 _probe_overlay.test.tsx。我新增的是 alert/ 目录,和这两个文件毫无交集。
更诡异的是,我之前跑过一次"基线记录",turbo 输出了 >>> FULL TURBO ... cache hit, replaying logs,全部绿色,11 个测试文件全过。现在却变成了 14 个文件、2 个失败——多出来 3 个文件从哪来的?
根因
问题一:untracked WIP 文件
git status 一跑就露馅了:
?? packages/ui/src/accordion/
?? packages/ui/src/slider/
?? packages/ui/src/_probe_overlay.test.tsx
这三个目录/文件都是 ??——完全未追踪,不是我的工作,是另一个并行会话(或另一个 agent)在做别的功能,半成品搁在工作区里还没提交。它们的测试写了断言但实现还没跑通,所以一旦 vitest 扫到,就爆红。
问题二:turbo 缓存命中掩盖了真实状态
┌─────────────────────────────────────────────────┐
│ 基线时(untracked 文件还不存在) │
│ cache key = git HEAD SHA → 命中缓存 → 回放旧日志│
│ 结果:11 文件全绿 ✅(但是假象) │
└─────────────────────────────────────────────────┘
turbo 的缓存键基于 git 追踪文件的哈希,untracked 文件不影响缓存键。并行会话在我开始之后写入了 untracked 文件,下一次有代码变更(我新增 alert 组件)导致缓存失效,turbo 重新执行,这才把那 3 个 untracked WIP 文件一起扫进去了——14 个文件,2 个失败。
当工作区存在 untracked 文件时,turbo run test 的缓存命中只能代表缓存写入时刻的状态,不代表当前工作区的真实状态。如果并行会话在缓存写入之后又丢进来新文件,基线就已经过期了,但 turbo 仍然会骄傲地打印"cache hit, replaying logs"并回放绿色日志。
正解
第一步:先 git status,不要急着"修"
git status --short找出 ?? 行。把失败的测试文件集合和 ?? 集合对比——如果失败文件全在 untracked 集合里,那这些红不是你的。
第二步:独立验证自己的 scope
# 只跑自己的包
pnpm --filter @ui/components exec vitest run alert
# typecheck
pnpm typecheck
# scoped build
pnpm build --filter=www三项全绿,自己的工作就干净。
第三步:需要看真实全量状态时用 --force
turbo run test --force绕过缓存,强制重新执行,看到的才是现在工作区的真实情况。
第四步:不要删、不要改别人的 untracked 文件
这是别人的在途工作。你要做的是:提交自己的改动,然后在报告里写清楚——
我的 scope(alert 组件)12 个测试全绿,typecheck 和 build 均干净。全量
pnpm test门禁红了,是accordion/和_probe_overlay.test.tsx这两个 untracked WIP 文件导致的,我未动过它们,请相关同学跟进。
git status --short识别??文件集合- 对比失败文件是否全在 untracked 集合里
- 独立用
--filter=<pkg>跑自己的测试验绿 - 怀疑缓存基线失真时加
--force强制重跑 - 汇报污染情况而不是替别人"修"
一句话外卖
在多并行会话的 monorepo 里,
turbo run test红了先git status看 untracked 文件,turbo 的缓存命中基线随时可能因为 untracked WIP 而失效——先验证自己的 scope 干净,再 surface 污染,不要帮别人修半成品测试。