使用玩笑监视非导出的 node.js 函数,但未按预期工作

Raj*_*ram 5 javascript unit-testing node.js jestjs

我试图通过“开玩笑”和“重新布线”来模拟一个非导出的函数。

在这里,我试图模拟“iAmBatman”(无双关语)但它没有被导出。

所以我使用重新布线,它工作得很好。但是 jest.mock 没有按预期工作。

我在这里遗漏了什么还是有一种简单的方法可以实现相同的目标?

jest 给出的错误信息是:

Cannot spy the property because it is not a function; undefined given instead

service.js

function iAmBatman() {
    return "Its not who I am underneath";
}

function makeACall() {
    service.someServiceCall(req => {
        iAmBatman();
    });
    return "response";
}

module.export = {
    makeACall : makeACall;
}
Run Code Online (Sandbox Code Playgroud)

jest.js

const services = require('./service');
const rewire = require('rewire');
const app = rewire('./service');
const generateDeepVoice = app.__get__('iAmBatman'); 

const mockDeepVoice = jest.spyOn(services, generateDeepVoice);

mockDeepVoice.mockImplementation(_ => {
    return "But what I do that defines me";
});

describe(`....', () => {
    test('....', done => {
        services.makeACall(response, () => {

        });
    });
})
Run Code Online (Sandbox Code Playgroud)

Ren*_*man 7

目前尚不完全清楚您的目标是什么,但是如果您查看jest.spyOn 的文档,您会发现它采用 amethodName作为第二个参数,而不是方法本身:

jest.spyOn(object, methodName)
Run Code Online (Sandbox Code Playgroud)

这解释了您的错误:您没有给出函数名称,而是给出了函数本身。在这种情况下, usingjest.spyOn(services, 'iAmBatman')不起作用,因为iAmBatman未导出,因此services.iAmBatman未定义。

幸运的是,您不需要spyOn,因为您可以简单地创建一个新的模拟函数,然后使用 rewire 注入它,__set__如下所示:

service.someServiceCall(请注意,我删除了第一个文件中的未定义内容,并修复了一些拼写错误和冗余导入)

jest.spyOn(object, methodName)
Run Code Online (Sandbox Code Playgroud)
// service.js

function iAmBatman() {
    return "Its not who I am underneath";
}

function makeACall() {
    return iAmBatman();
}

module.exports = {
    makeACall: makeACall
}
Run Code Online (Sandbox Code Playgroud)

另一种选择是iAmBatman在单独的模块中重构代码,然后使用 Jest 模拟模块导入。请参阅的文档jest.mock