Skip to content

Commit db2a3e3

Browse files
committed
Codemod act -> await act (4/?)
Similar to the rationale for `waitFor` (see facebook#26285), we should always await the result of an `act` call so that microtasks have a chance to fire. This only affects the internal `act` that we use in our repo, for now. In the public `act` API, we don't yet require this; however, we effectively will for any update that triggers suspense once `use` lands. So we likely will start warning in an upcoming minor.
1 parent 161f6ae commit db2a3e3

12 files changed

+769
-955
lines changed

packages/react-dom/src/__tests__/utils/ReactDOMServerIntegrationTestUtils.js

+10-15
Original file line numberDiff line numberDiff line change
@@ -48,21 +48,16 @@ module.exports = function (initModules) {
4848
// ====================================
4949

5050
// promisified version of ReactDOM.render()
51-
function asyncReactDOMRender(reactElement, domElement, forceHydrate) {
52-
return new Promise(resolve => {
53-
if (forceHydrate) {
54-
act(() => {
55-
ReactDOM.hydrate(reactElement, domElement);
56-
});
57-
} else {
58-
act(() => {
59-
ReactDOM.render(reactElement, domElement);
60-
});
61-
}
62-
// We can't use the callback for resolution because that will not catch
63-
// errors. They're thrown.
64-
resolve();
65-
});
51+
async function asyncReactDOMRender(reactElement, domElement, forceHydrate) {
52+
if (forceHydrate) {
53+
await act(async () => {
54+
ReactDOM.hydrate(reactElement, domElement);
55+
});
56+
} else {
57+
await act(async () => {
58+
ReactDOM.render(reactElement, domElement);
59+
});
60+
}
6661
}
6762
// performs fn asynchronously and expects count errors logged to console.error.
6863
// will fail the test if the count of errors logged is not equal to count.

packages/react-dom/src/events/__tests__/DOMPluginEventSystem-test.internal.js

+11-11
Original file line numberDiff line numberDiff line change
@@ -2520,7 +2520,7 @@ describe('DOMPluginEventSystem', () => {
25202520
});
25212521

25222522
// @gate www
2523-
it('beforeblur and afterblur are called after a focused element is suspended', () => {
2523+
it('beforeblur and afterblur are called after a focused element is suspended', async () => {
25242524
const log = [];
25252525
// We have to persist here because we want to read relatedTarget later.
25262526
const onAfterBlur = jest.fn(e => {
@@ -2575,7 +2575,7 @@ describe('DOMPluginEventSystem', () => {
25752575

25762576
const root = ReactDOMClient.createRoot(container2);
25772577

2578-
act(() => {
2578+
await act(async () => {
25792579
root.render(<Component />);
25802580
});
25812581
jest.runAllTimers();
@@ -2587,7 +2587,7 @@ describe('DOMPluginEventSystem', () => {
25872587
expect(onAfterBlur).toHaveBeenCalledTimes(0);
25882588

25892589
suspend = true;
2590-
act(() => {
2590+
await act(async () => {
25912591
root.render(<Component />);
25922592
});
25932593
jest.runAllTimers();
@@ -2604,7 +2604,7 @@ describe('DOMPluginEventSystem', () => {
26042604
});
26052605

26062606
// @gate www
2607-
it('beforeblur should skip handlers from a deleted subtree after the focused element is suspended', () => {
2607+
it('beforeblur should skip handlers from a deleted subtree after the focused element is suspended', async () => {
26082608
const onBeforeBlur = jest.fn();
26092609
const innerRef = React.createRef();
26102610
const innerRef2 = React.createRef();
@@ -2661,7 +2661,7 @@ describe('DOMPluginEventSystem', () => {
26612661

26622662
const root = ReactDOMClient.createRoot(container2);
26632663

2664-
act(() => {
2664+
await act(async () => {
26652665
root.render(<Component />);
26662666
});
26672667
jest.runAllTimers();
@@ -2672,7 +2672,7 @@ describe('DOMPluginEventSystem', () => {
26722672
expect(onBeforeBlur).toHaveBeenCalledTimes(0);
26732673

26742674
suspend = true;
2675-
act(() => {
2675+
await act(async () => {
26762676
root.render(<Component />);
26772677
});
26782678
jest.runAllTimers();
@@ -2684,17 +2684,17 @@ describe('DOMPluginEventSystem', () => {
26842684
});
26852685

26862686
// @gate www
2687-
it('regression: does not fire beforeblur/afterblur if target is already hidden', () => {
2687+
it('regression: does not fire beforeblur/afterblur if target is already hidden', async () => {
26882688
const Suspense = React.Suspense;
26892689
let suspend = false;
2690-
const promise = Promise.resolve();
2690+
const fakePromise = {then() {}};
26912691
const setBeforeBlurHandle =
26922692
ReactDOM.unstable_createEventHandle('beforeblur');
26932693
const innerRef = React.createRef();
26942694

26952695
function Child() {
26962696
if (suspend) {
2697-
throw promise;
2697+
throw fakePromise;
26982698
}
26992699
return <input ref={innerRef} />;
27002700
}
@@ -2726,7 +2726,7 @@ describe('DOMPluginEventSystem', () => {
27262726
document.body.appendChild(container2);
27272727

27282728
const root = ReactDOMClient.createRoot(container2);
2729-
act(() => {
2729+
await act(async () => {
27302730
root.render(<Component />);
27312731
});
27322732

@@ -2737,7 +2737,7 @@ describe('DOMPluginEventSystem', () => {
27372737

27382738
// Suspend. This hides the input node, causing it to lose focus.
27392739
suspend = true;
2740-
act(() => {
2740+
await act(async () => {
27412741
root.render(<Component />);
27422742
});
27432743

0 commit comments

Comments
 (0)