【问题标题】:Jest spy doesn't work in a different directory?Jest spy 在不同的目录中不起作用?
【发布时间】:2020-04-20 16:13:52
【问题描述】:

我正在尝试为发出 Web 请求的小型服务创建一些简单的单元测试,并且很难让 Jest 间谍正常工作。我发现jest.spyOn 功能会起作用,但这取决于测试文件的确切位置,这对我来说毫无意义。所以我有这样的东西:

src/getTimetableEventsAsync.js

const getTimetableEventsAsync = async (timetableSecrets, preferredUsername) => {
    console.log(got.get.toString());

    return got.get("someURL").json();

src/getTimetableEventsAsync.unit.test.js(可行)

const got = require('got');
const { getTimetableEventsAsync } = require('./getTimetableEventsAsync');

describe('getTimetableEvents', () => {
    it('Tests the mock', async () => {
        jest.spyOn(got, 'get').mockImplementation(() => {
            console.log('foo');
        });

        await getTimetableEventsAsync('', '');
    });
});

tests/getTimetableEventsAsync.unit.test.js(这不起作用)

const got = require('got');
const { getTimetableEventsAsync } = require('../src/getTimetableEventsAsync');

describe('getTimetableEvents', () => {
    it('Tests the mock', async () => {
        jest.spyOn(got, 'get').mockImplementation(() => {
            console.log('foo');
        });

        await getTimetableEventsAsync('', '');
    });
});

令我困惑的是两个测试文件的行为不同。有效的日志:

console.log src/getTimetableEventsAsync.js:11
     function mockConstructor() {
             return fn.apply(this, arguments);
           }
   console.log src/mocks.unit.test.js:7
     foo

不工作的日志:

console.log src/getTimetableEventsAsync.js:11
      (url, options) => got(url, { ...options, method })

所以当我的测试文件在我的tests 目录中时,jest.spyOn 显然不起作用,但相同的代码在我的src 目录中可以正常工作。 Jest 始终在根目录下运行,我可以让这些测试在同一个测试运行中运行,但结果不同。

谁能告诉我这里缺少什么?为什么我的测试不能在tests 目录中运行?理想情况下,我希望它们在这里运行,因为从任何部署等中排除这些文件要简单得多。

因此,在 tests/gettimetableEventsAsync.unit.test.js 中检查以确保间谍已经工作,这表明在本地测试中它工作正常,尽管在不匹配之后立即工作。

 console.log tests/getTimetableEventsAsync.unit.test.js:10
      function mockConstructor() {
              return fn.apply(this, arguments);
            }

   console.log src/getTimetableEventsAsync.js:11
      (url, options) => got(url, { ...options, method })

【问题讨论】:

  • 在调用 spyOn 后,您能否在 tests/getTimetableEventsAsync.unit.test.js 中检查 got.get 是一个间谍? getTimetableEventsAsync.js 中有const got = require('got') 吗?你能提供一种方法来复制这个问题吗?一种可能的解释是 got 在 src/getTimetableEventsAsync.js 和 tests/getTimetableEventsAsync.unit.test.js 中不一样(尝试将两者都分配给 global 并检查它们是否为 ===)。另一个是间谍没有按预期设置。发布的任何内容都无法说明为什么会发生这种情况。
  • @EstusFlask 我在第一部分添加了一些额外的信息。似乎我的global 在测试之间被空白,所以我无法验证这一点。我只是想尝试获得一个小的复制品。
  • @EstusFlask 好的,在尝试复制时,我有一个启示的时刻。其他人设置了这个项目,在src 中有一个package.json,其中包括got。然而,在根目录下还有一个 package.json,它没有 got(只有 CDK 的东西)。所以我猜这会导致一些 node_modules 问题。我仍然会尝试复制。
  • 是的,这就是我对 got is not the same 的意思。你不能再看了,肯定是这样的。如果您出于某种原因需要在 src/node_modules 中保留单独的 got ,请像 require('../src/node_modules/got') 一样导入它以模拟它。
  • @EstusFlask 你想添加一个答案,这样我就可以接受它。

标签: javascript unit-testing jestjs


【解决方案1】:

设置间谍时未设置的一个常见原因是它设置在错误的对象上。如果导入的包发生这种情况,这通常意味着包在node_modules 层次结构中重复。

在这种情况下,src/getTimetableEventsAsync.js 中的 gottests/getTimetableEventsAsync.unit.test.js 中的 got 不是同一个对象。看起来,src 中有一个嵌套项目,它有自己的node_modules

解决方案是在测试中模拟正确的 got 对象:

const got = require('../src/node_modules/got');
...
jest.spyOn(got, 'get').mockImplementation(() => {...});

或对包进行重复数据删除,例如删除src 中的嵌套项目或从中删除重复的依赖项,如got,因此src 中的require('got') 将从根node_modules 导入包。

【讨论】:

    猜你喜欢
    • 2015-11-18
    • 1970-01-01
    • 2016-11-04
    • 2017-04-27
    • 1970-01-01
    • 1970-01-01
    • 2019-06-22
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多