Filed unassigned from #6128 / PR #6248 —— 该 PR 的 Test Core (3/3) 被这条用例踢红,而它只改了 packages/lint + packages/formula。本单只记录发现,不含修法承诺。
签名
FAIL src/utils/format.exit-code.test.ts > emitJson / emitText — process.exitCode (#4873)
> a duration can no longer reach the exit-code slot (#4873)
AssertionError: expected 20 to be 19 // Object.is equality
❯ src/utils/format.exit-code.test.ts:115:31
判据(不是猜的)
用例(packages/cli/src/utils/format.exit-code.test.ts:101-115,由 #6220 / #4873 引入):
const timer = createTimer();
const durationMs = timer.elapsed() + 531; // 真实墙钟
…
expect(durationMs & 0xff).toBe(19); // 硬编码
而 createTimer(packages/cli/src/utils/format.ts:158-164)是真实墙钟:
export function createTimer() {
const start = Date.now();
return { elapsed: () => Date.now() - start, … };
}
531 & 0xff === 19,532 & 0xff === 20,533 & 0xff === 21。也就是说这条断言只有在 timer.elapsed() 恰好返回 0 时才成立 —— 而两行之间隔着一次 await emitJson(...) 和若干模块工作。runner 上只要跨了 1 毫秒就红,红的数字正好是 20,与 CI 的实际输出一致。
本机复现:空载时 6/6 全绿(elapsed() 一直是 0);把两行之间的耗时人为拉到 0-2ms 后,200 次里 133 次断言不成立。CI runner 比本机忙,所以它先撞上。
归属
修法方向(供分诊参考,非承诺)
用例真正想钉的是「Node 把退出码截断到 8 位,所以一个毫秒数会变成看似随机的退出码」。这与计时器无关,把 durationMs 换成一个字面量即可,断言随之变成确定性的:
const durationMs = 531; // 一次 `os migrate` 的合理耗时,取字面量
expect(durationMs & 0xff).toBe(19);
timer 在这条用例里只提供了一个不确定性来源,没有提供任何被测行为 —— emitJson 的类型拒绝与 process.exitCode 的截断都与它无关。
Refs:#6220 / #4873(引入处)、#5896(同族)、#5810(队列 flaky 处置)、PR #6248(被踢红的 PR)。
Filed unassigned from #6128 / PR #6248 —— 该 PR 的
Test Core (3/3)被这条用例踢红,而它只改了packages/lint+packages/formula。本单只记录发现,不含修法承诺。签名
判据(不是猜的)
用例(
packages/cli/src/utils/format.exit-code.test.ts:101-115,由 #6220 / #4873 引入):而
createTimer(packages/cli/src/utils/format.ts:158-164)是真实墙钟:531 & 0xff === 19,532 & 0xff === 20,533 & 0xff === 21。也就是说这条断言只有在timer.elapsed()恰好返回 0 时才成立 —— 而两行之间隔着一次await emitJson(...)和若干模块工作。runner 上只要跨了 1 毫秒就红,红的数字正好是20,与 CI 的实际输出一致。本机复现:空载时 6/6 全绿(
elapsed()一直是 0);把两行之间的耗时人为拉到 0-2ms 后,200 次里 133 次断言不成立。CI runner 比本机忙,所以它先撞上。归属
fix(cli): os migrate --json 成功时不再把耗时毫秒当成退出码),晚于 PR feat(lint): view/page 谓词裸标识符构建期闸门 —— 坏谓词发不出去 (#6128) #6248 的分支点,PR feat(lint): view/page 谓词裸标识符构建期闸门 —— 坏谓词发不出去 (#6128) #6248 树里根本没有这个文件 —— 它是通过 CI 的 merge ref 进来的,会踢红任何当天开出的 PR。now确定性断言按「值」比较,只有跨毫秒时才会红 —— 一条按运气报警的 pin #5896 是同一族:「确定性断言按值比较,只有跨毫秒时才会红 —— 一条按运气报警的 pin」。修法方向(供分诊参考,非承诺)
用例真正想钉的是「Node 把退出码截断到 8 位,所以一个毫秒数会变成看似随机的退出码」。这与计时器无关,把
durationMs换成一个字面量即可,断言随之变成确定性的:timer在这条用例里只提供了一个不确定性来源,没有提供任何被测行为 ——emitJson的类型拒绝与process.exitCode的截断都与它无关。Refs:#6220 / #4873(引入处)、#5896(同族)、#5810(队列 flaky 处置)、PR #6248(被踢红的 PR)。