You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Jest的单个测试用例中Mock ES6模块?

在Jest单个测试用例中Mock ES6模块的方法

针对你提到的场景——要在单个Jest测试用例里Mock src/validators.js 导出的isPositiveNumber函数,下面给你两种常用的实现方式,都能精准控制单个测试用例的Mock行为:


方法1:使用jest.spyOn + 临时Mock实现

这种方式适合只在特定测试用例中替换函数实现,其他测试用例仍使用原函数的场景,用完后还可以快速恢复原实现。

示例测试文件(比如src/calculators/__tests__/volume.test.js):

import { sphere } from '../volume';
import * as validators from '../../validators';
import { InvalidArgumentException } from '../../exceptions';

describe('sphere volume calculator', () => {
  // 在每个测试用例后恢复原函数,避免影响其他测试
  afterEach(() => {
    jest.restoreAllMocks();
  });

  test('抛出异常当radius不合法(Mock验证函数返回false)', () => {
    // 临时Mock isPositiveNumber函数,让它返回false
    const mockIsPositive = jest.spyOn(validators, 'isPositiveNumber').mockReturnValue(false);

    expect(() => sphere(0)).toThrow(InvalidArgumentException);
    expect(() => sphere(-5)).toThrow(InvalidArgumentException);
    // 验证Mock函数被调用
    expect(mockIsPositive).toHaveBeenCalledTimes(2);
  });

  test('正确计算球体体积(使用真实的验证函数)', () => {
    // 这里没有Mock,会使用原有的isPositiveNumber逻辑
    const radius = 3;
    const expectedVolume = (4/3) * Math.PI * Math.pow(radius, 3);
    expect(sphere(radius)).toBeCloseTo(expectedVolume);
  });
});

方法2:使用jest.mock结合mockImplementation动态修改

如果你需要在单个测试用例中覆盖全局的Mock实现,可以先在测试文件顶部全局Mock模块,然后在特定用例中修改它的返回值:

import { sphere } from '../volume';
import { isPositiveNumber } from '../../validators';
import { InvalidArgumentException } from '../../exceptions';

// 先全局Mock整个validators模块,初始让isPositiveNumber返回true
jest.mock('../../validators', () => ({
  isPositiveNumber: jest.fn().mockReturnValue(true)
}));

describe('sphere volume calculator', () => {
  test('抛出异常当radius不合法(修改Mock返回值)', () => {
    // 在这个测试用例中临时修改Mock的返回值为false
    isPositiveNumber.mockReturnValue(false);

    expect(() => sphere(-2)).toThrow(InvalidArgumentException);
    expect(isPositiveNumber).toHaveBeenCalledWith(-2);
  });

  test('正确计算球体体积(恢复Mock返回值为true)', () => {
    isPositiveNumber.mockReturnValue(true);

    expect(sphere(2)).toBeCloseTo((4/3)*Math.PI*8);
  });
});

注意点:

  • 如果你用jest.mock全局Mock,记得在需要的测试用例中重置或修改Mock的状态,避免测试用例之间互相影响;
  • 使用jest.spyOn的方式更灵活,因为它默认保留原函数实现,只在需要时替换,而且可以用jest.restoreAllMocks()在每个用例后快速恢复;
  • 不管哪种方式,都可以通过toHaveBeenCalled、toHaveBeenCalledWith等断言来验证Mock函数是否被正确调用。

内容的提问来源于stack exchange,提问作者AgmLauncher

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.25 03:53:35