SuperAPI AI 工具集

javascript-testing

测试与质量

查看项目

更新于 10-16 04:13

技能介绍

用途

该技能提供使用 Vitest 编写高质量 JavaScript/Node.js 测试的完整指导,目标是在生产代码中实现 100% 代码覆盖率。适用于编写测试、达成测试覆盖率,或处理 JavaScript/TypeScript 测试文件的场景。

测试框架:Vitest

选择 Vitest 的原因:原生 ESM 支持(无需实验性标志)、无缝的 JSDOM 集成、比 Jest 更快、兼容 Jest API、内置基于 v8 的覆盖率。

标准测试结构:

your-script-dir/ ├── script.js └── tests/ └── script.test.js

Vitest 全局 API

全局 API 自动可用,无需导入:describe、test、it、expect、beforeEach、afterEach、beforeAll、afterAll、vi。仅在 mocking 时才需要导入 vi:

import { vi } from 'vitest'; vi.mock('module-name');

覆盖率要求

必须达到 100% 的对象:.claude/hooks/ 中的所有脚本、.claude/skills/ 中的所有脚本、utils/ 中的所有工具、业务逻辑脚本、数据处理脚本、API 交互脚本。覆盖率检查命令:pnpm test:coverage,必须显示 Statements、Branches、Functions、Lines 均为 100%。

测试可选的对象:一次性自动化脚本、Shell 命令包装器、output/tasks/ 中的临时/实验性脚本。

核心原则

  1. 慎用覆盖率忽略。通用规则是重构代码使其可测试,而不是忽略覆盖率。不要忽略可测试的业务逻辑。例外情况是浏览器自动化/集成代码(如 Playwright、Puppeteer 页面交互)和带 process.exit() 与参数解析的 CLI 入口,可用 /* c8 ignore start / 与 / c8 ignore stop / 包裹。使用 c8 ignore 时要求:提取可测试逻辑到独立函数、创建集成测试文件(.integration.test.js)覆盖被忽略代码、添加注释说明原因与测试方式、尽量缩小被忽略的代码块。

  2. 将 I/O 与业务逻辑分离。把业务逻辑拆分为独立的可测试函数,主函数只做薄 I/O 包装。

  3. 导出以便测试,配合 runIfMain(import.meta.url, main) 模式。

  4. 测试所有分支,包括参数缺失、文件不存在、正常路径等每条分支。

  5. 测试错误路径,对每个函数同时测试成功与失败路径(如用 vi.fn() 模拟 fetch 返回成功与失败)。

测试组织

采用 Arrange-Act-Assert 结构;使用描述性名称(如 should throw ValidationError when email invalid);每个测试聚焦一件事;通过 beforeAll/afterAll/beforeEach/afterEach 创建与清理测试资源。

运行测试

pnpm test(运行全部)、pnpm test:watch(监听模式)、pnpm test:coverage(带覆盖率)、pnpm test script.test.js(指定文件)、pnpm test --grep "pattern"(匹配模式)。

进阶主题

mocking-guide.md 涵盖模块/函数/fs mocking、process.exit()、process.argv、环境变量、定时器、Date、fetch/HTTP,以及何时 mock 与何时用真实依赖。coverage-strategies.md 涵盖重构 I/O 密集代码、测试错误路径、测试全部分支、处理边界情况。

集成测试与优化

优先使用真实依赖(如 JSDOM 解析 HTML)。对外部 API、慢/破坏性 fs 操作、定时器、process.exit 进行 mock;对纯 JS 库、内部模块、数据转换、算法使用真实实现。优化集成测试的方法:合并相关测试(避免每个测试启动新浏览器,可将 9 个测试 17 秒压缩到 3 个测试 2 秒以内)、让延迟可配置(如 file:// URL 用更短等待时间)、合并错误场景、对浏览器自动化使用 c8 ignore。

最佳实践汇总

使用 Vitest(而非 Jest);仅导入 vi(全局自动可用);生产代码达到 100% 覆盖率;为可测试性重构,仅在浏览器自动化/CLI 代码中使用 c8 ignore;I/O 与业务逻辑分离;测试全部分支与错误;尽可能使用真实依赖;编写描述性测试名;测试后清理;每个测试单一断言焦点。

常见陷阱

不要使用覆盖率忽略注释、跳过错误路径、测试实现细节、过度 mock、遗漏 else 分支、假设代码不可测试。应做到分离 I/O 与逻辑、测试全部分支与错误、使用真实库、测试后清理、描述性命名、每个测试单一焦点。