client-ci: Windows unit tests 在 main 上稳定失败 —— VoiceInputSection 源码正则断言(疑与 CRLF 检出有关)
- Dominant language
- TypeScript
- Stars
- 2.7k
- Forks
- 395
- Avg merge
- 21h 48m
- Merged PRs (30d)
- 776
Description
## 现象
`client-ci` 的 **Windows unit tests (2/2)** 在 `main` 上稳定失败,卡住所有 PR 的
Windows check。失败的是一条**读源码做正则断言**的用例:
```
FAIL src/renderer/voice-input/__tests__/VoiceInputSection.recordingGate.test.ts
> VoiceInputSection shortcut recording gate
> keeps the Fn capture callback identity stable so the recording effect never re-runs mid-recording
AssertionError: expected 'import { useCallback, useEffect, useM…'
to match /const startFnKeyCapture = useCallbac…/
```
断言原文(`VoiceInputSection.recordingGate.test.ts:70`):
```ts
expect(source).toMatch(/const startFnKeyCapture = useCallback\([\s\S]*?\n {2}\}, \[\]\);/);
```
## 这是 main 的基线故障,不是某个 PR 引入的
`main` 上最近连续三次 `client-ci` 全红,失败的是**完全同一条断言**:
| head | run |
|---|---|
| `227dabf8` | [30785740406](https://github.com/makecindy/cindy/actions/runs/30785740406) |
| `643d232a` | [30783392096](https://github.com/makecindy/cindy/actions/runs/30783392096) |
| `3a3404b6` | [30782294875](https://github.com/makecindy/cindy/actions/runs/30782294875) |
## 平台相关,不是内容问题
同一份代码:
- **Linux(`verify`)**:SUCCESS
- **Windows(`unit tests 2/2`)**:FAILURE
- **本地 macOS**:`✓ 8 tests passed`(6ms)
被断言的模式在源码里确实存在(`VoiceInputSection.tsx:1255` 起,收尾 ` }, []);`
在 1286 行),所以不是「实现改了、断言没跟上」。
## 首要假设:Windows checkout 的 CRLF(**未实测确认**)
本仓 `.gitattributes` 没有 `* text=auto`,只对少数几类文件显式钉 LF:
```
*.sh text eol=lf
*.mjs text eol=lf # 注释里写明:CRLF + shebang 会让 vitest 直接 SyntaxError
.githooks/** text eol=lf # 注释里写明:CRLF 会让 git commit 直接 fatal
apps/desktop/drizzle/**/*.sql text eol=lf
```
**`.tsx` 不在其中**。Git for Windows 默认 `core.autocrlf=true`,会把它检出成 CRLF。
仓库对这类问题已有前科(上面两条注释就是被 CRLF 咬过之后加的),所以这是最合理的
方向。但我没能在 Windows 上实测复现,**这一条是假设不是结论**,请该模块负责人核实。
## 建议方向(二选一)
1. **测试不依赖行尾**:断言前把 `source` 归一化(`.replace(/\r\n/g, '\n')`),
或把正则里的 `\n` 换成 `\r?\n`。改动最小,且对所有「读源码正则断言」类用例通用。
2. **`.gitattributes` 钉住** `*.ts` / `*.tsx` 为 LF,与已有的 `.sh` / `.mjs` / hooks
同一处理。治本,但影响面大,要确认不会破坏其他 Windows 流程。
倾向 1:这类用例本来就不该对检出行尾敏感,而且仓里可能不止这一条。
## 出处
在 PR #1421 的 review follow-up 中撞上。该 PR 触及 voice-input **0 个文件**
(`git diff --name-only origin/main...HEAD | grep -c voice-input` = 0),
不宜顺带改这条,故单独开 issue。
> 另:同一 `Windows unit tests` 分片还有一条 **不同的** 间歇失败
> (`packages/maker-core` 的 SQLite 迁移用例超时),已记在 #1416,与本条互相独立。
Contributor guide
Research direction
Start with src/renderer/voice-input/__tests__/VoiceInputSection.recordingGate.test.ts:70 and inspect the source read from VoiceInputSection.tsx around line 1255. Run the recordingGate test on Windows or reproduce its line-ending behavior, then verify the assertion is insensitive to checkout line endings. Confirm the Windows unit-tests shard passes without changing the unrelated SQLite timeout issue in #1416.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- github-actions, typescript
- Domain
- ci-cd, testing
- Issue type
- Bug
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 72/100