bug: `resetAllMocks` messes up `runAllTimers` when using `useFakeTimers`
Do you want to request a feature or report a bug? Bug
What is the current behavior?
When using useFakeTimers, running resetAllMocks messes up runAllTimers in the second test (it does not advance the timer) and the test times out (fails).
If the current behavior is a bug, please provide the steps to reproduce and
either a repl.it demo through https://repl.it/languages/jest or a minimal
repository on GitHub that we can yarn install and yarn test.
https://repl.it/repls/CarelessNormalAssassinbug
What is the expected behavior?
resetAllMocks should indeed reset the calls instances of the setTimeout mock, but runAllTimers should still work as expected and complete the setTimeout
Please provide your exact Jest configuration and mention your Jest, node, yarn/npm version and operating system. Jest v22.1.4 Node v9.3.0 Yarn v1.3.2 Mac OS X 10.12.6
In your code you've called the jest.useFakeTimers on a beforeAll.
If you replace that with beforeEach and your afterAll with afterEach, it works (https://repl.it/@Rafazelramalho/CarelessNormalAssassinbug)
Do you really require it to be beforeAll and afterAll?
Yes, the current workaround is to useFakeTimers on beforeEach, but that's not the expected behavior.
If I understand correctly, useFakeTimers mocks setTimeout and the like with Jest mock functions, so they're supposed to act like all other jest.fn() and jest.spyOn() mocks.
In that sense, running resetAllMocks should reset the calls tracking of the mocks, but keep the actual mock intact.
So, the expected behavior would be to run useFakeTimers only once and reset the mocks after each test. In which case runAllTimers should have worked in my setup.
This is also based on what we see in the docs:
https://facebook.github.io/jest/docs/en/timer-mocks.html
If the docs would have noted to run it on beforeEach, I wouldn't have a problem with that.
But since I followed the examples and that led me to broken code, I consider it a bug.
@SimenB would you suggest updating the docs or looking into this particular issue?
I was not aware that we made setTimeout and friends into spies - I'm not sure how that will work once we start using Lolex (#5165).
So for now I'd say we should document the current behaviour. Thoughts @cpojer @thymikee?
@SimenB haven't thought about that either. Would be quite a breaking change with Lolex.
FWIW I've set up the Lolex branch to spy on the methods, so no longer breaking in that regard
My current thinking is that we should remove the mocks from the timing functions when using fake timers. Easy enough for people to do jest.spyOn(global, 'setTimeout') if they want.
it’s a surprise to me that jest. useFakeTimers could be clear by jest.resetAllMocks, no document for it and I spent one hour to figure out the root cause. If this is the rule, could you update related documents as well?
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.
Modern timers (available jest 26, default jest 27) are not affected by this. PR welcome documenting this for legacy timers, tho
@SimenB I would love to give it a try. Can I handle this ?
I would love to give it a try. Can I handle this ?
I would like to work on this issue
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.
This issue was closed because it has been stalled for 30 days with no activity. Please open a new issue if the issue is still relevant, linking to this one.
This issue has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs. Please note this issue tracker is not a help forum. We recommend using StackOverflow or our discord channel for questions.