javascript - Hvorfor fungerer ikke Jest.useFakeTimers i beforeAll-blokker?
Jeg ønsket å mocke timeout-funksjoner globalt, så jeg la til et kall til jest.useFakeTimers i en beforeAll-blokk. Da jeg kjørte testene mine, kjørte ikke jest.advanceTimersByTime den planlagte koden. Jeg brukte spioner for å bekrefte at mocken faktisk ble kalt. Jeg la imidlertid merke til at hvis jeg flyttet jest.advanceTimersByTime-kallet inn i testfunksjonen, eller inn i en beforeEach-blokk, så fungerte det.
Her er et enkelt eksempel som gjenskaper problemet.
describe('test', () => {
beforeEach(() => {
// Only beforeEach block works, NOT beforeAll
jest.useFakeTimers();
})
it('setTimeout calls callback', () => {
const callback = jest.fn();
setTimeout(() => {
callback()
}, 3000);
expect(callback).not.toHaveBeenCalled();
jest.advanceTimersByTime(3000);
expect(callback).toHaveBeenCalledTimes(1);
})
})
Jeg så ingenting i dokumentasjonen som forklarer dette. Jeg bruker Jest 26.6.2.
Svar #1
Det ser ut til at jest.useFakeTimers i dokumentasjonen erstatter setTimeout i produktkode, ikke i testkoden.
Svar #2
Kanskje du kan sjekke jest-oppsettfilen din (som setupFilesAfterEnv-konfigurasjonen). Si, hvis jeg legger de kodene i oppsettfilen, vil det da støte på problemet du nevnte ovenfor:
beforeEach(() => {
// reset to real timers
jest.useRealTimers();
})
Fordi som standardoppførsel blir callbacken til beforeEach alltid utført etter beforeAll, selv om den er definert før beforeAll.
