在其他函数中调用时,Jest模拟函数不起作用

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了在其他函数中调用时,Jest模拟函数不起作用相关的知识,希望对你有一定的参考价值。

我相信我对javascript的理解有些根本错误。

在文件abc.js中,我有代码

export function returnBoolean() {
  return true;
}

export function output() {
  return returnBoolean();
}

在测试中,我做到了

import * as abc from "../abc";

it("test", () => {
  abc.returnBoolean = jest.fn();
  abc.returnBoolean.mockReturnValue(false);
  expect(abc.returnBoolean()).toBe(false); // This is success
  expect(abc.output()).toBe(false); // This failed because return is true
});

我不知道为什么abc.output()回归是true

我真的很困惑。任何想法都非常感激。谢谢!

答案

output()returnBoolean()都在同一个文件中,output()直接调用returnBoolean()

模拟returnBoolean()的模块导出对output()没有任何影响,因为它没有使用模块,它直接调用returnBoolean()

就像felixmosh所说的那样,将returnBoolean()移动到另一个模块是一种能够在returnBoolean()内模仿对output()的调用的方法。

另一种方法是简单地将模块导入自身并使用模块在returnBoolean()中调用output(),如下所示:

// import the module back into itself
import * as abc from './abc';

export function returnBoolean() {
  return true;
}

export function output() {
  return abc.returnBoolean(); // use the module to call returnBoolean()
}

使用这种方法,您的单元测试应该可行。

另一答案

想想看,无论何时导入abc模块,都会声明该模块中的所有函数,因此,output函数将“绑定”到原始的returnBoolean。

您的模拟不适用于原始功能。

你有2个选择:

  1. 如果returnBoolean可以在一个单独的模块上,您将能够使用jest's mocking mechnisem
  2. 如果您能够更改output方法的接口,那么它将能够从模块外部获取returnBoolean。然后你就可以传递给它,jest.fn()并对它做出你的期望。

以上是关于在其他函数中调用时,Jest模拟函数不起作用的主要内容,如果未能解决你的问题,请参考以下文章

为啥直接在构造函数中创建 ES6 类的实例时 Jest 的 toThrow 不起作用?

当模拟点击调用调用 promise 的函数时,使用 React 的 Jest 和 Enzyme 进行测试

使用 jest 模拟 react-router-dom 钩子不起作用

为啥我的函数在调用时不起作用? [关闭]

在 jest testrunner 中运行时,Mongoose 模型函数超时

如何在每次测试之前重置 Jest 模拟函数调用计数