Skip to content
看累了听个音乐吧

4.4 编写测试

4.4 编写测试

写测试是最适合外包给 AI 的工作之一

写测试这件事有个有趣的特点:你知道它该怎么做,但就是不想做。

不是不会写,就是枯燥——大量的 expect(xxx).toBe(yyy),大量的 mock,大量的重复结构……每次都要从头写,费时费力,而且容易漏。

这种"正确但无聊"的工作,正是 Claude Code 最擅长的。


第一步:找出没被测到的地方

别猜,让它扫:

analyze the test coverage for src/services/OrderService.ts.
which functions and branches are not covered by existing tests?
list them with a brief explanation of what each untested scenario does.

或者范围更大的:

scan the entire src/services/ directory.
identify the top 5 functions or modules with the lowest test coverage
or no tests at all. prioritize by business criticality.

拿到清单之后,你来决定先补哪些——业务核心逻辑优先,工具函数次之。


第二步:生成测试

write comprehensive tests for the checkout flow in
src/services/CheckoutService.ts.

cover:
- happy path: successful checkout
- payment failure: what happens when the payment gateway returns an error
- inventory check: what happens when an item goes out of stock during checkout
- discount code: valid codes, expired codes, already-used codes

use the existing test style in src/services/__tests__/
as a reference for structure and conventions.

注意最后一行:让它参考现有的测试风格。这样生成的测试在命名方式、mock 风格、断言写法上会和你的项目保持一致,不会突然出现一种全新的风格。


第三步:专门找 Edge Case

生成完基础测试之后,让它再想想边界条件:

for the tests you just wrote, what edge cases did you miss?
think about:
- null and undefined inputs
- empty arrays and strings
- extreme numeric values (0, negative numbers, very large numbers)
- concurrent calls (race conditions)
- what happens right at the boundary of a validation rule

add tests for the most important missing edge cases.

这一步往往能挖出真正有价值的测试——不是"系统正常工作时的验证",而是"系统在压力下还对不对"。


第四步:审查生成的测试

生成的测试不能无脑接受,要检查几件事:

它真的测试了行为,而不只是实现?

差的测试:

typescript
// 只测了内部实现细节
expect(service.internalCache).toHaveLength(1)

好的测试:

typescript
// 测试了外部可观测的行为
const result = await service.getUser(id)
expect(result.name).toBe('Alice')

如果测试和内部实现高度耦合,一次重构就会让所有测试红掉,测试本身成了负担。

Mock 的位置对不对?

review the tests you wrote.
are there any cases where you're mocking too much?
mocking internal implementation details makes tests brittle.
focus mocks on external dependencies (database, API calls, file system).

测试能真正发现 bug 吗?

for the test cases you wrote, if I introduced a bug in the function
(for example, reversed the conditional logic), would the tests catch it?
identify any tests that are "always green" regardless of the implementation.

把测试约定写进 CLAUDE.md

如果你的项目有特定的测试约定,写进 CLAUDE.md,避免每次都要重新说:

markdown
## 测试规范

- 测试框架:Vitest
- 单个测试文件:`npx vitest run path/to/test.ts`
- 命名规范:`describe('FunctionName')` + `it('should [behavior] when [condition]')`
- Mock 原则:只 mock 外部依赖(数据库、第三方 API),不 mock 内部模块
- 测试文件位置:和源文件同目录,命名 `xxx.test.ts`

快速补测试的完整流程

# 1. 找出测试缺口
find untested functions in src/services/PaymentService.ts

# 2. 生成测试骨架
write test cases for the processPayment function.
follow the test style in src/services/__tests__/UserService.test.ts

# 3. 运行确认
run the new tests and fix any failures

# 4. 找边界条件
what edge cases are missing from the tests you wrote?
add the 3 most important ones.

# 5. 检查测试质量
would these tests catch a bug if I accidentally swapped
the success and failure response handling?

把这个流程走一遍,一个函数的测试覆盖基本就齐了。

基于 CC BY-NC-SA 4.0 协议发布