Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We鈥檒l occasionally send you account related emails.

Already on GitHub? Sign in to your account

jest.useFakeTimers() does not work with whatwg-fetch>=3.1.0 #11103

Open
ntucker opened this issue Feb 22, 2021 · 12 comments
Open

jest.useFakeTimers() does not work with whatwg-fetch>=3.1.0 #11103

ntucker opened this issue Feb 22, 2021 · 12 comments

Comments

@ntucker
Copy link

ntucker commented Feb 22, 2021

馃悰 Bug Report

Due to this change: JakeChampion/fetch#575 using whatwg-fetch to make fetch work in node and then trying to run timers will cause the fetches to never resolve.

To Reproduce

Steps to reproduce the behavior:

  • use whatwg-fetch
  • nock a response
  • jest.useFakeTimers()
  • fetch
  • advance time

Expected behavior

The promise should resolve. Instead, the nock response gets called - but the then clause of the promise never gets run

Link to repl or repo (highly encouraged)

reactive/data-client#553

envinfo


  System:
    OS: Linux 4.19 Ubuntu 20.04 LTS (Focal Fossa)
    CPU: (16) x64 Intel(R) Core(TM) i7-10875H CPU @ 2.30GHz
  Binaries:
    Node: 14.8.0 - ~/.nvm/versions/node/v14.8.0/bin/node
    Yarn: 1.22.5 - /usr/bin/yarn
    npm: 7.5.4 - ~/.nvm/versions/node/v14.8.0/bin/npm
  npmPackages:
    jest: ^26.6.3 => 26.6.3 

@CrOrc
Copy link

CrOrc commented Feb 22, 2021

You have to add
jest.runOnlyPendingTimers()
or
jest.runAllTimers()
after advancing time to resolve your issue.

@ntucker
Copy link
Author

ntucker commented Feb 22, 2021

runOnlyPendingTimers() didn't change anything. runAllTimers() caused infinite loop (due to other timers in my code).

Is there some sort of debug thing for jest mock timers where I can see the current timers in flight?

Based on the probing it seems like the whatwg-fetch addition of setTimeout is somehow not being mocked at all.

@ntucker
Copy link
Author

ntucker commented Feb 22, 2021

The problem is the setTimeout isn't called until the promise is resolved...this must be BEFORE runOnlyPendingTimers is run, otherwise it doesn't advance that timer.

However, since this is internal to whatwg-fetch library, I have no way of hooking code up to after the settimeout is called, since there is no promise resolution until that part runs.

@CrOrc
Copy link

CrOrc commented Feb 28, 2021

Call
jest.runOnlyPendingTimers()
after calling
jest.advanceTimersByTime

This way timers with setTimeout(fn,0) will be called and you promise will resolve.

@ntucker
Copy link
Author

ntucker commented Mar 1, 2021

@CrOrc you already said that, and I tried to explain why that doesn't work. you can see this in my PR here reactive/data-client#553

Find any of the newly failing tests and add that - it doesn't work. I explained why in the comment above.

@joselcvarela
Copy link

I had hard time using whatwg-fetch with useFakeTimers. My suggestion is to use unfetch.
The reason is whatwg-fetch relies on setTimeout and when you are in async mode it's not easy to handle timers functions.

@joselcvarela
Copy link

This solved to mock frontend web API.
Although, I still have the issue on node with node-fetch.

@davazp
Copy link

davazp commented Oct 25, 2021

I am experiencing the same issue, but it seems to work with the legacy useFakeTimers('legacy'). Did the legacy implementation had a special case for 0 ms timeouts so they were run without calling jest.runAllTimers() ?

If that is the case, perhaps the same special case could be introduced in the new implementation?

@github-actions
Copy link

This issue is stale because it has been open for 1 year with no activity. Remove stale label or comment or this will be closed in 30 days.

@github-actions github-actions bot added the Stale label Feb 17, 2023
@borodean
Copy link

Still relevant.

@github-actions github-actions bot removed the Stale label Feb 17, 2023
@markuskullberg-sanoma
Copy link

Any updates on this? Seems like devs are moving away from jest-fetch-mock to whatwg-fetch + msw/nock, but this seems to me like a blocker. Any good workarounds? Not sure what I feel about using unfetch over whatwg-fetch.

Copy link

github-actions bot commented May 4, 2024

This issue is stale because it has been open for 1 year with no activity. Remove stale label or comment or this will be closed in 30 days.

@github-actions github-actions bot added the Stale label May 4, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

7 participants