diff --git a/e2e/__tests__/__snapshots__/showConfig.test.ts.snap b/e2e/__tests__/__snapshots__/showConfig.test.ts.snap index 4c7058473159..e08e1c804615 100644 --- a/e2e/__tests__/__snapshots__/showConfig.test.ts.snap +++ b/e2e/__tests__/__snapshots__/showConfig.test.ts.snap @@ -66,7 +66,7 @@ exports[`--showConfig outputs config info and exits 1`] = ` ], "testRegex": [], "testRunner": "<>/jest-circus/runner.js", - "timers": "real", + "timers": {}, "transform": [ [ "\\\\.[jt]sx?$", diff --git a/e2e/fake-promises/asap/package.json b/e2e/fake-promises/asap/package.json index 0f50640514e1..8592ccefa3ef 100644 --- a/e2e/fake-promises/asap/package.json +++ b/e2e/fake-promises/asap/package.json @@ -1,9 +1,9 @@ { "jest": { - "timers": "fake", "setupFiles": [ "/fake-promises" ], - "testEnvironment": "node" + "testEnvironment": "node", + "timers": {"strategy": "modern"} } } diff --git a/e2e/fake-promises/immediate/package.json b/e2e/fake-promises/immediate/package.json index 0f50640514e1..8592ccefa3ef 100644 --- a/e2e/fake-promises/immediate/package.json +++ b/e2e/fake-promises/immediate/package.json @@ -1,9 +1,9 @@ { "jest": { - "timers": "fake", "setupFiles": [ "/fake-promises" ], - "testEnvironment": "node" + "testEnvironment": "node", + "timers": {"strategy": "modern"} } } diff --git a/e2e/fake-time/legacy/from-config/package.json b/e2e/fake-time/legacy/from-config/package.json index 3d94760ca58b..37c77e1275e6 100644 --- a/e2e/fake-time/legacy/from-config/package.json +++ b/e2e/fake-time/legacy/from-config/package.json @@ -1,6 +1,6 @@ { "jest": { - "timers": "legacy", - "testEnvironment": "node" + "testEnvironment": "node", + "timers": {"strategy": "legacy"} } } diff --git a/e2e/fake-time/legacy/from-jest-object/__tests__/test.js b/e2e/fake-time/legacy/from-jest-object/__tests__/test.js index 982b23cbf809..06ce552135d0 100644 --- a/e2e/fake-time/legacy/from-jest-object/__tests__/test.js +++ b/e2e/fake-time/legacy/from-jest-object/__tests__/test.js @@ -8,7 +8,7 @@ 'use strict'; test('fake timers', () => { - jest.useFakeTimers('legacy'); + jest.useFakeTimers({strategy: 'legacy'}); expect(() => jest.setSystemTime(0)).toThrow( 'setSystemTime is not available when not using modern timers', diff --git a/e2e/fake-time/legacy/requestAnimationFrame/__tests__/test.js b/e2e/fake-time/legacy/requestAnimationFrame/__tests__/test.js index 42c638bbf191..4b94d5c9514d 100644 --- a/e2e/fake-time/legacy/requestAnimationFrame/__tests__/test.js +++ b/e2e/fake-time/legacy/requestAnimationFrame/__tests__/test.js @@ -10,7 +10,7 @@ 'use strict'; test('requestAnimationFrame', () => { - jest.useFakeTimers('legacy'); + jest.useFakeTimers({strategy: 'legacy'}); let frameTimestamp = -1; requestAnimationFrame(timestamp => { frameTimestamp = timestamp; diff --git a/e2e/fake-time/modern/from-config/package.json b/e2e/fake-time/modern/from-config/package.json index 8d831ccf6947..7512977b8010 100644 --- a/e2e/fake-time/modern/from-config/package.json +++ b/e2e/fake-time/modern/from-config/package.json @@ -1,6 +1,6 @@ { "jest": { - "timers": "fake", - "testEnvironment": "node" + "testEnvironment": "node", + "timers": {"strategy": "modern"} } } diff --git a/e2e/fake-time/modern/requestAnimationFrame/__tests__/test.js b/e2e/fake-time/modern/requestAnimationFrame/__tests__/test.js index 17e29447c67a..776036011cf8 100644 --- a/e2e/fake-time/modern/requestAnimationFrame/__tests__/test.js +++ b/e2e/fake-time/modern/requestAnimationFrame/__tests__/test.js @@ -10,7 +10,8 @@ 'use strict'; test('requestAnimationFrame', () => { - jest.useFakeTimers('modern'); + jest.useFakeTimers(); + let frameTimestamp = -1; requestAnimationFrame(timestamp => { frameTimestamp = timestamp; diff --git a/e2e/modern-fake-timers/from-config/package.json b/e2e/modern-fake-timers/from-config/package.json index 48517c65a548..7512977b8010 100644 --- a/e2e/modern-fake-timers/from-config/package.json +++ b/e2e/modern-fake-timers/from-config/package.json @@ -1,6 +1,6 @@ { "jest": { - "timers": "modern", - "testEnvironment": "node" + "testEnvironment": "node", + "timers": {"strategy": "modern"} } } diff --git a/e2e/modern-fake-timers/from-jest-object/__tests__/test.js b/e2e/modern-fake-timers/from-jest-object/__tests__/test.js index 6fd28535c2bd..fd294d2323e3 100644 --- a/e2e/modern-fake-timers/from-jest-object/__tests__/test.js +++ b/e2e/modern-fake-timers/from-jest-object/__tests__/test.js @@ -8,7 +8,7 @@ 'use strict'; test('fake timers with number argument', () => { - jest.useFakeTimers('modern'); + jest.useFakeTimers(); jest.setSystemTime(0); @@ -20,7 +20,7 @@ test('fake timers with number argument', () => { }); test('fake timers with Date argument', () => { - jest.useFakeTimers('modern'); + jest.useFakeTimers(); jest.setSystemTime(new Date(0)); diff --git a/e2e/set-immediate/package.json b/e2e/set-immediate/package.json index 1cb610cba16b..7512977b8010 100644 --- a/e2e/set-immediate/package.json +++ b/e2e/set-immediate/package.json @@ -1,6 +1,6 @@ { "jest": { "testEnvironment": "node", - "timers": "fake" + "timers": {"strategy": "modern"} } } diff --git a/e2e/timer-reset-mocks/with-reset-mocks/package.json b/e2e/timer-reset-mocks/with-reset-mocks/package.json index 7c8e0b6b4210..bf9c895e1ef3 100644 --- a/e2e/timer-reset-mocks/with-reset-mocks/package.json +++ b/e2e/timer-reset-mocks/with-reset-mocks/package.json @@ -1,7 +1,7 @@ { "jest": { - "testEnvironment": "node", "resetMocks": true, - "timers": "fake" + "testEnvironment": "node", + "timers": {"strategy": "modern"} } } diff --git a/e2e/timer-reset-mocks/with-reset-mocks/timerWithMock.test.js b/e2e/timer-reset-mocks/with-reset-mocks/timerWithMock.test.js index d45bb7b54ed5..69cfea365703 100644 --- a/e2e/timer-reset-mocks/with-reset-mocks/timerWithMock.test.js +++ b/e2e/timer-reset-mocks/with-reset-mocks/timerWithMock.test.js @@ -8,7 +8,6 @@ describe('timers', () => { it('should work before calling resetAllMocks', () => { const f = jest.fn(); - jest.useFakeTimers(); setTimeout(f, 0); jest.runAllTimers(); expect(f).toHaveBeenCalledTimes(1); diff --git a/e2e/timer-use-real-timers/package.json b/e2e/timer-use-real-timers/package.json index 1cb610cba16b..7512977b8010 100644 --- a/e2e/timer-use-real-timers/package.json +++ b/e2e/timer-use-real-timers/package.json @@ -1,6 +1,6 @@ { "jest": { "testEnvironment": "node", - "timers": "fake" + "timers": {"strategy": "modern"} } } diff --git a/packages/jest-circus/src/legacy-code-todo-rewrite/jestAdapter.ts b/packages/jest-circus/src/legacy-code-todo-rewrite/jestAdapter.ts index dc8059b39acf..f37bb6546e03 100644 --- a/packages/jest-circus/src/legacy-code-todo-rewrite/jestAdapter.ts +++ b/packages/jest-circus/src/legacy-code-todo-rewrite/jestAdapter.ts @@ -38,10 +38,10 @@ const jestAdapter = async ( testPath, }); - if (config.timers === 'fake' || config.timers === 'modern') { + if (config.timers.strategy === 'modern') { // during setup, this cannot be null (and it's fine to explode if it is) - environment.fakeTimersModern!.useFakeTimers(); - } else if (config.timers === 'legacy') { + environment.fakeTimersModern!.useFakeTimers(config.timers); + } else if (config.timers.strategy === 'legacy') { environment.fakeTimers!.useFakeTimers(); } diff --git a/packages/jest-cli/src/init/__tests__/__snapshots__/init.test.js.snap b/packages/jest-cli/src/init/__tests__/__snapshots__/init.test.js.snap index 157419444c3d..2151a310bc4d 100644 --- a/packages/jest-cli/src/init/__tests__/__snapshots__/init.test.js.snap +++ b/packages/jest-cli/src/init/__tests__/__snapshots__/init.test.js.snap @@ -284,7 +284,7 @@ module.exports = { // testRunner: "jest-circus/runner", // Setting this value to "fake" allows the use of fake timers for functions such as "setTimeout" - // timers: "real", + // timers: {}, // A map from regular expressions to paths to transformers // transform: undefined, diff --git a/packages/jest-config/src/Defaults.ts b/packages/jest-config/src/Defaults.ts index 9cc30e2d09e3..89be51afd672 100644 --- a/packages/jest-config/src/Defaults.ts +++ b/packages/jest-config/src/Defaults.ts @@ -72,7 +72,7 @@ const defaultOptions: Config.DefaultOptions = { testRegex: [], testRunner: 'jest-circus/runner', testSequencer: '@jest/test-sequencer', - timers: 'real', + timers: {}, transformIgnorePatterns: [NODE_MODULES_REGEXP, `\\.pnp\\.[^\\${sep}]+$`], useStderr: false, watch: false, diff --git a/packages/jest-config/src/Descriptions.ts b/packages/jest-config/src/Descriptions.ts index 795637460a1d..0bcff52ba053 100644 --- a/packages/jest-config/src/Descriptions.ts +++ b/packages/jest-config/src/Descriptions.ts @@ -84,6 +84,7 @@ const descriptions: {[key in keyof Config.InitialOptions]: string} = { testResultsProcessor: 'This option allows the use of a custom results processor', testRunner: 'This option allows use of a custom test runner', + // TODO timers: 'Setting this value to "fake" allows the use of fake timers for functions such as "setTimeout"', transform: 'A map from regular expressions to paths to transformers', diff --git a/packages/jest-config/src/ValidConfig.ts b/packages/jest-config/src/ValidConfig.ts index 5757431123ed..cdc7c9ceb4f5 100644 --- a/packages/jest-config/src/ValidConfig.ts +++ b/packages/jest-config/src/ValidConfig.ts @@ -132,7 +132,34 @@ const initialOptions: Config.InitialOptions = { testRunner: 'circus', testSequencer: '@jest/test-sequencer', testTimeout: 5000, - timers: 'real', + timers: multipleValidOptions( + {loopLimit: 1000, strategy: 'legacy'} as const, + { + advanceTimeDelta: 1000, + loopLimit: 1000, + now: multipleValidOptions(0, new Date()), + shouldAdvanceTime: false, + shouldClearNativeTimers: false, + strategy: 'modern', + toFake: [ + 'setImmediate', + 'clearImmediate', + 'setInterval', + 'clearInterval', + 'setTimeout', + 'clearTimeout', + 'requestAnimationFrame', + 'cancelAnimationFrame', + 'requestIdleCallback', + 'cancelIdleCallback', + 'Date', + 'hrtime', + 'nextTick', + 'performance', + 'queueMicrotask', // ? + ] as Array, + } as const, + ), transform: { '\\.js$': '/preprocessor.js', }, diff --git a/packages/jest-core/src/lib/__tests__/__snapshots__/logDebugMessages.test.ts.snap b/packages/jest-core/src/lib/__tests__/__snapshots__/logDebugMessages.test.ts.snap index dea4afbba9ef..3c0dbeb0504b 100644 --- a/packages/jest-core/src/lib/__tests__/__snapshots__/logDebugMessages.test.ts.snap +++ b/packages/jest-core/src/lib/__tests__/__snapshots__/logDebugMessages.test.ts.snap @@ -52,7 +52,7 @@ exports[`prints the config object 1`] = ` "\\\\.test\\\\.js$" ], "testRunner": "myRunner", - "timers": "real", + "timers": {}, "transform": [], "transformIgnorePatterns": [], "watchPathIgnorePatterns": [] diff --git a/packages/jest-environment/src/index.ts b/packages/jest-environment/src/index.ts index ac7fe89c30cc..bc01dfb717f6 100644 --- a/packages/jest-environment/src/index.ts +++ b/packages/jest-environment/src/index.ts @@ -304,7 +304,7 @@ export interface Jest { /** * Instructs Jest to use fake versions of the standard timer functions. */ - useFakeTimers(implementation?: 'modern' | 'legacy'): Jest; + useFakeTimers(config?: Config.TimersConfig): Jest; /** * Instructs Jest to use the real versions of the standard timer functions. */ diff --git a/packages/jest-fake-timers/package.json b/packages/jest-fake-timers/package.json index 264beaa4f5b0..2628c49d119f 100644 --- a/packages/jest-fake-timers/package.json +++ b/packages/jest-fake-timers/package.json @@ -25,6 +25,7 @@ "jest-util": "^28.0.0-alpha.7" }, "devDependencies": { + "@jest/test-utils": "^28.0.0-alpha.7", "@types/sinonjs__fake-timers": "^8.1.1" }, "engines": { diff --git a/packages/jest-fake-timers/src/__tests__/__snapshots__/modernFakeTimers.test.ts.snap b/packages/jest-fake-timers/src/__tests__/__snapshots__/modernFakeTimers.test.ts.snap index 8b00458786e1..5d407bdceba6 100644 --- a/packages/jest-fake-timers/src/__tests__/__snapshots__/modernFakeTimers.test.ts.snap +++ b/packages/jest-fake-timers/src/__tests__/__snapshots__/modernFakeTimers.test.ts.snap @@ -1,3 +1,3 @@ // Jest Snapshot v1, https://goo.gl/fbAQLP -exports[`FakeTimers runAllTimers warns when trying to advance timers while real timers are used 1`] = `"A function to advance timers was called but the timers API is not mocked with fake timers. Call \`jest.useFakeTimers()\` in this test or enable fake timers globally by setting \`"timers": "fake"\` in the configuration file"`; +exports[`FakeTimers runAllTimers warns when trying to advance timers while real timers are used 1`] = `"A function to advance timers was called but the timers API is not mocked with fake timers. Call \`jest.useFakeTimers()\` in this test or enable fake timers globally by setting \`"timers": {"strategy": "modern"}\` in the configuration file"`; diff --git a/packages/jest-fake-timers/src/__tests__/modernFakeTimers.test.ts b/packages/jest-fake-timers/src/__tests__/modernFakeTimers.test.ts index 36b14aecc128..7fe690989293 100644 --- a/packages/jest-fake-timers/src/__tests__/modernFakeTimers.test.ts +++ b/packages/jest-fake-timers/src/__tests__/modernFakeTimers.test.ts @@ -6,6 +6,7 @@ * */ +import {makeProjectConfig} from '@jest/test-utils'; import FakeTimers from '../modernFakeTimers'; describe('FakeTimers', () => { @@ -17,7 +18,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); expect(global.setTimeout).not.toBe(undefined); }); @@ -29,7 +30,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); expect(global.clearTimeout).not.toBe(undefined); }); @@ -41,7 +42,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); expect(global.setInterval).not.toBe(undefined); }); @@ -53,7 +54,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); expect(global.clearInterval).not.toBe(undefined); }); @@ -68,7 +69,7 @@ describe('FakeTimers', () => { }, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); expect(global.process.nextTick).not.toBe(origNextTick); }); @@ -82,7 +83,7 @@ describe('FakeTimers', () => { setImmediate: origSetImmediate, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); expect(global.setImmediate).not.toBe(origSetImmediate); }); @@ -98,7 +99,7 @@ describe('FakeTimers', () => { setImmediate: origSetImmediate, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); expect(global.clearImmediate).not.toBe(origClearImmediate); }); @@ -115,7 +116,7 @@ describe('FakeTimers', () => { setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const runOrder = []; @@ -146,7 +147,7 @@ describe('FakeTimers', () => { setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); timers.runAllTicks(); @@ -163,7 +164,7 @@ describe('FakeTimers', () => { setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const mock1 = jest.fn(); @@ -187,7 +188,10 @@ describe('FakeTimers', () => { setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global, maxLoops: 100}); + const timers = new FakeTimers({ + config: makeProjectConfig({timers: {loopLimit: 100}}), + global, + }); timers.useFakeTimers(); @@ -211,7 +215,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const runOrder = []; @@ -247,9 +251,7 @@ describe('FakeTimers', () => { const consoleWarn = console.warn; console.warn = jest.fn(); const timers = new FakeTimers({ - config: { - rootDir: __dirname, - }, + config: makeProjectConfig({rootDir: __dirname}), global: globalThis, }); timers.runAllTimers(); @@ -268,7 +270,7 @@ describe('FakeTimers', () => { setTimeout: nativeSetTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); timers.runAllTimers(); }); @@ -280,7 +282,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const fn = jest.fn(); @@ -301,7 +303,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const fn = jest.fn(); @@ -322,7 +324,7 @@ describe('FakeTimers', () => { setTimeout: nativeSetTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); // @sinonjs/fake-timers uses `setTimeout` during init to figure out if it's in Node or // browser env. So clear its calls before we install them into the env nativeSetTimeout.mockClear(); @@ -343,7 +345,10 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global, maxLoops: 100}); + const timers = new FakeTimers({ + config: makeProjectConfig({timers: {loopLimit: 1000}}), + global, + }); timers.useFakeTimers(); global.setTimeout(function infinitelyRecursingCallback() { @@ -354,7 +359,7 @@ describe('FakeTimers', () => { timers.runAllTimers(); }).toThrow( new Error( - 'Aborting after running 100 timers, assuming an infinite loop!', + 'Aborting after running 1000 timers, assuming an infinite loop!', ), ); }); @@ -366,7 +371,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const fn = jest.fn(); @@ -388,7 +393,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const runOrder = []; @@ -432,7 +437,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); timers.advanceTimersByTime(100); @@ -447,7 +452,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const runOrder: Array = []; @@ -487,7 +492,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const runOrder: Array = []; @@ -526,7 +531,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const runOrder: Array = []; @@ -554,7 +559,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); timers.advanceTimersToNextTimer(); @@ -569,7 +574,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const mock1 = jest.fn(); @@ -587,7 +592,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const mock1 = jest.fn(); @@ -608,7 +613,7 @@ describe('FakeTimers', () => { setImmediate: () => {}, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const mock1 = jest.fn(); @@ -627,7 +632,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const mock1 = jest.fn(); @@ -654,7 +659,7 @@ describe('FakeTimers', () => { setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const runOrder = []; @@ -719,7 +724,7 @@ describe('FakeTimers', () => { process, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); const fn = jest.fn(); @@ -748,7 +753,7 @@ describe('FakeTimers', () => { setInterval: nativeSetInterval, setTimeout: nativeSetTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); // Ensure that timers has overridden the native timer APIs @@ -775,7 +780,7 @@ describe('FakeTimers', () => { process: {nextTick: nativeProcessNextTick}, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); // Ensure that timers has overridden the native timer APIs @@ -799,7 +804,7 @@ describe('FakeTimers', () => { setImmediate: nativeSetImmediate, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useFakeTimers(); // Ensure that timers has overridden the native timer APIs @@ -829,7 +834,7 @@ describe('FakeTimers', () => { setInterval: nativeSetInterval, setTimeout: nativeSetTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useRealTimers(); // Ensure that the real timers are installed at this point @@ -856,7 +861,7 @@ describe('FakeTimers', () => { process: {nextTick: nativeProcessNextTick}, setTimeout, } as unknown as typeof globalThis; - const timers = new FakeTimers({global}); + const timers = new FakeTimers({config: makeProjectConfig(), global}); timers.useRealTimers(); // Ensure that the real timers are installed at this point @@ -880,7 +885,7 @@ describe('FakeTimers', () => { setImmediate: nativeSetImmediate, setTimeout, } as unknown as typeof globalThis; - const fakeTimers = new FakeTimers({global}); + const fakeTimers = new FakeTimers({config: makeProjectConfig(), global}); fakeTimers.useRealTimers(); // Ensure that the real timers are installed at this point @@ -897,7 +902,10 @@ describe('FakeTimers', () => { describe('getTimerCount', () => { it('returns the correct count', () => { - const timers = new FakeTimers({global: globalThis}); + const timers = new FakeTimers({ + config: makeProjectConfig(), + global: globalThis, + }); timers.useFakeTimers(); @@ -917,7 +925,10 @@ describe('FakeTimers', () => { }); it('includes immediates and ticks', () => { - const timers = new FakeTimers({global: globalThis}); + const timers = new FakeTimers({ + config: makeProjectConfig(), + global: globalThis, + }); timers.useFakeTimers(); @@ -929,7 +940,10 @@ describe('FakeTimers', () => { }); it('not includes cancelled immediates', () => { - const timers = new FakeTimers({global: globalThis}); + const timers = new FakeTimers({ + config: makeProjectConfig(), + global: globalThis, + }); timers.useFakeTimers(); diff --git a/packages/jest-fake-timers/src/modernFakeTimers.ts b/packages/jest-fake-timers/src/modernFakeTimers.ts index 93abce4dd4c9..01262b536e41 100644 --- a/packages/jest-fake-timers/src/modernFakeTimers.ts +++ b/packages/jest-fake-timers/src/modernFakeTimers.ts @@ -8,30 +8,28 @@ import { FakeTimerWithContext, InstalledClock, + FakeTimerInstallOpts as SinonTimersConfig, withGlobal, } from '@sinonjs/fake-timers'; -import {StackTraceConfig, formatStackTrace} from 'jest-message-util'; +import type {Config} from '@jest/types'; +import {formatStackTrace} from 'jest-message-util'; export default class FakeTimers { private _clock!: InstalledClock; - private _config: StackTraceConfig; + private _config: Config.ProjectConfig; private _fakingTime: boolean; private _global: typeof globalThis; private _fakeTimers: FakeTimerWithContext; - private _maxLoops: number; constructor({ global, config, - maxLoops, }: { global: typeof globalThis; - config: StackTraceConfig; - maxLoops?: number; + config: Config.ProjectConfig; }) { this._global = global; this._config = config; - this._maxLoops = maxLoops || 100000; this._fakingTime = false; this._fakeTimers = withGlobal(global); @@ -93,17 +91,21 @@ export default class FakeTimers { } } - useFakeTimers(): void { + useFakeTimers(timersConfig?: SinonTimersConfig): void { if (!this._fakingTime) { const toFake = Object.keys(this._fakeTimers.timers) as Array< keyof FakeTimerWithContext['timers'] >; - this._clock = this._fakeTimers.install({ - loopLimit: this._maxLoops, + const resolvedTimersConfig: SinonTimersConfig = { + loopLimit: 100_000, now: Date.now(), toFake, - }); + ...this._config.timers, + ...timersConfig, + }; + + this._clock = this._fakeTimers.install(resolvedTimersConfig); this._fakingTime = true; } @@ -140,8 +142,8 @@ export default class FakeTimers { this._global.console.warn( 'A function to advance timers was called but the timers API is not ' + 'mocked with fake timers. Call `jest.useFakeTimers()` in this test or ' + - 'enable fake timers globally by setting `"timers": "fake"` in the ' + - `configuration file\nStack Trace:\n${formatStackTrace( + 'enable fake timers globally by setting `"timers": {"strategy": "modern"}` ' + + `in the configuration file\nStack Trace:\n${formatStackTrace( new Error().stack!, this._config, {noStackTrace: false}, diff --git a/packages/jest-fake-timers/tsconfig.json b/packages/jest-fake-timers/tsconfig.json index 0bdcddc53258..4a4b01562562 100644 --- a/packages/jest-fake-timers/tsconfig.json +++ b/packages/jest-fake-timers/tsconfig.json @@ -10,6 +10,7 @@ {"path": "../jest-message-util"}, {"path": "../jest-mock"}, {"path": "../jest-types"}, - {"path": "../jest-util"} + {"path": "../jest-util"}, + {"path": "../test-utils"} ] } diff --git a/packages/jest-jasmine2/src/index.ts b/packages/jest-jasmine2/src/index.ts index d8f1a14bc4f5..b6ff009cfda1 100644 --- a/packages/jest-jasmine2/src/index.ts +++ b/packages/jest-jasmine2/src/index.ts @@ -88,9 +88,9 @@ export default async function jasmine2( environment.global.describe.skip = environment.global.xdescribe; environment.global.describe.only = environment.global.fdescribe; - if (config.timers === 'fake' || config.timers === 'modern') { - environment.fakeTimersModern!.useFakeTimers(); - } else if (config.timers === 'legacy') { + if (config.timers.strategy === 'modern') { + environment.fakeTimersModern!.useFakeTimers(config.timers); + } else if (config.timers.strategy === 'legacy') { environment.fakeTimers!.useFakeTimers(); } diff --git a/packages/jest-runtime/src/index.ts b/packages/jest-runtime/src/index.ts index 7fc8a91f6af3..42157c978929 100644 --- a/packages/jest-runtime/src/index.ts +++ b/packages/jest-runtime/src/index.ts @@ -185,7 +185,7 @@ export default class Runtime { private readonly _environment: JestEnvironment; private readonly _explicitShouldMock: Map; private readonly _explicitShouldMockModule: Map; - private _fakeTimersImplementation: + private _fakeTimersImplementation!: | LegacyFakeTimers | ModernFakeTimers | null; @@ -279,10 +279,11 @@ export default class Runtime { this._shouldUnmockTransitiveDependenciesCache = new Map(); this._transitiveShouldMock = new Map(); - this._fakeTimersImplementation = - config.timers === 'legacy' - ? this._environment.fakeTimers - : this._environment.fakeTimersModern; + if (config.timers.strategy === 'modern') { + this._fakeTimersImplementation = this._environment.fakeTimersModern; + } else if (config.timers.strategy === 'legacy') { + this._fakeTimersImplementation = this._environment.fakeTimers; + } this._unmockList = unmockRegExpCache.get(config); if (!this._unmockList && config.unmockedModulePathPatterns) { @@ -2065,13 +2066,13 @@ export default class Runtime { return this._fakeTimersImplementation!; }; - const useFakeTimers: Jest['useFakeTimers'] = (type = 'modern') => { - if (type === 'legacy') { - this._fakeTimersImplementation = this._environment.fakeTimers; - } else { + const useFakeTimers: Jest['useFakeTimers'] = config => { + if (config?.strategy === 'modern') { this._fakeTimersImplementation = this._environment.fakeTimersModern; + } else if (config?.strategy === 'legacy') { + this._fakeTimersImplementation = this._environment.fakeTimers; } - this._fakeTimersImplementation!.useFakeTimers(); + this._fakeTimersImplementation!.useFakeTimers(config); return jestObject; }; const useRealTimers = () => { diff --git a/packages/jest-transform/src/__tests__/__snapshots__/ScriptTransformer.test.ts.snap b/packages/jest-transform/src/__tests__/__snapshots__/ScriptTransformer.test.ts.snap index 7d89d8bbf339..f08efe9bca42 100644 --- a/packages/jest-transform/src/__tests__/__snapshots__/ScriptTransformer.test.ts.snap +++ b/packages/jest-transform/src/__tests__/__snapshots__/ScriptTransformer.test.ts.snap @@ -76,7 +76,7 @@ exports[`ScriptTransformer in async mode, passes expected transform options to g "\\.test\\.js$", ], "testRunner": "jest-circus/runner", - "timers": "real", + "timers": Object {}, "transform": Array [ Array [ "\\.js$", @@ -92,7 +92,7 @@ exports[`ScriptTransformer in async mode, passes expected transform options to g "unmockedModulePathPatterns": undefined, "watchPathIgnorePatterns": Array [], }, - "configString": "{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":"real","transform":[["\\\\.js$","test_preprocessor",{"configKey":"configValue"}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]}", + "configString": "{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":{},"transform":[["\\\\.js$","test_preprocessor",{"configKey":"configValue"}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]}", "coverageProvider": "babel", "instrument": true, "supportsDynamicImport": false, @@ -118,7 +118,7 @@ exports[`ScriptTransformer in async mode, uses the supplied async preprocessor 1 "const TRANSFORMED = { filename: '/fruits/banana.js', script: 'module.exports = "banana";', - config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":"real","transform":[["\\\\.js$","test_async_preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":\\"real\\",\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_async_preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', + config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":{},"transform":[["\\\\.js$","test_async_preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":{},\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_async_preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', };" `; @@ -128,7 +128,7 @@ exports[`ScriptTransformer in async mode, uses the supplied preprocessor 1`] = ` "const TRANSFORMED = { filename: '/fruits/banana.js', script: 'module.exports = "banana";', - config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":"real","transform":[["\\\\.js$","test_preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":\\"real\\",\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', + config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":{},"transform":[["\\\\.js$","test_preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":{},\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', };" `; @@ -207,7 +207,7 @@ exports[`ScriptTransformer passes expected transform options to getCacheKey 1`] "\\.test\\.js$", ], "testRunner": "jest-circus/runner", - "timers": "real", + "timers": Object {}, "transform": Array [ Array [ "\\.js$", @@ -223,7 +223,7 @@ exports[`ScriptTransformer passes expected transform options to getCacheKey 1`] "unmockedModulePathPatterns": undefined, "watchPathIgnorePatterns": Array [], }, - "configString": "{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":"real","transform":[["\\\\.js$","test_preprocessor",{"configKey":"configValue"}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]}", + "configString": "{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":{},"transform":[["\\\\.js$","test_preprocessor",{"configKey":"configValue"}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]}", "coverageProvider": "babel", "instrument": true, "supportsDynamicImport": false, @@ -312,7 +312,7 @@ exports[`ScriptTransformer passes expected transform options to getCacheKeyAsync "\\.test\\.js$", ], "testRunner": "jest-circus/runner", - "timers": "real", + "timers": Object {}, "transform": Array [ Array [ "\\.js$", @@ -328,7 +328,7 @@ exports[`ScriptTransformer passes expected transform options to getCacheKeyAsync "unmockedModulePathPatterns": undefined, "watchPathIgnorePatterns": Array [], }, - "configString": "{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":"real","transform":[["\\\\.js$","test_async_preprocessor",{"configKey":"configValue"}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]}", + "configString": "{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":{},"transform":[["\\\\.js$","test_async_preprocessor",{"configKey":"configValue"}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]}", "coverageProvider": "babel", "instrument": true, "supportsDynamicImport": false, @@ -676,7 +676,7 @@ exports[`ScriptTransformer uses mixture of sync/async preprocessors 1`] = ` "const TRANSFORMED = { filename: '/fruits/banana.js', script: 'module.exports = "banana";', - config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":"real","transform":[["\\\\.js$","test_async_preprocessor",{}],["\\\\.css$","css-preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":\\"real\\",\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_async_preprocessor\\",{}],[\\"\\\\\\\\.css$\\",\\"css-preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', + config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":{},"transform":[["\\\\.js$","test_async_preprocessor",{}],["\\\\.css$","css-preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":{},\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_async_preprocessor\\",{}],[\\"\\\\\\\\.css$\\",\\"css-preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', };" `; @@ -693,7 +693,7 @@ exports[`ScriptTransformer uses multiple preprocessors 1`] = ` "const TRANSFORMED = { filename: '/fruits/banana.js', script: 'module.exports = "banana";', - config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":"real","transform":[["\\\\.js$","test_preprocessor",{}],["\\\\.css$","css-preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":\\"real\\",\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_preprocessor\\",{}],[\\"\\\\\\\\.css$\\",\\"css-preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', + config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":{},"transform":[["\\\\.js$","test_preprocessor",{}],["\\\\.css$","css-preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":{},\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_preprocessor\\",{}],[\\"\\\\\\\\.css$\\",\\"css-preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', };" `; @@ -710,7 +710,7 @@ exports[`ScriptTransformer uses the supplied preprocessor 1`] = ` "const TRANSFORMED = { filename: '/fruits/banana.js', script: 'module.exports = "banana";', - config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":"real","transform":[["\\\\.js$","test_preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":\\"real\\",\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', + config: '{"collectCoverage":false,"collectCoverageFrom":[],"coverageProvider":"babel","supportsDynamicImport":false,"supportsExportNamespaceFrom":false,"supportsStaticESM":false,"supportsTopLevelAwait":false,"instrument":false,"cacheFS":{},"config":{"automock":false,"cache":true,"cacheDirectory":"/cache/","clearMocks":false,"coveragePathIgnorePatterns":[],"cwd":"/test_root_dir/","detectLeaks":false,"detectOpenHandles":false,"errorOnDeprecated":false,"extensionsToTreatAsEsm":[],"forceCoverageMatch":[],"globals":{},"haste":{},"injectGlobals":true,"moduleDirectories":[],"moduleFileExtensions":["js"],"moduleNameMapper":[],"modulePathIgnorePatterns":[],"modulePaths":[],"name":"test","prettierPath":"prettier","resetMocks":false,"resetModules":false,"restoreMocks":false,"rootDir":"/","roots":[],"runner":"jest-runner","runtime":"/test_module_loader_path","sandboxInjectedGlobals":[],"setupFiles":[],"setupFilesAfterEnv":[],"skipFilter":false,"skipNodeResolution":false,"slowTestThreshold":5,"snapshotFormat":{},"snapshotSerializers":[],"testEnvironment":"node","testEnvironmentOptions":{},"testLocationInResults":false,"testMatch":[],"testPathIgnorePatterns":[],"testRegex":["\\\\.test\\\\.js$"],"testRunner":"jest-circus/runner","timers":{},"transform":[["\\\\.js$","test_preprocessor",{}]],"transformIgnorePatterns":["/node_modules/"],"watchPathIgnorePatterns":[]},"configString":"{\\"automock\\":false,\\"cache\\":true,\\"cacheDirectory\\":\\"/cache/\\",\\"clearMocks\\":false,\\"coveragePathIgnorePatterns\\":[],\\"cwd\\":\\"/test_root_dir/\\",\\"detectLeaks\\":false,\\"detectOpenHandles\\":false,\\"errorOnDeprecated\\":false,\\"extensionsToTreatAsEsm\\":[],\\"forceCoverageMatch\\":[],\\"globals\\":{},\\"haste\\":{},\\"injectGlobals\\":true,\\"moduleDirectories\\":[],\\"moduleFileExtensions\\":[\\"js\\"],\\"moduleNameMapper\\":[],\\"modulePathIgnorePatterns\\":[],\\"modulePaths\\":[],\\"name\\":\\"test\\",\\"prettierPath\\":\\"prettier\\",\\"resetMocks\\":false,\\"resetModules\\":false,\\"restoreMocks\\":false,\\"rootDir\\":\\"/\\",\\"roots\\":[],\\"runner\\":\\"jest-runner\\",\\"runtime\\":\\"/test_module_loader_path\\",\\"sandboxInjectedGlobals\\":[],\\"setupFiles\\":[],\\"setupFilesAfterEnv\\":[],\\"skipFilter\\":false,\\"skipNodeResolution\\":false,\\"slowTestThreshold\\":5,\\"snapshotFormat\\":{},\\"snapshotSerializers\\":[],\\"testEnvironment\\":\\"node\\",\\"testEnvironmentOptions\\":{},\\"testLocationInResults\\":false,\\"testMatch\\":[],\\"testPathIgnorePatterns\\":[],\\"testRegex\\":[\\"\\\\\\\\.test\\\\\\\\.js$\\"],\\"testRunner\\":\\"jest-circus/runner\\",\\"timers\\":{},\\"transform\\":[[\\"\\\\\\\\.js$\\",\\"test_preprocessor\\",{}]],\\"transformIgnorePatterns\\":[\\"/node_modules/\\"],\\"watchPathIgnorePatterns\\":[]}","transformerConfig":{}}', };" `; diff --git a/packages/jest-types/__typetests__/jest.test.ts b/packages/jest-types/__typetests__/jest.test.ts index 6c2a9f17b75a..ede89db79faf 100644 --- a/packages/jest-types/__typetests__/jest.test.ts +++ b/packages/jest-types/__typetests__/jest.test.ts @@ -43,8 +43,7 @@ expectType( .setTimeout(6000) .unmock('moduleName') .useFakeTimers() - .useFakeTimers('modern') - .useFakeTimers('legacy') + .useFakeTimers({strategy: 'legacy'}) .useRealTimers(), ); @@ -248,9 +247,42 @@ expectType(jest.setSystemTime(new Date(1995, 11, 17))); expectError(jest.setSystemTime('1995-12-17T03:24:00')); expectType(jest.useFakeTimers()); -expectType(jest.useFakeTimers('modern')); -expectType(jest.useFakeTimers('legacy')); -expectError(jest.useFakeTimers('latest')); +expectType(jest.useFakeTimers({strategy: 'modern'})); +expectType(jest.useFakeTimers({loopLimit: 1000})); +expectType(jest.useFakeTimers({now: 1483228800000})); +expectType(jest.useFakeTimers({now: Date.now()})); +expectType(jest.useFakeTimers({now: new Date(1995, 11, 17)})); +expectType(jest.useFakeTimers({shouldAdvanceTime: true})); +expectType(jest.useFakeTimers({advanceTimeDelta: 10})); +expectType(jest.useFakeTimers({shouldClearNativeTimers: false})); +expectType( + jest.useFakeTimers({ + toFake: [ + 'setImmediate', + 'clearImmediate', + 'setInterval', + 'clearInterval', + 'setTimeout', + 'clearTimeout', + 'requestAnimationFrame', + 'cancelAnimationFrame', + 'requestIdleCallback', + 'cancelIdleCallback', + 'Date', + 'hrtime', + 'nextTick', + 'performance', + ], + }), +); + +expectType(jest.useFakeTimers({strategy: 'legacy'})); +expectType( + jest.useFakeTimers({loopLimit: 1000, strategy: 'legacy'}), +); + +expectError(jest.useFakeTimers('modern')); +expectError(jest.useFakeTimers({strategy: 'legacy', toFake: 'Date'})); expectType(jest.useRealTimers()); expectError(jest.useRealTimers(true)); diff --git a/packages/jest-types/src/Config.ts b/packages/jest-types/src/Config.ts index 80243eb45512..14e8d099f5dd 100644 --- a/packages/jest-types/src/Config.ts +++ b/packages/jest-types/src/Config.ts @@ -12,7 +12,104 @@ import type {SnapshotFormat} from '@jest/schemas'; type CoverageProvider = 'babel' | 'v8'; -type Timers = 'real' | 'fake' | 'modern' | 'legacy'; +export type FakeableTimerAPIs = + | 'setImmediate' + | 'clearImmediate' + | 'setInterval' + | 'clearInterval' + | 'setTimeout' + | 'clearTimeout' + | 'requestAnimationFrame' + | 'cancelAnimationFrame' + | 'requestIdleCallback' + | 'cancelIdleCallback' + | 'Date' + | 'hrtime' + | 'nextTick' + | 'performance'; +// | 'queueMicrotask'; // ? + +export type LegacyTimersConfig = { + /** + * The strategy to be use for the fake timers. + * + * @defaultValue + * The default is `'modern'`. + */ + strategy?: 'legacy'; + /** + * The maximum number of timers that will be run when calling `jest.advanceTimersByTime()`, + * `jest.runAllImmediates()`, `jest.runAllTicks()` or `jest.runAllTimers()`. + * + * @defaultValue + * The default is `100_000` timers. + */ + loopLimit?: number; +}; + +export type ModernTimersConfig = { + /** + * The strategy to be use for the fake timers. + * + * @defaultValue + * The default is `'modern'`. + */ + strategy?: 'modern'; + /** + * Sets the default unix epoch. May be a number (in milliseconds) or a Date object. + * + * @defaultValue + * The default is `Date.now()`. + */ + now?: number | Date; + /** + * Allows to cherry pick the timer methods and objects (e.g. `setTimeout()`, + * `setImmediate()`, `Date`, `nextTick`, `performance`) that should be faked. + * + * @defaultValue + * All timer APIs are faked by default. + * + * @example + * {toFake: ['nextTick', 'setTimeout']} + */ + toFake?: Array; + /** + * The maximum number of timers that will be run when calling `jest.advanceTimersByTime()`, + * `jest.runAllTicks()` or `jest.runAllTimers()`. + * + * @defaultValue + * The default is `100_000` timers. + */ + loopLimit?: number; + /** + * Whether to increment mocked time automatically based on the real system time + * shift. If `shouldAdvanceTime` is not set, the mocked time will be incremented + * by 20 milliseconds for every 20 milliseconds change in the real system time. + * + * @defaultValue + * The default is `false`. + */ + shouldAdvanceTime?: boolean; + /** + * Relevant only when using with `shouldAdvanceTime: true`. Increment mocked + * time by `advanceTimeDelta` milliseconds every `advanceTimeDelta` milliseconds. + * + * @defaultValue + * The default is `20` milliseconds. + */ + advanceTimeDelta?: number; + /** + * Forwards clear timer calls to native functions if they are not fakes. + * These are not cleared by default, leading to potentially unexpected behavior + * if timers existed prior to installing fake timers. + * + * @defaultValue + * The default is `false`. + */ + shouldClearNativeTimers?: boolean; +}; + +export type TimersConfig = LegacyTimersConfig | ModernTimersConfig; export type HasteConfig = { /** Whether to hash files using SHA-1. */ @@ -112,7 +209,7 @@ export type DefaultOptions = { testRegex: Array; testRunner: string; testSequencer: string; - timers: Timers; + timers: TimersConfig; transformIgnorePatterns: Array; useStderr: boolean; watch: boolean; @@ -241,7 +338,7 @@ export type InitialOptions = Partial<{ testRunner: string; testSequencer: string; testTimeout: number; - timers: Timers; + timers: TimersConfig; transform: { [regex: string]: string | TransformerConfig; }; @@ -401,7 +498,7 @@ export type ProjectConfig = { testPathIgnorePatterns: Array; testRegex: Array; testRunner: string; - timers: Timers; + timers: TimersConfig; transform: Array<[string, string, Record]>; transformIgnorePatterns: Array; watchPathIgnorePatterns: Array; diff --git a/packages/jest-worker/src/workers/__tests__/processChild.test.js b/packages/jest-worker/src/workers/__tests__/processChild.test.js index ba579e052efe..55b29107bdf7 100644 --- a/packages/jest-worker/src/workers/__tests__/processChild.test.js +++ b/packages/jest-worker/src/workers/__tests__/processChild.test.js @@ -241,8 +241,6 @@ it('returns results immediately when function is synchronous', () => { }); it('returns results when it gets resolved if function is asynchronous', async () => { - jest.useRealTimers(); - process.emit('message', [ CHILD_MESSAGE_INITIALIZE, true, // Not really used here, but for flow type purity. diff --git a/packages/jest-worker/src/workers/__tests__/threadChild.test.js b/packages/jest-worker/src/workers/__tests__/threadChild.test.js index 657ce23a33bb..fe0107a926f2 100644 --- a/packages/jest-worker/src/workers/__tests__/threadChild.test.js +++ b/packages/jest-worker/src/workers/__tests__/threadChild.test.js @@ -268,8 +268,6 @@ it('returns results immediately when function is synchronous', () => { }); it('returns results when it gets resolved if function is asynchronous', async () => { - jest.useRealTimers(); - thread.emit('message', [ CHILD_MESSAGE_INITIALIZE, true, // Not really used here, but for flow type purity. diff --git a/packages/test-utils/src/config.ts b/packages/test-utils/src/config.ts index f86bbd3f0c65..3b9ac8475a8d 100644 --- a/packages/test-utils/src/config.ts +++ b/packages/test-utils/src/config.ts @@ -116,7 +116,7 @@ const DEFAULT_PROJECT_CONFIG: Config.ProjectConfig = { testPathIgnorePatterns: [], testRegex: ['\\.test\\.js$'], testRunner: 'jest-circus/runner', - timers: 'real', + timers: {}, transform: [], transformIgnorePatterns: [], unmockedModulePathPatterns: undefined, diff --git a/yarn.lock b/yarn.lock index f0cfc2e76ffc..32787aac7539 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2650,6 +2650,7 @@ __metadata: version: 0.0.0-use.local resolution: "@jest/fake-timers@workspace:packages/jest-fake-timers" dependencies: + "@jest/test-utils": ^28.0.0-alpha.7 "@jest/types": ^28.0.0-alpha.7 "@sinonjs/fake-timers": ^9.1.1 "@types/node": "*"