Jest无法模拟Node.js模块中existsObject函数求助
解决Jest模拟Google Storage existsObject函数失效的问题
你的问题出在mock执行时机、导出结构匹配以及异步函数mock方式这几个核心点上,以下是具体修正方案:
问题根源
- mock时机错误:你在测试用例内部调用
jest.mock,但此时existsPrivatekey模块已完成导入,真实的existsObject函数已经被加载,mock无法覆盖原有引用。 - 导出结构不匹配:
storage.js导出的是包含多个函数的对象,你直接返回单个函数作为mock,和原模块的导出结构不一致,导致测试代码无法正确识别mock函数。 - 异步函数mock方式错误:
existsObject是异步函数,返回Promise,使用mockReturnValue会直接返回同步值,无法被await正确处理,必须用mockResolvedValue模拟异步返回。
修正后的测试代码
import { jest } from '@jest/globals'; // 先mock目标模块,再导入待测试函数,确保mock生效 jest.mock('../../functions/storage.js', () => ({ existsObject: jest.fn() })); import existsPrivatekey from '../../helpers/existsPrivatekey.js'; // 导入mock的函数,方便在测试用例中动态修改返回值 import { existsObject } from '../../functions/storage.js'; describe('[existsPrivatekey] Check if exists privatekey', () => { it('Exists privatekey in Storage', async () => { // 模拟异步返回true existsObject.mockResolvedValue(true); const result = await existsPrivatekey('meudominio.com.br', 'bucket'); expect(result).toBe(true); // 验证函数被正确调用,参数符合预期(替换为实际的config.certificates.private值) expect(existsObject).toHaveBeenCalledWith('meudominio.com.br/private-key.pem'); }); it('Not Exists privatekey in Storage', async () => { // 重置mock,避免和上一个用例的状态冲突 existsObject.mockReset(); // 模拟异步返回false existsObject.mockResolvedValue(false); const result = await existsPrivatekey('meudominio.com.br', 'bucket'); expect(result).toBe(false); }); });
额外优化建议
- 如果测试需要依赖
config模块的配置值,建议同时mock配置模块,避免测试环境受真实配置影响:jest.mock('../config/config.js', () => ({ certificates_dir: '/test-cert-dir', certificates: { private: 'private-key.pem' }, bucket: 'test-bucket' })); - 若要测试本地文件检查分支,需mock
fs.existsSync,避免依赖真实文件系统:import fs from 'node:fs'; jest.spyOn(fs, 'existsSync').mockReturnValue(true); // 根据测试场景切换为false
内容的提问来源于stack exchange,提问作者Alisson Acioli
相关产品推荐
相关产品推荐

