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

如何在Jest中实现类的全方法Mock(替代Sinon createStubInstance)

在Jest中实现类的全方法自动存根(类似Sinon的createStubInstance)

在Jest里,你可以通过以下几种方式自动为类的所有方法生成存根,避免手动逐个列出方法:

方法一:基于原类原型自动生成Mock类

这种方式最接近Sinon createStubInstance的效果,会自动给原类的所有原型方法创建jest.fn()存根:

import AuditTrailClient from '<path-to-AuditTrailClient>';

jest.mock('<path-to-AuditTrailClient>', () => {
  // 创建空的Mock构造函数
  const MockAuditTrailClient = function() {};
  
  // 遍历原类原型的所有方法,为Mock类添加对应的jest.fn()存根
  Object.getOwnPropertyNames(AuditTrailClient.prototype).forEach(methodName => {
    // 跳过构造函数本身
    if (methodName !== 'constructor') {
      MockAuditTrailClient.prototype[methodName] = jest.fn();
    }
  });

  return MockAuditTrailClient;
});

使用时,你只需要正常导入并实例化类,得到的实例就会包含原类所有原型方法的存根:

import AuditTrailClient from '<path-to-AuditTrailClient>';

const auditTrailClientStub = new AuditTrailClient();
// 可以直接调用存根方法并断言
auditTrailClientStub.method1();
expect(auditTrailClientStub.method1).toHaveBeenCalled();

补充:处理静态方法

如果原类包含静态方法,你可以在Mock工厂里额外遍历类自身的属性,为静态方法也生成存根:

jest.mock('<path-to-AuditTrailClient>', () => {
  const MockAuditTrailClient = function() {};
  
  // 处理原型方法
  Object.getOwnPropertyNames(AuditTrailClient.prototype).forEach(methodName => {
    if (methodName !== 'constructor') {
      MockAuditTrailClient.prototype[methodName] = jest.fn();
    }
  });

  // 处理静态方法
  Object.getOwnPropertyNames(AuditTrailClient).forEach(propName => {
    const prop = AuditTrailClient[propName];
    // 只处理静态函数,跳过prototype等特殊属性
    if (typeof prop === 'function' && propName !== 'prototype') {
      MockAuditTrailClient[propName] = jest.fn();
    }
  });

  return MockAuditTrailClient;
});

方法二:对已创建的实例批量生成存根

如果已经创建了类的实例,想要批量存根它的所有方法,可以用jest.spyOn遍历原型方法:

import AuditTrailClient from '<path-to-AuditTrailClient>';

const auditTrailClient = new AuditTrailClient();

// 遍历原型方法,逐个生成存根
Object.getOwnPropertyNames(AuditTrailClient.prototype).forEach(methodName => {
  if (methodName !== 'constructor') {
    jest.spyOn(auditTrailClient, methodName).mockImplementation(() => {});
    // 或者直接用mockReturnValue等自定义行为
    // jest.spyOn(auditTrailClient, methodName).mockReturnValue('mocked result');
  }
});

这种方式适合只需要存根单个实例的场景,不需要全局Mock整个类。

方法三:使用第三方库(可选)

如果你不想自己写遍历逻辑,可以使用第三方库jest-create-stub-instance,它专门实现了类似Sinon的功能:

npm install jest-create-stub-instance --save-dev

使用示例:

import createStubInstance from 'jest-create-stub-instance';
import AuditTrailClient from '<path-to-AuditTrailClient>';

const auditTrailClientStub = createStubInstance(AuditTrailClient);
// 所有方法自动成为jest.fn()存根
auditTrailClientStub.method2();
expect(auditTrailClientStub.method2).toHaveBeenCalled();

不过这种方式需要额外引入依赖,如果你更倾向原生Jest实现,优先选择前两种方法。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.22 00:45:16