Jest未使用Mock却调用实际实现问题求助
Jest spyOn 不生效的解决办法
问题出在模块内部函数调用的引用上——你的retrieveDataFromMongo直接调用的是模块内定义的connectToMongo函数声明,而Jest的spyOn仅能mock模块导出对象上的函数引用,模块内部的直接调用不会被拦截,所以实际函数依然会执行。
下面是三种可行的解决办法:
方法一:修改模块内部调用引用(最直接)
将connectToMongo改为变量赋值形式,让模块内部调用和导出的是同一个引用:
原模块代码修改:
import {MongoClient} from 'mongo'; // 改为变量赋值的函数表达式 export const connectToMongo = async (): Promise<MongoClient> => { ... return MongoClient.connect('connstring'); } async retrieveDataFromMongo() { // 这里调用的是导出的变量引用,而非原始函数声明 const client = await connectToMongo(); // 使用client逻辑 }
测试代码无需改动,此时jest.spyOn(my_module, 'connectToMongo')会替换掉模块内部使用的引用,mock生效。
方法二:使用jest.mock直接mock模块导出
如果不想修改原代码结构,用jest.mock覆盖模块的导出函数:
测试代码修改:
import * as my_module from '../src/mymodule'; import {mock} from 'jest-mock-extended'; const mockedMongoClient = mock<MongoClient>(); // 用jest.mock覆盖模块导出,保留其他原始导出 jest.mock('../src/mymodule', () => { const originalModule = jest.requireActual('../src/mymodule'); return { ...originalModule, connectToMongo: jest.fn().mockResolvedValue(mockedMongoClient) }; }); describe('MyMongoTests', () => { it.only('test1', async() => { await my_module.retrieveDataFromMongo(...); // 验证mock函数被调用 expect(my_module.connectToMongo).toHaveBeenCalled(); }); });
方法三:针对类成员方法的mock(如果是类场景)
如果retrieveDataFromMongo是类的成员函数,把connectToMongo也改为类方法,然后mock实例的方法:
原类代码:
import {MongoClient} from 'mongo'; export class MongoService { async connectToMongo(): Promise<MongoClient> { return MongoClient.connect('connstring'); } async retrieveDataFromMongo() { const client = await this.connectToMongo(); // 使用client逻辑 } }
测试代码:
import {MongoService} from '../src/mymodule'; import {mock} from 'jest-mock-extended'; const mockedMongoClient = mock<MongoClient>(); describe('MyMongoTests', () => { let service: MongoService; beforeEach(() => { service = new MongoService(); // spyOn类实例的connectToMongo方法 jest.spyOn(service, 'connectToMongo').mockResolvedValue(mockedMongoClient); }); it.only('test1', async() => { await service.retrieveDataFromMongo(...); expect(service.connectToMongo).toHaveBeenCalled(); }); });
内容的提问来源于stack exchange,提问作者Phate
相关产品推荐
相关产品推荐

