Jest: Timeout - Async callback was not invoked within the 5000ms timeout not showing where it failed

Created on 25 Apr 2020  ·  2Comments  ·  Source: facebook/jest

Bug Report

Jest is not showing which on which line the timeout is happening.

To Reproduce

https://repl.it/@evandrocoan/AttractiveShabbyBusinesses

const sum = require('./sum');

test('Timeout on the wrong place...', async () => {
  expect(sum(1, 2)).toBe(3);
  await new Promise(function(resolve) {});
});

test.each([
  [`Timeout on the wrong place...`, 1],
  [`Tests passing normally now on forwards...`, 2],
])(
  `%s`,
  async function(name, index) {
    expect(sum(1, 2)).toBe(3);
    if(index === 1) {
      await new Promise(function(resolve) {});      
    }
  }
);

Actual behavior

  ● Timeout on the wrong place...

    : Timeout - Async callback was not invoked within the 5000ms timeout specified 
by jest.setTimeout.Timeout - Async callback was not invoked within the 5000ms timeout 
specified by jest.setTimeout.Error:

      1 | const sum = require('./sum');
      2 | 
    > 3 | test('Timeout on the wrong place...', async () => {
        | ^
      4 |   expect(sum(1, 2)).toBe(3);
      5 |   await new Promise(function(resolve) {});
      6 | });

      at new Spec (node_modules/jest-jasmine2/build/jasmine/Spec.js:116:22)
      at Object.<anonymous> (sum.test.js:3:1)

Expected behavior

  ● Timeout on the wrong place...

    : Timeout - Async callback was not invoked within the 5000ms timeout specified by 
jest.setTimeout.Timeout - Async callback was not invoked within the 5000ms timeout 
specified by jest.setTimeout.Error:

      3 | test('Timeout on the wrong place...', () => {
      4 |   expect(sum(1, 2)).toBe(3);
    > 5 |   await new Promise(function(resolve) {});
        |   ^
      6 | });
      7 | 
      8 | test.each([

envinfo

 npx envinfo --preset jest
npx: installed 1 in 3.299s

  System:
    OS: Linux 4.15 Debian GNU/Linux 9 (stretch) 9 (stretch)
    CPU: (4) x64 Intel(R) Xeon(R) CPU @ 2.30GHz
  Binaries:
    Node: 12.16.2 - /usr/local/bin/node
    Yarn: 1.22.4 - /usr/local/bin/yarn
    npm: 6.14.4 - /usr/local/bin/npm
  npmPackages:
    jest: ^24.9.0 => 24.9.0 

Related:

  1. https://github.com/facebook/jest/issues/7817 - Asynchronous operations not stopped in tests?
  2. https://github.com/facebook/jest/issues/8384 - Async callback was not invoked within the 5000ms timeout - Error Message Improvement
  3. https://github.com/facebook/jest/issues/8284 - before handlers timing out looks like the test timing out
  4. https://github.com/facebook/jest/issues/9527 - beforeAll() executed in parallel with test case in case of timeout
Bug Report Needs Repro Needs Triage

Most helpful comment

For anyone experiencing the same issue with jest puppeteer tests, I found a workaround to make the failure message display the line where it's timing out:

  1. Increase the global default Jest timeout to something large (anywhere in the test):
jest.setTimeout(30000);
  1. Then, inside the test, set an explicit shorter timeout duration on the waitFor line which is timing out:
await page.waitForSelector('.Foo', { timeout: 5000 });

Now, my failure message looks like this:

    TimeoutError: waiting for selector ".Foo" failed: timeout 5000ms exceeded

      42 | 
      43 |              // wait for the Foo button
    > 44 |              await page.waitForSelector('.Foo', { timeout: 5000 });
         |                         ^
      45 |              await page.click('.Foo');
      46 | 

Note, the timeout duration inside the test has to be a shorter than the global timeout, otherwise it has no effect.

Edit: Caveat - this seems to work for page.waitForSelector but not page.goto in my experience

All 2 comments

For anyone experiencing the same issue with jest puppeteer tests, I found a workaround to make the failure message display the line where it's timing out:

  1. Increase the global default Jest timeout to something large (anywhere in the test):
jest.setTimeout(30000);
  1. Then, inside the test, set an explicit shorter timeout duration on the waitFor line which is timing out:
await page.waitForSelector('.Foo', { timeout: 5000 });

Now, my failure message looks like this:

    TimeoutError: waiting for selector ".Foo" failed: timeout 5000ms exceeded

      42 | 
      43 |              // wait for the Foo button
    > 44 |              await page.waitForSelector('.Foo', { timeout: 5000 });
         |                         ^
      45 |              await page.click('.Foo');
      46 | 

Note, the timeout duration inside the test has to be a shorter than the global timeout, otherwise it has no effect.

Edit: Caveat - this seems to work for page.waitForSelector but not page.goto in my experience

Was this page helpful?
0 / 5 - 0 ratings