Skip to content

Commit

Permalink
Codemod tests to waitFor pattern (9/?) (#26309)
Browse files Browse the repository at this point in the history
This converts some of our test suite to use the `waitFor` test pattern,
instead of the `expect(Scheduler).toFlushAndYield` pattern. Most of
these changes are automated with jscodeshift, with some slight manual
cleanup in certain cases.

See #26285 for full context.
  • Loading branch information
acdlite committed Mar 4, 2023
1 parent 64dde70 commit 25685d8
Show file tree
Hide file tree
Showing 22 changed files with 233 additions and 217 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ let TextResource;
let textResourceShouldFail;
let waitForAll;
let assertLog;
let waitForThrow;

describe('ReactCache', () => {
beforeEach(() => {
Expand All @@ -38,6 +39,7 @@ describe('ReactCache', () => {
const InternalTestUtils = require('internal-test-utils');
waitForAll = InternalTestUtils.waitForAll;
assertLog = InternalTestUtils.assertLog;
waitForThrow = InternalTestUtils.waitForThrow;

TextResource = createResource(
([text, ms = 0]) => {
Expand Down Expand Up @@ -150,12 +152,12 @@ describe('ReactCache', () => {
jest.advanceTimersByTime(100);
assertLog(['Promise rejected [Hi]']);

expect(Scheduler).toFlushAndThrow('Failed to load: Hi');
await waitForThrow('Failed to load: Hi');
assertLog(['Error! [Hi]', 'Error! [Hi]']);

// Should throw again on a subsequent read
root.update(<App />);
expect(Scheduler).toFlushAndThrow('Failed to load: Hi');
await waitForThrow('Failed to load: Hi');
assertLog(['Error! [Hi]', 'Error! [Hi]']);
});

Expand Down
2 changes: 1 addition & 1 deletion packages/react-dom/src/__tests__/ReactDOMFloat-test.js
Original file line number Diff line number Diff line change
Expand Up @@ -4398,7 +4398,7 @@ background-color: green;
</body>
</html>,
);
expect(Scheduler).toFlushWithoutYielding();
await waitForAll([]);
expect(getMeaningfulChildren(document)).toEqual(
<html>
<head>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1092,17 +1092,19 @@ describe('ReactDOMServerSelectiveHydration', () => {
const innerHTML = ReactDOMServer.renderToString(<InnerApp />);
innerContainer.innerHTML = innerHTML;

expect(OuterScheduler).toHaveYielded(['Outer']);
expect(InnerScheduler).toHaveYielded(['Inner']);
expect(OuterScheduler.unstable_clearYields()).toEqual(['Outer']);
expect(InnerScheduler.unstable_clearYields()).toEqual(['Inner']);

suspendOuter = true;
suspendInner = true;

OuterReactDOMClient.hydrateRoot(outerContainer, <OuterApp />);
InnerReactDOMClient.hydrateRoot(innerContainer, <InnerApp />);

expect(OuterScheduler).toFlushAndYield(['Suspend Outer']);
expect(InnerScheduler).toFlushAndYield(['Suspend Inner']);
OuterScheduler.unstable_flushAllWithoutAsserting();
InnerScheduler.unstable_flushAllWithoutAsserting();
expect(OuterScheduler.unstable_clearYields()).toEqual(['Suspend Outer']);
expect(InnerScheduler.unstable_clearYields()).toEqual(['Suspend Inner']);

innerDiv = document.querySelector('#inner');

Expand All @@ -1115,7 +1117,7 @@ describe('ReactDOMServerSelectiveHydration', () => {
InnerScheduler.unstable_flushAllWithoutAsserting();
});

expect(OuterScheduler).toHaveYielded(['Suspend Outer']);
expect(OuterScheduler.unstable_clearYields()).toEqual(['Suspend Outer']);
if (
gate(
flags =>
Expand All @@ -1124,10 +1126,12 @@ describe('ReactDOMServerSelectiveHydration', () => {
) {
// InnerApp doesn't see the event because OuterApp calls stopPropagation in
// capture phase since the event is blocked on suspended component
expect(InnerScheduler).toHaveYielded([]);
expect(InnerScheduler.unstable_clearYields()).toEqual([]);
} else {
// no stopPropagation
expect(InnerScheduler).toHaveYielded(['Suspend Inner']);
expect(InnerScheduler.unstable_clearYields()).toEqual([
'Suspend Inner',
]);
}

assertLog([]);
Expand All @@ -1149,15 +1153,15 @@ describe('ReactDOMServerSelectiveHydration', () => {
InnerScheduler.unstable_flushAllWithoutAsserting();
});

expect(OuterScheduler).toHaveYielded(['Suspend Outer']);
expect(OuterScheduler.unstable_clearYields()).toEqual(['Suspend Outer']);
// Inner App renders because it is unblocked
expect(InnerScheduler).toHaveYielded(['Inner']);
expect(InnerScheduler.unstable_clearYields()).toEqual(['Inner']);
// No event is replayed yet
assertLog([]);

dispatchMouseHoverEvent(innerDiv);
expect(OuterScheduler).toHaveYielded([]);
expect(InnerScheduler).toHaveYielded([]);
expect(OuterScheduler.unstable_clearYields()).toEqual([]);
expect(InnerScheduler.unstable_clearYields()).toEqual([]);
// No event is replayed yet
assertLog([]);

Expand All @@ -1172,9 +1176,9 @@ describe('ReactDOMServerSelectiveHydration', () => {

// Nothing happens to inner app yet.
// Its blocked on the outer app replaying the event
expect(InnerScheduler).toHaveYielded([]);
expect(InnerScheduler.unstable_clearYields()).toEqual([]);
// Outer hydrates and schedules Replay
expect(OuterScheduler).toHaveYielded(['Outer']);
expect(OuterScheduler.unstable_clearYields()).toEqual(['Outer']);
// No event is replayed yet
assertLog([]);

Expand Down Expand Up @@ -1203,9 +1207,9 @@ describe('ReactDOMServerSelectiveHydration', () => {
});

// Outer resolves and scheduled replay
expect(OuterScheduler).toHaveYielded(['Outer']);
expect(OuterScheduler.unstable_clearYields()).toEqual(['Outer']);
// Inner App is still blocked
expect(InnerScheduler).toHaveYielded([]);
expect(InnerScheduler.unstable_clearYields()).toEqual([]);

// Replay outer event
await act(async () => {
Expand All @@ -1217,12 +1221,12 @@ describe('ReactDOMServerSelectiveHydration', () => {
// Inner is still blocked so when Outer replays the event in capture phase
// inner ends up caling stopPropagation
assertLog([]);
expect(OuterScheduler).toHaveYielded([]);
expect(InnerScheduler).toHaveYielded(['Suspend Inner']);
expect(OuterScheduler.unstable_clearYields()).toEqual([]);
expect(InnerScheduler.unstable_clearYields()).toEqual(['Suspend Inner']);

dispatchMouseHoverEvent(innerDiv);
expect(OuterScheduler).toHaveYielded([]);
expect(InnerScheduler).toHaveYielded([]);
expect(OuterScheduler.unstable_clearYields()).toEqual([]);
expect(InnerScheduler.unstable_clearYields()).toEqual([]);
assertLog([]);

await act(async () => {
Expand All @@ -1234,9 +1238,9 @@ describe('ReactDOMServerSelectiveHydration', () => {
});

// Inner hydrates
expect(InnerScheduler).toHaveYielded(['Inner']);
expect(InnerScheduler.unstable_clearYields()).toEqual(['Inner']);
// Outer was hydrated earlier
expect(OuterScheduler).toHaveYielded([]);
expect(OuterScheduler.unstable_clearYields()).toEqual([]);

await act(async () => {
Scheduler.unstable_flushAllWithoutAsserting();
Expand Down
22 changes: 10 additions & 12 deletions packages/react-dom/src/__tests__/ReactDeprecationWarnings-test.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@

let React;
let ReactNoop;
let Scheduler;
let JSXDEVRuntime;
let waitForAll;

Expand All @@ -20,15 +19,14 @@ describe('ReactDeprecationWarnings', () => {
jest.resetModules();
React = require('react');
ReactNoop = require('react-noop-renderer');
Scheduler = require('scheduler');
const InternalTestUtils = require('internal-test-utils');
waitForAll = InternalTestUtils.waitForAll;
if (__DEV__) {
JSXDEVRuntime = require('react/jsx-dev-runtime');
}
});

it('should warn when given defaultProps', () => {
it('should warn when given defaultProps', async () => {
function FunctionalComponent(props) {
return null;
}
Expand All @@ -38,14 +36,14 @@ describe('ReactDeprecationWarnings', () => {
};

ReactNoop.render(<FunctionalComponent />);
expect(() => expect(Scheduler).toFlushWithoutYielding()).toErrorDev(
await expect(async () => await waitForAll([])).toErrorDev(
'Warning: FunctionalComponent: Support for defaultProps ' +
'will be removed from function components in a future major ' +
'release. Use JavaScript default parameters instead.',
);
});

it('should warn when given defaultProps on a memoized function', () => {
it('should warn when given defaultProps on a memoized function', async () => {
const MemoComponent = React.memo(function FunctionalComponent(props) {
return null;
});
Expand All @@ -59,14 +57,14 @@ describe('ReactDeprecationWarnings', () => {
<MemoComponent />
</div>,
);
expect(() => expect(Scheduler).toFlushWithoutYielding()).toErrorDev(
await expect(async () => await waitForAll([])).toErrorDev(
'Warning: FunctionalComponent: Support for defaultProps ' +
'will be removed from memo components in a future major ' +
'release. Use JavaScript default parameters instead.',
);
});

it('should warn when given string refs', () => {
it('should warn when given string refs', async () => {
class RefComponent extends React.Component {
render() {
return null;
Expand All @@ -79,7 +77,7 @@ describe('ReactDeprecationWarnings', () => {
}

ReactNoop.render(<Component />);
expect(() => expect(Scheduler).toFlushWithoutYielding()).toErrorDev(
await expect(async () => await waitForAll([])).toErrorDev(
'Warning: Component "Component" contains the string ref "refComponent". ' +
'Support for string refs will be removed in a future major release. ' +
'We recommend using useRef() or createRef() instead. ' +
Expand Down Expand Up @@ -108,7 +106,7 @@ describe('ReactDeprecationWarnings', () => {
await waitForAll([]);
});

it('should warn when owner and self are different for string refs', () => {
it('should warn when owner and self are different for string refs', async () => {
class RefComponent extends React.Component {
render() {
return null;
Expand All @@ -121,7 +119,7 @@ describe('ReactDeprecationWarnings', () => {
}

ReactNoop.render(<Component />);
expect(() => expect(Scheduler).toFlushWithoutYielding()).toErrorDev([
await expect(async () => await waitForAll([])).toErrorDev([
'Warning: Component "Component" contains the string ref "refComponent". ' +
'Support for string refs will be removed in a future major release. ' +
'This case cannot be automatically converted to an arrow function. ' +
Expand All @@ -132,7 +130,7 @@ describe('ReactDeprecationWarnings', () => {
});

if (__DEV__) {
it('should warn when owner and self are different for string refs', () => {
it('should warn when owner and self are different for string refs', async () => {
class RefComponent extends React.Component {
render() {
return null;
Expand All @@ -152,7 +150,7 @@ describe('ReactDeprecationWarnings', () => {
}

ReactNoop.render(<Component />);
expect(() => expect(Scheduler).toFlushWithoutYielding()).toErrorDev(
await expect(async () => await waitForAll([])).toErrorDev(
'Warning: Component "Component" contains the string ref "refComponent". ' +
'Support for string refs will be removed in a future major release. ' +
'This case cannot be automatically converted to an arrow function. ' +
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ let Suspense;
let scheduleCallback;
let NormalPriority;
let waitForAll;
let waitFor;

describe('ReactSuspenseList', () => {
beforeEach(() => {
Expand All @@ -24,6 +25,7 @@ describe('ReactSuspenseList', () => {

const InternalTestUtils = require('internal-test-utils');
waitForAll = InternalTestUtils.waitForAll;
waitFor = InternalTestUtils.waitFor;
});

function Text(props) {
Expand Down Expand Up @@ -86,11 +88,11 @@ describe('ReactSuspenseList', () => {
});

// This resolves A and schedules a task for React to retry.
await expect(Scheduler).toFlushAndYieldThrough(['Resolve A']);
await waitFor(['Resolve A']);

// The next task that flushes should be the one that resolves B. The render
// task should not jump the queue ahead of B.
await expect(Scheduler).toFlushAndYieldThrough(['Resolve B']);
await waitFor(['Resolve B']);

await waitForAll(['A', 'B']);
expect(root).toMatchRenderedOutput('AB');
Expand Down
8 changes: 3 additions & 5 deletions packages/react-reconciler/src/__tests__/ReactFragment-test.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@

let React;
let ReactNoop;
let Scheduler;
let waitForAll;

describe('ReactFragment', () => {
Expand All @@ -20,7 +19,6 @@ describe('ReactFragment', () => {

React = require('react');
ReactNoop = require('react-noop-renderer');
Scheduler = require('scheduler');

const InternalTestUtils = require('internal-test-utils');
waitForAll = InternalTestUtils.waitForAll;
Expand Down Expand Up @@ -707,7 +705,7 @@ describe('ReactFragment', () => {
);
});

it('should not preserve state when switching to a keyed fragment to an array', async function () {
it('should not preserve state when switching to a keyed fragment to an array', async () => {
const ops = [];

class Stateful extends React.Component {
Expand Down Expand Up @@ -742,7 +740,7 @@ describe('ReactFragment', () => {
await waitForAll([]);

ReactNoop.render(<Foo condition={false} />);
expect(() => expect(Scheduler).toFlushWithoutYielding()).toErrorDev(
await expect(async () => await waitForAll([])).toErrorDev(
'Each child in a list should have a unique "key" prop.',
);

Expand Down Expand Up @@ -939,7 +937,7 @@ describe('ReactFragment', () => {
}

ReactNoop.render(<Foo condition={true} />);
expect(() => expect(Scheduler).toFlushWithoutYielding()).toErrorDev(
await expect(async () => await waitForAll([])).toErrorDev(
'Each child in a list should have a unique "key" prop.',
);

Expand Down
Loading

0 comments on commit 25685d8

Please sign in to comment.