【问题标题】:What is the meaning of UnhandledPromiseRejectionWarning in jest tests?开玩笑测试中 UnhandledPromiseRejectionWarning 的含义是什么?
【发布时间】:2019-10-10 23:28:09
【问题描述】:

ant 测试以下模块index.ts

async function theFunctionFail() {
  return await fail();
}

async function theFunctionSucceed() {
  return await succeed();
}

async function fail() {
  throw new Error();
}

async function succeed() {
  return "a";
}

export { theFunctionFail, theFunctionSucceed };

使用测试index.test.ts

import { theFunctionFail, theFunctionSucceed } from "../index";

it('theFunctionFail', () => {
  expect(theFunctionFail()).rejects;
});

输出中的UnhandledPromiseRejectionWarning 是什么

(node:10515) UnhandledPromiseRejectionWarning: Error
(node:10515) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 2)
(node:10515) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.
 PASS  src/__tests__/index.test.ts
  ✓ theFunctionFail (6ms)

Test Suites: 1 passed, 1 total
Tests:       1 passed, 1 total
Snapshots:   0 total
Time:        1.806s
Ran all test suites.

参考?将 expect(theFunctionFail()).rejects 包装在 try-catch(err) 块中并不能避免我认为值得修复的警告。

为什么测试没有失败?/我怎样才能让测试失败?如果我的测试发现了一个严重的缺陷,我的理解应该不会成功。

我正在使用带有react-scripts 的 Typescript 和 Jest 24.7.1。

【问题讨论】:

    标签: javascript typescript unit-testing promise jestjs


    【解决方案1】:

    此警告指的是测试中发生了未处理的错误。真正的问题是你的测试没有测试任何东西——有一个没有匹配器的expect。应该是这样的:

    return expect(theFunctionFail()).rejects.toEqual(new Error());
    

    查看 .rejects 的 Jest 文档:https://jestjs.io/docs/en/tutorial-async#rejects

    注意:也可以使用try/catch,但您必须像这样使用await

    it('theFunctionFail', async () => {
      expect.assertions(1);
      try {
        await theFunctionFail();
      } catch (err) {
        expect(err).toEqual(new Error());
      }
    });
    

    或者返回异步函数并捕获错误(确保你返回函数):

    it('theFunctionFail', () => {
      expect.assertions(1);
      return theFunctionFail().catch(err => {
        expect(err).toEqual(new Error());
      });
    });
    

    expect.assertions(number) 是确保在测试异步行为时调用所有 expects 的好方法。

    此外,如果您添加错误消息,例如new Error('oh no!'),你肯定会知道你捕捉到了正确的错误,并且会让调试变得更容易。

    【讨论】:

    • 有没有办法更容易找到有问题的测试?我可以做一个临时的猴子补丁吗?对于这个项目,我有超过 1000 个,并且错误与输出中显示的位置不一致。
    • 听起来您的问题可能出在您的代码中,而不是您的测试中。我会确保你的代码没有任何没有.catch 的承诺,或者try/catch 之外的任何awaits
    • 对。如果不煞费苦心地单独运行每个测试,我只是不知道如何在代码中找到它。
    • 嗨,想知道您是否找到了识别违规测试的方法?或者在你当地的笑话中重现这个?我们的笑话只在我们的 CI 管道中退出,在本地一切似乎都很好
    【解决方案2】:

    在控制台中不产生 UnhandledPromiseRejectionWarning 的最干净的解决方案是使用 jest 的 expect.toThrow() 函数。

    import { theFunctionFail, theFunctionSucceed } from "../index";
    
    it('theFunctionFail', () => {
      expect(theFunctionFail()).rejects.toThrow();
    });
    

    您可以再次尝试匹配特定错误。例如。如果:

    async function fail() {
      throw new Error('Something failed');
    }
    

    那么,你会测试:

    it('theFunctionFail', () => {
      expect(theFunctionFail()).rejects.toThrow(Error('Something failed'));
    });
    

    【讨论】:

      猜你喜欢
      • 2020-11-22
      • 2018-06-02
      • 2017-11-01
      • 1970-01-01
      • 2019-09-25
      • 2020-02-06
      • 2020-03-25
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多