单元测试用例必须相互隔离,需在beforeEach中重置localStorage、mock、模块缓存及被测对象实例,在afterEach中清除定时器和事件监听器,并显式处理异步操作完成。

单元测试用例之间必须相互隔离,否则一个测试的副作用可能让另一个测试意外失败或通过——这是 JavaScript 单元测试中最隐蔽也最常被忽视的问题之一。
清理全局状态和共享对象
浏览器环境中的 localStorage、sessionStorage、document、globalThis 上挂载的变量,或者 Node.js 中的模块级缓存,都可能在测试间残留数据。Jest 默认不自动清空这些内容。
- 在 beforeEach 中主动重置:比如
localStorage.clear()、jest.clearAllMocks() - 对单例类或全局配置对象,每次测试前重新初始化,而不是复用上一个测试创建的实例
- 避免在
describe外部声明可变变量(如let cache = {}),改用beforeEach内声明
重置模块加载器与 Mock 状态
ES 模块在 Node.js 中是单例缓存的。如果一个测试里 import 了某个模块并修改了它的导出值(比如打补丁、赋新函数),后续测试会继承这个改动。
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
- 使用
jest.resetModules()在 beforeEach 中重置模块缓存,确保每次import都拿到原始模块 - 对
jest.mock()创建的模拟,配合jest.clearAllMocks()清除调用记录和返回值,防止断言误判 - 若需在单个测试中临时 mock,优先用
jest.spyOn(obj, 'method').mockImplementation(...),它默认作用域更可控
避免异步操作跨测试泄漏
未正确 await 的定时器、未关闭的事件监听器、未 resolve 的 Promise,可能在下一个测试开始后才触发回调,导致断言错位或状态污染。
立即学习“Java免费学习笔记(深入)”;
- 所有异步测试必须显式处理完成:用
async/await、return Promise或done()回调 - 在 afterEach 中清除已注册的定时器(
clearTimeout、clearInterval)和事件监听器(removeEventListener) - 对基于事件的代码(如 EventEmitter),确保每个测试单独创建实例,不复用
不共用被测对象实例
多个测试用例如果都操作同一个对象(比如 new 一次然后反复 use),就等于在共享状态。
- 把被测对象的创建逻辑放进 beforeEach,保证每个测试拥有干净的新实例
- 对 React 组件测试,每次
render都应是全新挂载;避免在describe外部保留container或rerender引用 - 数据库连接、HTTP 客户端等外部依赖,一律通过构造函数注入,而非静态单例访问

















