From 9410b51534f169a9474ac49d37f0347cc4294dbb Mon Sep 17 00:00:00 2001 From: Maciej Jastrzebski Date: Thu, 23 Mar 2023 11:13:41 +0100 Subject: [PATCH 1/4] refactor: flush microtask queue implementation --- src/flushMicroTasks.ts | 12 ++---------- 1 file changed, 2 insertions(+), 10 deletions(-) diff --git a/src/flushMicroTasks.ts b/src/flushMicroTasks.ts index 7b964a9d6..4e5fac764 100644 --- a/src/flushMicroTasks.ts +++ b/src/flushMicroTasks.ts @@ -1,13 +1,5 @@ import { setImmediate } from './helpers/timers'; -type Thenable = { then: (callback: () => T) => unknown }; - -export function flushMicroTasks(): Thenable { - return { - // using "thenable" instead of a Promise, because otherwise it breaks when - // using "modern" fake timers - then(resolve) { - setImmediate(resolve); - }, - }; +export function flushMicroTasks() { + return new Promise((resolve) => setImmediate(resolve)); } From 58a807388c11e85c71216699025db2f0fd54b78a Mon Sep 17 00:00:00 2001 From: Maciej Jastrzebski Date: Fri, 24 Mar 2023 23:30:42 +0100 Subject: [PATCH 2/4] refactor: code review changes --- src/waitFor.ts | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/waitFor.ts b/src/waitFor.ts index ac515fe86..e1253309b 100644 --- a/src/waitFor.ts +++ b/src/waitFor.ts @@ -6,7 +6,6 @@ import { ErrorWithStack, copyStackTrace } from './helpers/errors'; import { setTimeout, clearTimeout, - setImmediate, jestFakeTimersAreEnabled, } from './helpers/timers'; import { checkReactVersionAtLeast } from './react-versions'; @@ -89,7 +88,7 @@ function waitForInternal( // of parallelization so we're fine. // https://stackoverflow.com/a/59243586/971592 // eslint-disable-next-line no-await-in-loop - await new Promise((resolve) => setImmediate(resolve)); + await flushMicroTasks(); } } else { overallTimeoutTimer = setTimeout(handleTimeout, timeout); From 42636964e6521f3a614cc34c915013cb1c87473f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Jastrze=CC=A8bski?= Date: Wed, 31 May 2023 13:36:25 +0200 Subject: [PATCH 3/4] refactor: restore original flush function as legacy version --- src/flushMicroTasks.ts | 25 +++++++++++++++++++++++++ src/index.ts | 4 ++-- src/waitFor.ts | 4 ++-- 3 files changed, 29 insertions(+), 4 deletions(-) diff --git a/src/flushMicroTasks.ts b/src/flushMicroTasks.ts index 4e5fac764..08295740b 100644 --- a/src/flushMicroTasks.ts +++ b/src/flushMicroTasks.ts @@ -3,3 +3,28 @@ import { setImmediate } from './helpers/timers'; export function flushMicroTasks() { return new Promise((resolve) => setImmediate(resolve)); } + +/** + * @deprecated To be removed in the next major release. + */ +type Thenable = { then: (callback: () => T) => unknown }; + +/** + * This legacy implementation of `flushMicroTasks` is used for compatibility with + * older versions of React Native (pre 0.71) which uses Promise polyfil. + * + * For users with older version of React Native there is a workaround of using our own + * Jest preset instead the `react-native` one, but requiring such change would be a + * breaking change for existing users. + * + * @deprecated To be removed in the next major release. + */ +export function flushMicroTasksLegacy(): Thenable { + return { + // using "thenable" instead of a Promise, because otherwise it breaks when + // using "modern" fake timers + then(resolve) { + setImmediate(resolve); + }, + }; +} diff --git a/src/index.ts b/src/index.ts index f2f2f342c..6acbe951a 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,5 +1,5 @@ import { cleanup } from './pure'; -import { flushMicroTasks } from './flushMicroTasks'; +import { flushMicroTasksLegacy } from './flushMicroTasks'; import { getIsReactActEnvironment, setReactActEnvironment } from './act'; if (typeof process === 'undefined' || !process.env?.RNTL_SKIP_AUTO_CLEANUP) { @@ -11,7 +11,7 @@ if (typeof process === 'undefined' || !process.env?.RNTL_SKIP_AUTO_CLEANUP) { if (typeof afterEach === 'function') { // eslint-disable-next-line no-undef afterEach(async () => { - await flushMicroTasks(); + await flushMicroTasksLegacy(); cleanup(); }); } diff --git a/src/waitFor.ts b/src/waitFor.ts index e1253309b..5f46270d7 100644 --- a/src/waitFor.ts +++ b/src/waitFor.ts @@ -1,7 +1,7 @@ /* globals jest */ import act, { setReactActEnvironment, getIsReactActEnvironment } from './act'; import { getConfig } from './config'; -import { flushMicroTasks } from './flushMicroTasks'; +import { flushMicroTasks, flushMicroTasksLegacy } from './flushMicroTasks'; import { ErrorWithStack, copyStackTrace } from './helpers/errors'; import { setTimeout, @@ -206,7 +206,7 @@ export default async function waitFor( try { const result = await waitForInternal(expectation, optionsWithStackTrace); // Flush the microtask queue before restoring the `act` environment - await flushMicroTasks(); + await flushMicroTasksLegacy(); return result; } finally { setReactActEnvironment(previousActEnvironment); From ffaa8df9498d2ce5a0b879e19e5afe9844f517b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Maciej=20Jastrze=CC=A8bski?= Date: Wed, 31 May 2023 13:45:47 +0200 Subject: [PATCH 4/4] chore: rename file --- src/{flushMicroTasks.ts => flush-micro-tasks.ts} | 0 src/index.ts | 2 +- src/waitFor.ts | 2 +- 3 files changed, 2 insertions(+), 2 deletions(-) rename src/{flushMicroTasks.ts => flush-micro-tasks.ts} (100%) diff --git a/src/flushMicroTasks.ts b/src/flush-micro-tasks.ts similarity index 100% rename from src/flushMicroTasks.ts rename to src/flush-micro-tasks.ts diff --git a/src/index.ts b/src/index.ts index 6acbe951a..4d699fcdd 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,5 +1,5 @@ import { cleanup } from './pure'; -import { flushMicroTasksLegacy } from './flushMicroTasks'; +import { flushMicroTasksLegacy } from './flush-micro-tasks'; import { getIsReactActEnvironment, setReactActEnvironment } from './act'; if (typeof process === 'undefined' || !process.env?.RNTL_SKIP_AUTO_CLEANUP) { diff --git a/src/waitFor.ts b/src/waitFor.ts index 5f46270d7..d28a80c63 100644 --- a/src/waitFor.ts +++ b/src/waitFor.ts @@ -1,7 +1,7 @@ /* globals jest */ import act, { setReactActEnvironment, getIsReactActEnvironment } from './act'; import { getConfig } from './config'; -import { flushMicroTasks, flushMicroTasksLegacy } from './flushMicroTasks'; +import { flushMicroTasks, flushMicroTasksLegacy } from './flush-micro-tasks'; import { ErrorWithStack, copyStackTrace } from './helpers/errors'; import { setTimeout,