make testing builds for React/ReactDOM (#17915)
This PR introduces adds `react/testing` and `react-dom/testing`. - changes infra to generate these builds - exports act on ReactDOM in these testing builds - uses the new test builds in fixtures/dom In the next PR - - I'll use the new builds for all our own tests - I'll replace usages of TestUtils.act with ReactDOM.act.
Sunil Pai committed
Feb 3, 2020 at 23:31 UTC
3e9251d605692e6db6103e4fca9771ac30a62247
26 files changed
+474
-494
fixtures/dom/src/__tests__/nested-act-test.js
+12
-7
@@ -8,18 +8,23 @@
8
*/
9
10
let React;
11
-let TestUtils;
11
+let ReactDOM;
12
let TestRenderer;
13
14
global.__DEV__ = process.env.NODE_ENV !== 'production';
15
16
+jest.mock('react-dom', () =>
17
+ require.requireActual('react-dom/cjs/react-dom-testing.development.js')
18
+);
19
+// we'll replace the above with react/testing and react-dom/testing right before the next minor
20
+
21
expect.extend(require('../toWarnDev'));
22
23
describe('unmocked scheduler', () => {
24
beforeEach(() => {
25
jest.resetModules();
26
React = require('react');
22
- TestUtils = require('react-dom/test-utils');
27
+ ReactDOM = require('react-dom');
28
TestRenderer = require('react-test-renderer');
29
});
30
@@ -33,7 +38,7 @@ describe('unmocked scheduler', () => {
38
}
39
// in legacy mode, this tests whether an act only flushes its own effects
40
TestRenderer.act(() => {
36
- TestUtils.act(() => {
41
+ ReactDOM.act(() => {
42
TestRenderer.create(<Effecty />);
43
});
44
expect(log).toEqual([]);
@@ -42,7 +47,7 @@ describe('unmocked scheduler', () => {
47
48
log = [];
49
// for doublechecking, we flip it inside out, and assert on the outermost
45
- TestUtils.act(() => {
50
+ ReactDOM.act(() => {
51
TestRenderer.act(() => {
52
TestRenderer.create(<Effecty />);
53
});
@@ -59,7 +64,7 @@ describe('mocked scheduler', () => {
64
require.requireActual('scheduler/unstable_mock')
65
);
66
React = require('react');
62
- TestUtils = require('react-dom/test-utils');
67
+ ReactDOM = require('react-dom');
68
TestRenderer = require('react-test-renderer');
69
});
70
@@ -77,7 +82,7 @@ describe('mocked scheduler', () => {
82
}
83
// with a mocked scheduler, this tests whether it flushes all work only on the outermost act
84
TestRenderer.act(() => {
80
- TestUtils.act(() => {
85
+ ReactDOM.act(() => {
86
TestRenderer.create(<Effecty />);
87
});
88
expect(log).toEqual([]);
@@ -86,7 +91,7 @@ describe('mocked scheduler', () => {
91
92
log = [];
93
// for doublechecking, we flip it inside out, and assert on the outermost
89
- TestUtils.act(() => {
94
+ ReactDOM.act(() => {
95
TestRenderer.act(() => {
96
TestRenderer.create(<Effecty />);
97
});
fixtures/dom/src/__tests__/wrong-act-test.js
+16
-13
@@ -12,13 +12,17 @@ let ReactDOM;
12
let ReactART;
13
let ARTSVGMode;
14
let ARTCurrentMode;
15
-let TestUtils;
15
let TestRenderer;
16
let ARTTest;
17
18
global.__DEV__ = process.env.NODE_ENV !== 'production';
19
global.__EXPERIMENTAL__ = process.env.RELEASE_CHANNEL === 'experimental';
20
21
+jest.mock('react-dom', () =>
22
+ require.requireActual('react-dom/cjs/react-dom-testing.development.js')
23
+);
24
+// we'll replace the above with react/testing and react-dom/testing right before the next minor
25
+
26
expect.extend(require('../toWarnDev'));
27
28
function App(props) {
@@ -32,7 +36,6 @@ beforeEach(() => {
36
ReactART = require('react-art');
37
ARTSVGMode = require('art/modes/svg');
38
ARTCurrentMode = require('art/modes/current');
35
- TestUtils = require('react-dom/test-utils');
39
TestRenderer = require('react-test-renderer');
40
41
ARTCurrentMode.setCurrent(ARTSVGMode);
@@ -70,8 +73,8 @@ beforeEach(() => {
73
});
74
75
it("doesn't warn when you use the right act + renderer: dom", () => {
73
- TestUtils.act(() => {
74
- TestUtils.renderIntoDocument(<App />);
76
+ ReactDOM.act(() => {
77
+ ReactDOM.render(<App />, document.createElement('div'));
78
});
79
});
80
@@ -86,7 +89,7 @@ it('resets correctly across renderers', () => {
89
React.useEffect(() => {}, []);
90
return null;
91
}
89
- TestUtils.act(() => {
92
+ ReactDOM.act(() => {
93
TestRenderer.act(() => {});
94
expect(() => {
95
TestRenderer.create(<Effecty />);
@@ -99,7 +102,7 @@ it('resets correctly across renderers', () => {
102
it('warns when using the wrong act version - test + dom: render', () => {
103
expect(() => {
104
TestRenderer.act(() => {
102
- TestUtils.renderIntoDocument(<App />);
105
+ ReactDOM.render(<App />, document.createElement('div'));
106
});
107
}).toWarnDev(["It looks like you're using the wrong act()"], {
108
withoutStack: true,
@@ -113,7 +116,7 @@ it('warns when using the wrong act version - test + dom: updates', () => {
116
setCtr = _setCtr;
117
return ctr;
118
}
116
- TestUtils.renderIntoDocument(<Counter />);
119
+ ReactDOM.render(<Counter />, document.createElement('div'));
120
expect(() => {
121
TestRenderer.act(() => {
122
setCtr(1);
@@ -123,7 +126,7 @@ it('warns when using the wrong act version - test + dom: updates', () => {
126
127
it('warns when using the wrong act version - dom + test: .create()', () => {
128
expect(() => {
126
- TestUtils.act(() => {
129
+ ReactDOM.act(() => {
130
TestRenderer.create(<App />);
131
});
132
}).toWarnDev(["It looks like you're using the wrong act()"], {
@@ -134,7 +137,7 @@ it('warns when using the wrong act version - dom + test: .create()', () => {
137
it('warns when using the wrong act version - dom + test: .update()', () => {
138
const root = TestRenderer.create(<App key="one" />);
139
expect(() => {
137
- TestUtils.act(() => {
140
+ ReactDOM.act(() => {
141
root.update(<App key="two" />);
142
});
143
}).toWarnDev(["It looks like you're using the wrong act()"], {
@@ -151,15 +154,15 @@ it('warns when using the wrong act version - dom + test: updates', () => {
154
}
155
TestRenderer.create(<Counter />);
156
expect(() => {
154
- TestUtils.act(() => {
157
+ ReactDOM.act(() => {
158
setCtr(1);
159
});
160
}).toWarnDev(["It looks like you're using the wrong act()"]);
161
});
162
163
it('does not warn when nesting react-act inside react-dom', () => {
161
- TestUtils.act(() => {
162
- TestUtils.renderIntoDocument(<ARTTest />);
164
+ ReactDOM.act(() => {
165
+ ReactDOM.render(<ARTTest />, document.createElement('div'));
166
});
167
});
168
@@ -171,7 +174,7 @@ it('does not warn when nesting react-act inside react-test-renderer', () => {
174
175
it("doesn't warn if you use nested acts from different renderers", () => {
176
TestRenderer.act(() => {
174
- TestUtils.act(() => {
177
+ ReactDOM.act(() => {
178
TestRenderer.create(<App />);
179
});
180
});
packages/react-dom/npm/testing.js
new
+38
@@ -0,0 +1,38 @@
1
+'use strict';
2
+
3
+function checkDCE() {
4
+ /* global __REACT_DEVTOOLS_GLOBAL_HOOK__ */
5
+ if (
6
+ typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === 'undefined' ||
7
+ typeof __REACT_DEVTOOLS_GLOBAL_HOOK__.checkDCE !== 'function'
8
+ ) {
9
+ return;
10
+ }
11
+ if (process.env.NODE_ENV !== 'production') {
12
+ // This branch is unreachable because this function is only called
13
+ // in production, but the condition is true only in development.
14
+ // Therefore if the branch is still here, dead code elimination wasn't
15
+ // properly applied.
16
+ // Don't change the message. React DevTools relies on it. Also make sure
17
+ // this message doesn't occur elsewhere in this function, or it will cause
18
+ // a false positive.
19
+ throw new Error('^_^');
20
+ }
21
+ try {
22
+ // Verify that the code above has been dead code eliminated (DCE'd).
23
+ __REACT_DEVTOOLS_GLOBAL_HOOK__.checkDCE(checkDCE);
24
+ } catch (err) {
25
+ // DevTools shouldn't crash React, no matter what.
26
+ // We should still report in case we break this code.
27
+ console.error(err);
28
+ }
29
+}
30
+
31
+if (process.env.NODE_ENV === 'production') {
32
+ // DCE check should happen before ReactDOM bundle executes so that
33
+ // DevTools can report bad minification during injection.
34
+ checkDCE();
35
+ module.exports = require('./cjs/react-dom-testing.production.min.js');
36
+} else {
37
+ module.exports = require('./cjs/react-dom-testing.development.js');
38
+}
packages/react-dom/src/__tests__/ReactTestUtilsAct-test.js
+1
@@ -722,6 +722,7 @@ function runActTests(label, render, unmount, rerender) {
722
723
describe('suspense', () => {
724
if (__DEV__ && __EXPERIMENTAL__) {
725
+ // todo - remove __DEV__ check once we start using testing builds
726
it('triggers fallbacks if available', async () => {
727
let resolved = false;
728
let resolve;
packages/react-dom/src/client/ReactDOM.js
+6
@@ -35,6 +35,7 @@ import {
35
attemptUserBlockingHydration,
36
attemptContinuousHydration,
37
attemptHydrationAtCurrentPriority,
38
+ act,
39
} from 'react-reconciler/inline.dom';
40
import {createPortal as createPortalImpl} from 'shared/ReactPortal';
41
import {canUseDOM} from 'shared/ExecutionEnvironment';
@@ -58,6 +59,7 @@ import {
59
disableUnstableCreatePortal,
60
disableUnstableRenderSubtreeIntoContainer,
61
warnUnstableRenderSubtreeIntoContainer,
62
+ isTestEnvironment,
63
} from 'shared/ReactFeatureFlags';
64
65
import {
@@ -251,4 +253,8 @@ if (__DEV__) {
253
}
254
}
255
256
+if (isTestEnvironment) {
257
+ ReactDOM.act = act;
258
+}
259
+
260
export default ReactDOM;
packages/react-dom/testing.js
new
+16
@@ -0,0 +1,16 @@
1
+/**
2
+ * Copyright (c) Facebook, Inc. and its affiliates.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ *
7
+ * @flow
8
+ */
9
+
10
+'use strict';
11
+
12
+const ReactDOM = require('./src/client/ReactDOM');
13
+
14
+// TODO: decide on the top-level export form.
15
+// This is hacky but makes it work with both Rollup and Jest.
16
+module.exports = ReactDOM.default || ReactDOM;
packages/react-noop-renderer/src/createReactNoop.js
+1
-197
@@ -14,7 +14,6 @@
14
* environment.
15
*/
16
17
-import type {Thenable} from 'react-reconciler/src/ReactFiberWorkLoop';
17
import type {Fiber} from 'react-reconciler/src/ReactFiber';
18
import type {UpdateQueue} from 'react-reconciler/src/ReactUpdateQueue';
19
import type {ReactNodeList} from 'shared/ReactTypes';
@@ -23,8 +22,6 @@ import type {RootTag} from 'shared/ReactRootTags';
22
import * as Scheduler from 'scheduler/unstable_mock';
23
import {createPortal} from 'shared/ReactPortal';
24
import {REACT_FRAGMENT_TYPE, REACT_ELEMENT_TYPE} from 'shared/ReactSymbols';
26
-import enqueueTask from 'shared/enqueueTask';
27
-import ReactSharedInternals from 'shared/ReactSharedInternals';
25
import {ConcurrentRoot, BlockingRoot, LegacyRoot} from 'shared/ReactRootTags';
26
27
type Container = {
@@ -60,8 +57,6 @@ type TextInstance = {|
57
|};
58
type HostContext = Object;
59
63
-const {IsSomeRendererActing} = ReactSharedInternals;
64
-
60
const NO_CONTEXT = {};
61
const UPPERCASE_CONTEXT = {};
62
const UPDATE_SIGNAL = {};
@@ -597,197 +592,6 @@ function createReactNoop(reconciler: Function, useMutation: boolean) {
592
const roots = new Map();
593
const DEFAULT_ROOT_ID = '<default>';
594
600
- const {
601
- flushPassiveEffects,
602
- batchedUpdates,
603
- IsThisRendererActing,
604
- } = NoopRenderer;
605
-
606
- // this act() implementation should be exactly the same in
607
- // ReactTestUtilsAct.js, ReactTestRendererAct.js, createReactNoop.js
608
-
609
- const isSchedulerMocked =
610
- typeof Scheduler.unstable_flushAllWithoutAsserting === 'function';
611
- const flushWork =
612
- Scheduler.unstable_flushAllWithoutAsserting ||
613
- function() {
614
- let didFlushWork = false;
615
- while (flushPassiveEffects()) {
616
- didFlushWork = true;
617
- }
618
-
619
- return didFlushWork;
620
- };
621
-
622
- function flushWorkAndMicroTasks(onDone: (err: ?Error) => void) {
623
- try {
624
- flushWork();
625
- enqueueTask(() => {
626
- if (flushWork()) {
627
- flushWorkAndMicroTasks(onDone);
628
- } else {
629
- onDone();
630
- }
631
- });
632
- } catch (err) {
633
- onDone(err);
634
- }
635
- }
636
-
637
- // we track the 'depth' of the act() calls with this counter,
638
- // so we can tell if any async act() calls try to run in parallel.
639
-
640
- let actingUpdatesScopeDepth = 0;
641
- let didWarnAboutUsingActInProd = false;
642
-
643
- function act(callback: () => Thenable) {
644
- if (!__DEV__) {
645
- if (didWarnAboutUsingActInProd === false) {
646
- didWarnAboutUsingActInProd = true;
647
- // eslint-disable-next-line react-internal/no-production-logging
648
- console.error(
649
- 'act(...) is not supported in production builds of React, and might not behave as expected.',
650
- );
651
- }
652
- }
653
- let previousActingUpdatesScopeDepth = actingUpdatesScopeDepth;
654
- let previousIsSomeRendererActing;
655
- let previousIsThisRendererActing;
656
- actingUpdatesScopeDepth++;
657
-
658
- previousIsSomeRendererActing = IsSomeRendererActing.current;
659
- previousIsThisRendererActing = IsThisRendererActing.current;
660
- IsSomeRendererActing.current = true;
661
- IsThisRendererActing.current = true;
662
-
663
- function onDone() {
664
- actingUpdatesScopeDepth--;
665
- IsSomeRendererActing.current = previousIsSomeRendererActing;
666
- IsThisRendererActing.current = previousIsThisRendererActing;
667
- if (__DEV__) {
668
- if (actingUpdatesScopeDepth > previousActingUpdatesScopeDepth) {
669
- // if it's _less than_ previousActingUpdatesScopeDepth, then we can assume the 'other' one has warned
670
- console.error(
671
- 'You seem to have overlapping act() calls, this is not supported. ' +
672
- 'Be sure to await previous act() calls before making a new one. ',
673
- );
674
- }
675
- }
676
- }
677
-
678
- let result;
679
- try {
680
- result = batchedUpdates(callback);
681
- } catch (error) {
682
- // on sync errors, we still want to 'cleanup' and decrement actingUpdatesScopeDepth
683
- onDone();
684
- throw error;
685
- }
686
-
687
- if (
688
- result !== null &&
689
- typeof result === 'object' &&
690
- typeof result.then === 'function'
691
- ) {
692
- // setup a boolean that gets set to true only
693
- // once this act() call is await-ed
694
- let called = false;
695
- if (__DEV__) {
696
- if (typeof Promise !== 'undefined') {
697
- //eslint-disable-next-line no-undef
698
- Promise.resolve()
699
- .then(() => {})
700
- .then(() => {
701
- if (called === false) {
702
- console.error(
703
- 'You called act(async () => ...) without await. ' +
704
- 'This could lead to unexpected testing behaviour, interleaving multiple act ' +
705
- 'calls and mixing their scopes. You should - await act(async () => ...);',
706
- );
707
- }
708
- });
709
- }
710
- }
711
-
712
- // in the async case, the returned thenable runs the callback, flushes
713
- // effects and microtasks in a loop until flushPassiveEffects() === false,
714
- // and cleans up
715
- return {
716
- then(resolve: () => void, reject: (?Error) => void) {
717
- called = true;
718
- result.then(
719
- () => {
720
- if (
721
- actingUpdatesScopeDepth > 1 ||
722
- (isSchedulerMocked === true &&
723
- previousIsSomeRendererActing === true)
724
- ) {
725
- onDone();
726
- resolve();
727
- return;
728
- }
729
- // we're about to exit the act() scope,
730
- // now's the time to flush tasks/effects
731
- flushWorkAndMicroTasks((err: ?Error) => {
732
- onDone();
733
- if (err) {
734
- reject(err);
735
- } else {
736
- resolve();
737
- }
738
- });
739
- },
740
- err => {
741
- onDone();
742
- reject(err);
743
- },
744
- );
745
- },
746
- };
747
- } else {
748
- if (__DEV__) {
749
- if (result !== undefined) {
750
- console.error(
751
- 'The callback passed to act(...) function ' +
752
- 'must return undefined, or a Promise. You returned %s',
753
- result,
754
- );
755
- }
756
- }
757
-
758
- // flush effects until none remain, and cleanup
759
- try {
760
- if (
761
- actingUpdatesScopeDepth === 1 &&
762
- (isSchedulerMocked === false ||
763
- previousIsSomeRendererActing === false)
764
- ) {
765
- // we're about to exit the act() scope,
766
- // now's the time to flush effects
767
- flushWork();
768
- }
769
- onDone();
770
- } catch (err) {
771
- onDone();
772
- throw err;
773
- }
774
-
775
- // in the sync case, the returned thenable only warns *if* await-ed
776
- return {
777
- then(resolve: () => void) {
778
- if (__DEV__) {
779
- console.error(
780
- 'Do not await the result of calling act(...) with sync logic, it is not a Promise.',
781
- );
782
- }
783
- resolve();
784
- },
785
- };
786
- }
787
- }
788
-
789
- // end act() implementation
790
-
595
function childToJSX(child, text) {
596
if (text !== null) {
597
return text;
@@ -1106,7 +910,7 @@ function createReactNoop(reconciler: Function, useMutation: boolean) {
910
911
flushPassiveEffects: NoopRenderer.flushPassiveEffects,
912
1109
- act,
913
+ act: NoopRenderer.act,
914
915
// Logs the current state of the tree.
916
dumpTree(rootID: string = DEFAULT_ROOT_ID) {
packages/react-reconciler/src/ReactFiberReconciler.js
+187
@@ -87,6 +87,11 @@ import {
87
findHostInstancesForRefresh,
88
} from './ReactFiberHotReloading';
89
90
+// used by isTestEnvironment builds
91
+import enqueueTask from 'shared/enqueueTask';
92
+import * as Scheduler from 'scheduler';
93
+// end isTestEnvironment imports
94
+
95
type OpaqueRoot = FiberRoot;
96
97
// 0 is PROD, 1 is DEV.
@@ -535,3 +540,185 @@ export function injectIntoDevTools(devToolsConfig: DevToolsConfig): boolean {
540
getCurrentFiber: __DEV__ ? () => ReactCurrentFiberCurrent : null,
541
});
542
}
543
+
544
+const {IsSomeRendererActing} = ReactSharedInternals;
545
+const isSchedulerMocked =
546
+ typeof Scheduler.unstable_flushAllWithoutAsserting === 'function';
547
+const flushWork =
548
+ Scheduler.unstable_flushAllWithoutAsserting ||
549
+ function() {
550
+ let didFlushWork = false;
551
+ while (flushPassiveEffects()) {
552
+ didFlushWork = true;
553
+ }
554
+
555
+ return didFlushWork;
556
+ };
557
+
558
+function flushWorkAndMicroTasks(onDone: (err: ?Error) => void) {
559
+ try {
560
+ flushWork();
561
+ enqueueTask(() => {
562
+ if (flushWork()) {
563
+ flushWorkAndMicroTasks(onDone);
564
+ } else {
565
+ onDone();
566
+ }
567
+ });
568
+ } catch (err) {
569
+ onDone(err);
570
+ }
571
+}
572
+
573
+// we track the 'depth' of the act() calls with this counter,
574
+// so we can tell if any async act() calls try to run in parallel.
575
+
576
+let actingUpdatesScopeDepth = 0;
577
+let didWarnAboutUsingActInProd = false;
578
+
579
+// eslint-disable-next-line no-inner-declarations
580
+export function act(callback: () => Thenable) {
581
+ if (!__DEV__) {
582
+ if (didWarnAboutUsingActInProd === false) {
583
+ didWarnAboutUsingActInProd = true;
584
+ // eslint-disable-next-line react-internal/no-production-logging
585
+ console.error(
586
+ 'act(...) is not supported in production builds of React, and might not behave as expected.',
587
+ );
588
+ }
589
+ }
590
+
591
+ let previousActingUpdatesScopeDepth = actingUpdatesScopeDepth;
592
+ let previousIsSomeRendererActing;
593
+ let previousIsThisRendererActing;
594
+ actingUpdatesScopeDepth++;
595
+
596
+ previousIsSomeRendererActing = IsSomeRendererActing.current;
597
+ previousIsThisRendererActing = IsThisRendererActing.current;
598
+ IsSomeRendererActing.current = true;
599
+ IsThisRendererActing.current = true;
600
+
601
+ function onDone() {
602
+ actingUpdatesScopeDepth--;
603
+ IsSomeRendererActing.current = previousIsSomeRendererActing;
604
+ IsThisRendererActing.current = previousIsThisRendererActing;
605
+ if (__DEV__) {
606
+ if (actingUpdatesScopeDepth > previousActingUpdatesScopeDepth) {
607
+ // if it's _less than_ previousActingUpdatesScopeDepth, then we can assume the 'other' one has warned
608
+ console.error(
609
+ 'You seem to have overlapping act() calls, this is not supported. ' +
610
+ 'Be sure to await previous act() calls before making a new one. ',
611
+ );
612
+ }
613
+ }
614
+ }
615
+
616
+ let result;
617
+ try {
618
+ result = batchedUpdates(callback);
619
+ } catch (error) {
620
+ // on sync errors, we still want to 'cleanup' and decrement actingUpdatesScopeDepth
621
+ onDone();
622
+ throw error;
623
+ }
624
+
625
+ if (
626
+ result !== null &&
627
+ typeof result === 'object' &&
628
+ typeof result.then === 'function'
629
+ ) {
630
+ // setup a boolean that gets set to true only
631
+ // once this act() call is await-ed
632
+ let called = false;
633
+ if (__DEV__) {
634
+ if (typeof Promise !== 'undefined') {
635
+ //eslint-disable-next-line no-undef
636
+ Promise.resolve()
637
+ .then(() => {})
638
+ .then(() => {
639
+ if (called === false) {
640
+ console.error(
641
+ 'You called act(async () => ...) without await. ' +
642
+ 'This could lead to unexpected testing behaviour, interleaving multiple act ' +
643
+ 'calls and mixing their scopes. You should - await act(async () => ...);',
644
+ );
645
+ }
646
+ });
647
+ }
648
+ }
649
+
650
+ // in the async case, the returned thenable runs the callback, flushes
651
+ // effects and microtasks in a loop until flushPassiveEffects() === false,
652
+ // and cleans up
653
+ return {
654
+ then(resolve: () => void, reject: (?Error) => void) {
655
+ called = true;
656
+ result.then(
657
+ () => {
658
+ if (
659
+ actingUpdatesScopeDepth > 1 ||
660
+ (isSchedulerMocked === true &&
661
+ previousIsSomeRendererActing === true)
662
+ ) {
663
+ onDone();
664
+ resolve();
665
+ return;
666
+ }
667
+ // we're about to exit the act() scope,
668
+ // now's the time to flush tasks/effects
669
+ flushWorkAndMicroTasks((err: ?Error) => {
670
+ onDone();
671
+ if (err) {
672
+ reject(err);
673
+ } else {
674
+ resolve();
675
+ }
676
+ });
677
+ },
678
+ err => {
679
+ onDone();
680
+ reject(err);
681
+ },
682
+ );
683
+ },
684
+ };
685
+ } else {
686
+ if (__DEV__) {
687
+ if (result !== undefined) {
688
+ console.error(
689
+ 'The callback passed to act(...) function ' +
690
+ 'must return undefined, or a Promise. You returned %s',
691
+ result,
692
+ );
693
+ }
694
+ }
695
+
696
+ // flush effects until none remain, and cleanup
697
+ try {
698
+ if (
699
+ actingUpdatesScopeDepth === 1 &&
700
+ (isSchedulerMocked === false || previousIsSomeRendererActing === false)
701
+ ) {
702
+ // we're about to exit the act() scope,
703
+ // now's the time to flush effects
704
+ flushWork();
705
+ }
706
+ onDone();
707
+ } catch (err) {
708
+ onDone();
709
+ throw err;
710
+ }
711
+
712
+ // in the sync case, the returned thenable only warns *if* await-ed
713
+ return {
714
+ then(resolve: () => void) {
715
+ if (__DEV__) {
716
+ console.error(
717
+ 'Do not await the result of calling act(...) with sync logic, it is not a Promise.',
718
+ );
719
+ }
720
+ resolve();
721
+ },
722
+ };
723
+ }
724
+}
packages/react-test-renderer/src/ReactTestRenderer.js
+1
-1
@@ -19,6 +19,7 @@ import {
19
flushSync,
20
injectIntoDevTools,
21
batchedUpdates,
22
+ act,
23
} from 'react-reconciler/inline.test';
24
import {findCurrentFiberUsingSlowPath} from 'react-reconciler/reflection';
25
import {
@@ -42,7 +43,6 @@ import {
43
} from 'shared/ReactWorkTags';
44
import invariant from 'shared/invariant';
45
import ReactVersion from 'shared/ReactVersion';
45
-import act from './ReactTestRendererAct';
46
47
import {getPublicInstance} from './ReactTestHostConfig';
48
import {ConcurrentRoot, LegacyRoot} from 'shared/ReactRootTags';
packages/react-test-renderer/src/ReactTestRendererAct.js
deleted
-204
@@ -1,204 +0,0 @@
1
-/**
2
- * Copyright (c) Facebook, Inc. and its affiliates.
3
- *
4
- * This source code is licensed under the MIT license found in the
5
- * LICENSE file in the root directory of this source tree.
6
- *
7
- * @flow
8
- */
9
-import type {Thenable} from 'react-reconciler/src/ReactFiberWorkLoop';
10
-
11
-import {
12
- batchedUpdates,
13
- flushPassiveEffects,
14
- IsThisRendererActing,
15
-} from 'react-reconciler/inline.test';
16
-import ReactSharedInternals from 'shared/ReactSharedInternals';
17
-import enqueueTask from 'shared/enqueueTask';
18
-import * as Scheduler from 'scheduler';
19
-
20
-const {IsSomeRendererActing} = ReactSharedInternals;
21
-
22
-// this implementation should be exactly the same in
23
-// ReactTestUtilsAct.js, ReactTestRendererAct.js, createReactNoop.js
24
-
25
-const isSchedulerMocked =
26
- typeof Scheduler.unstable_flushAllWithoutAsserting === 'function';
27
-const flushWork =
28
- Scheduler.unstable_flushAllWithoutAsserting ||
29
- function() {
30
- let didFlushWork = false;
31
- while (flushPassiveEffects()) {
32
- didFlushWork = true;
33
- }
34
-
35
- return didFlushWork;
36
- };
37
-
38
-function flushWorkAndMicroTasks(onDone: (err: ?Error) => void) {
39
- try {
40
- flushWork();
41
- enqueueTask(() => {
42
- if (flushWork()) {
43
- flushWorkAndMicroTasks(onDone);
44
- } else {
45
- onDone();
46
- }
47
- });
48
- } catch (err) {
49
- onDone(err);
50
- }
51
-}
52
-
53
-// we track the 'depth' of the act() calls with this counter,
54
-// so we can tell if any async act() calls try to run in parallel.
55
-
56
-let actingUpdatesScopeDepth = 0;
57
-let didWarnAboutUsingActInProd = false;
58
-
59
-function act(callback: () => Thenable) {
60
- if (!__DEV__) {
61
- if (didWarnAboutUsingActInProd === false) {
62
- didWarnAboutUsingActInProd = true;
63
- // eslint-disable-next-line react-internal/no-production-logging
64
- console.error(
65
- 'act(...) is not supported in production builds of React, and might not behave as expected.',
66
- );
67
- }
68
- }
69
- let previousActingUpdatesScopeDepth = actingUpdatesScopeDepth;
70
- let previousIsSomeRendererActing;
71
- let previousIsThisRendererActing;
72
- actingUpdatesScopeDepth++;
73
-
74
- previousIsSomeRendererActing = IsSomeRendererActing.current;
75
- previousIsThisRendererActing = IsThisRendererActing.current;
76
- IsSomeRendererActing.current = true;
77
- IsThisRendererActing.current = true;
78
-
79
- function onDone() {
80
- actingUpdatesScopeDepth--;
81
- IsSomeRendererActing.current = previousIsSomeRendererActing;
82
- IsThisRendererActing.current = previousIsThisRendererActing;
83
- if (__DEV__) {
84
- if (actingUpdatesScopeDepth > previousActingUpdatesScopeDepth) {
85
- // if it's _less than_ previousActingUpdatesScopeDepth, then we can assume the 'other' one has warned
86
- console.error(
87
- 'You seem to have overlapping act() calls, this is not supported. ' +
88
- 'Be sure to await previous act() calls before making a new one. ',
89
- );
90
- }
91
- }
92
- }
93
-
94
- let result;
95
- try {
96
- result = batchedUpdates(callback);
97
- } catch (error) {
98
- // on sync errors, we still want to 'cleanup' and decrement actingUpdatesScopeDepth
99
- onDone();
100
- throw error;
101
- }
102
-
103
- if (
104
- result !== null &&
105
- typeof result === 'object' &&
106
- typeof result.then === 'function'
107
- ) {
108
- // setup a boolean that gets set to true only
109
- // once this act() call is await-ed
110
- let called = false;
111
- if (__DEV__) {
112
- if (typeof Promise !== 'undefined') {
113
- //eslint-disable-next-line no-undef
114
- Promise.resolve()
115
- .then(() => {})
116
- .then(() => {
117
- if (called === false) {
118
- console.error(
119
- 'You called act(async () => ...) without await. ' +
120
- 'This could lead to unexpected testing behaviour, interleaving multiple act ' +
121
- 'calls and mixing their scopes. You should - await act(async () => ...);',
122
- );
123
- }
124
- });
125
- }
126
- }
127
-
128
- // in the async case, the returned thenable runs the callback, flushes
129
- // effects and microtasks in a loop until flushPassiveEffects() === false,
130
- // and cleans up
131
- return {
132
- then(resolve: () => void, reject: (?Error) => void) {
133
- called = true;
134
- result.then(
135
- () => {
136
- if (
137
- actingUpdatesScopeDepth > 1 ||
138
- (isSchedulerMocked === true &&
139
- previousIsSomeRendererActing === true)
140
- ) {
141
- onDone();
142
- resolve();
143
- return;
144
- }
145
- // we're about to exit the act() scope,
146
- // now's the time to flush tasks/effects
147
- flushWorkAndMicroTasks((err: ?Error) => {
148
- onDone();
149
- if (err) {
150
- reject(err);
151
- } else {
152
- resolve();
153
- }
154
- });
155
- },
156
- err => {
157
- onDone();
158
- reject(err);
159
- },
160
- );
161
- },
162
- };
163
- } else {
164
- if (__DEV__) {
165
- if (result !== undefined) {
166
- console.error(
167
- 'The callback passed to act(...) function ' +
168
- 'must return undefined, or a Promise. You returned %s',
169
- result,
170
- );
171
- }
172
- }
173
-
174
- // flush effects until none remain, and cleanup
175
- try {
176
- if (
177
- actingUpdatesScopeDepth === 1 &&
178
- (isSchedulerMocked === false || previousIsSomeRendererActing === false)
179
- ) {
180
- // we're about to exit the act() scope,
181
- // now's the time to flush effects
182
- flushWork();
183
- }
184
- onDone();
185
- } catch (err) {
186
- onDone();
187
- throw err;
188
- }
189
-
190
- // in the sync case, the returned thenable only warns *if* await-ed
191
- return {
192
- then(resolve: () => void) {
193
- if (__DEV__) {
194
- console.error(
195
- 'Do not await the result of calling act(...) with sync logic, it is not a Promise.',
196
- );
197
- }
198
- resolve();
199
- },
200
- };
201
- }
202
-}
203
-
204
-export default act;
packages/react/npm/testing.js
new
+7
@@ -0,0 +1,7 @@
1
+'use strict';
2
+
3
+if (process.env.NODE_ENV === 'production') {
4
+ module.exports = require('./cjs/react-testing.production.min.js');
5
+} else {
6
+ module.exports = require('./cjs/react-testing.development.js');
7
+}
packages/react/testing.js
new
+16
@@ -0,0 +1,16 @@
1
+/**
2
+ * Copyright (c) Facebook, Inc. and its affiliates.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ *
7
+ * @flow
8
+ */
9
+
10
+'use strict';
11
+
12
+const React = require('./src/React');
13
+
14
+// TODO: decide on the top-level export form.
15
+// This is hacky but makes it work with both Rollup and Jest.
16
+module.exports = React.default || React;
packages/shared/ReactFeatureFlags.js
+2
@@ -122,3 +122,5 @@ export const warnUnstableRenderSubtreeIntoContainer = false;
122
123
// Disables ReactDOM.unstable_createPortal
124
export const disableUnstableCreatePortal = false;
125
+
126
+export const isTestEnvironment = false;
packages/shared/enqueueTask.js
+35
-31
@@ -8,37 +8,41 @@
8
*/
9
10
let didWarnAboutMessageChannel = false;
11
-let enqueueTask;
12
-try {
13
- // read require off the module object to get around the bundlers.
14
- // we don't want them to detect a require and bundle a Node polyfill.
15
- let requireString = ('require' + Math.random()).slice(0, 7);
16
- let nodeRequire = module && module[requireString];
17
- // assuming we're in node, let's try to get node's
18
- // version of setImmediate, bypassing fake timers if any.
19
- enqueueTask = nodeRequire('timers').setImmediate;
20
-} catch (_err) {
21
- // we're in a browser
22
- // we can't use regular timers because they may still be faked
23
- // so we try MessageChannel+postMessage instead
24
- enqueueTask = function(callback: () => void) {
25
- if (__DEV__) {
26
- if (didWarnAboutMessageChannel === false) {
27
- didWarnAboutMessageChannel = true;
28
- if (typeof MessageChannel === 'undefined') {
29
- console.error(
30
- 'This browser does not have a MessageChannel implementation, ' +
31
- 'so enqueuing tasks via await act(async () => ...) will fail. ' +
32
- 'Please file an issue at https://github.com/facebook/react/issues ' +
33
- 'if you encounter this warning.',
34
- );
11
+let enqueueTaskImpl = null;
12
+
13
+export default function enqueueTask(task: () => void) {
14
+ if (enqueueTaskImpl === null) {
15
+ try {
16
+ // read require off the module object to get around the bundlers.
17
+ // we don't want them to detect a require and bundle a Node polyfill.
18
+ let requireString = ('require' + Math.random()).slice(0, 7);
19
+ let nodeRequire = module && module[requireString];
20
+ // assuming we're in node, let's try to get node's
21
+ // version of setImmediate, bypassing fake timers if any.
22
+ enqueueTaskImpl = nodeRequire('timers').setImmediate;
23
+ } catch (_err) {
24
+ // we're in a browser
25
+ // we can't use regular timers because they may still be faked
26
+ // so we try MessageChannel+postMessage instead
27
+ enqueueTaskImpl = function(callback: () => void) {
28
+ if (__DEV__) {
29
+ if (didWarnAboutMessageChannel === false) {
30
+ didWarnAboutMessageChannel = true;
31
+ if (typeof MessageChannel === 'undefined') {
32
+ console.error(
33
+ 'This browser does not have a MessageChannel implementation, ' +
34
+ 'so enqueuing tasks via await act(async () => ...) will fail. ' +
35
+ 'Please file an issue at https://github.com/facebook/react/issues ' +
36
+ 'if you encounter this warning.',
37
+ );
38
+ }
39
+ }
40
}
36
- }
41
+ const channel = new MessageChannel();
42
+ channel.port1.onmessage = callback;
43
+ channel.port2.postMessage(undefined);
44
+ };
45
}
38
- const channel = new MessageChannel();
39
- channel.port1.onmessage = callback;
40
- channel.port2.postMessage(undefined);
41
- };
46
+ }
47
+ return enqueueTaskImpl(task);
48
}
43
-
44
-export default enqueueTask;
packages/shared/forks/ReactFeatureFlags.native-fb.js
+1
@@ -51,6 +51,7 @@ export const disableUnstableRenderSubtreeIntoContainer = false;
51
export const warnUnstableRenderSubtreeIntoContainer = false;
52
export const disableUnstableCreatePortal = false;
53
export const deferPassiveEffectCleanupDuringUnmount = false;
54
+export const isTestEnvironment = false;
55
56
// Only used in www builds.
57
export function addUserTimingListener() {
packages/shared/forks/ReactFeatureFlags.native-oss.js
+1
@@ -46,6 +46,7 @@ export const disableUnstableRenderSubtreeIntoContainer = false;
46
export const warnUnstableRenderSubtreeIntoContainer = false;
47
export const disableUnstableCreatePortal = false;
48
export const deferPassiveEffectCleanupDuringUnmount = false;
49
+export const isTestEnvironment = false;
50
51
// Only used in www builds.
52
export function addUserTimingListener() {
packages/shared/forks/ReactFeatureFlags.persistent.js
+1
@@ -46,6 +46,7 @@ export const disableUnstableRenderSubtreeIntoContainer = false;
46
export const warnUnstableRenderSubtreeIntoContainer = false;
47
export const disableUnstableCreatePortal = false;
48
export const deferPassiveEffectCleanupDuringUnmount = false;
49
+export const isTestEnvironment = false;
50
51
// Only used in www builds.
52
export function addUserTimingListener() {
packages/shared/forks/ReactFeatureFlags.test-renderer.js
+1
@@ -46,6 +46,7 @@ export const disableUnstableRenderSubtreeIntoContainer = false;
46
export const warnUnstableRenderSubtreeIntoContainer = false;
47
export const disableUnstableCreatePortal = false;
48
export const deferPassiveEffectCleanupDuringUnmount = false;
49
+export const isTestEnvironment = true; // this should probably *never* change
50
51
// Only used in www builds.
52
export function addUserTimingListener() {
packages/shared/forks/ReactFeatureFlags.test-renderer.www.js
+1
@@ -44,6 +44,7 @@ export const disableUnstableRenderSubtreeIntoContainer = false;
44
export const warnUnstableRenderSubtreeIntoContainer = false;
45
export const disableUnstableCreatePortal = false;
46
export const deferPassiveEffectCleanupDuringUnmount = false;
47
+export const isTestEnvironment = true; // this should probably *never* change
48
49
// Only used in www builds.
50
export function addUserTimingListener() {
packages/shared/forks/ReactFeatureFlags.testing.js
new
+60
@@ -0,0 +1,60 @@
1
+/**
2
+ * Copyright (c) Facebook, Inc. and its affiliates.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ *
7
+ * @flow
8
+ */
9
+
10
+import invariant from 'shared/invariant';
11
+
12
+import typeof * as FeatureFlagsType from 'shared/ReactFeatureFlags';
13
+import typeof * as PersistentFeatureFlagsType from './ReactFeatureFlags.persistent';
14
+
15
+export const debugRenderPhaseSideEffectsForStrictMode = false;
16
+export const enableUserTimingAPI = __DEV__;
17
+export const warnAboutDeprecatedLifecycles = true;
18
+export const replayFailedUnitOfWorkWithInvokeGuardedCallback = false;
19
+export const enableProfilerTimer = __PROFILE__;
20
+export const enableSchedulerTracing = __PROFILE__;
21
+export const enableSuspenseServerRenderer = false;
22
+export const enableSelectiveHydration = false;
23
+export const enableChunksAPI = false;
24
+export const disableJavaScriptURLs = false;
25
+export const disableInputAttributeSyncing = false;
26
+export const exposeConcurrentModeAPIs = __EXPERIMENTAL__;
27
+export const warnAboutShorthandPropertyCollision = false;
28
+export const enableSchedulerDebugging = false;
29
+export const enableDeprecatedFlareAPI = false;
30
+export const enableFundamentalAPI = false;
31
+export const enableScopeAPI = false;
32
+export const enableJSXTransformAPI = false;
33
+export const warnAboutUnmockedScheduler = false;
34
+export const flushSuspenseFallbacksInTests = true;
35
+export const enableSuspenseCallback = false;
36
+export const warnAboutDefaultPropsOnFunctionComponents = false;
37
+export const warnAboutStringRefs = false;
38
+export const disableLegacyContext = false;
39
+export const disableSchedulerTimeoutBasedOnReactExpirationTime = false;
40
+export const enableTrainModelFix = true;
41
+export const enableTrustedTypesIntegration = false;
42
+export const enableNativeTargetAsInstance = false;
43
+export const disableCreateFactory = false;
44
+export const disableTextareaChildren = false;
45
+export const disableUnstableRenderSubtreeIntoContainer = false;
46
+export const warnUnstableRenderSubtreeIntoContainer = false;
47
+export const disableUnstableCreatePortal = false;
48
+export const deferPassiveEffectCleanupDuringUnmount = false;
49
+export const isTestEnvironment = true;
50
+
51
+// Only used in www builds.
52
+export function addUserTimingListener() {
53
+ invariant(false, 'Not implemented.');
54
+}
55
+
56
+// Flow magic to verify the exports of this file match the original version.
57
+// eslint-disable-next-line no-unused-vars
58
+type Check<_X, Y: _X, X: Y = _X> = null;
59
+// eslint-disable-next-line no-unused-expressions
60
+(null: Check<PersistentFeatureFlagsType, FeatureFlagsType>);
packages/shared/forks/ReactFeatureFlags.www.js
+2
@@ -102,6 +102,8 @@ export const warnUnstableRenderSubtreeIntoContainer = false;
102
103
export const disableUnstableCreatePortal = false;
104
105
+export const isTestEnvironment = false;
106
+
107
// Flow magic to verify the exports of this file match the original version.
108
// eslint-disable-next-line no-unused-vars
109
type Check<_X, Y: _X, X: Y = _X> = null;
scripts/rollup/bundles.js
+26
-1
@@ -104,6 +104,31 @@ const bundles = [
104
externals: ['react', 'react-dom'],
105
},
106
107
+ /******* React DOM - Testing *******/
108
+ {
109
+ moduleType: RENDERER,
110
+ bundleTypes: [
111
+ UMD_DEV,
112
+ UMD_PROD,
113
+ UMD_PROFILING,
114
+ NODE_DEV,
115
+ NODE_PROD,
116
+ NODE_PROFILING,
117
+ ],
118
+ entry: 'react-dom/testing',
119
+ global: 'ReactDOM',
120
+ externals: ['react'],
121
+ },
122
+
123
+ /******* React DOM - www - Testing *******/
124
+ {
125
+ moduleType: RENDERER,
126
+ bundleTypes: [FB_WWW_DEV, FB_WWW_PROD, FB_WWW_PROFILING],
127
+ entry: 'react-dom/testing',
128
+ global: 'ReactDOMTesting',
129
+ externals: ['react'],
130
+ },
131
+
132
/* React DOM internals required for react-native-web (e.g., to shim native events from react-dom) */
133
{
134
bundleTypes: [
@@ -517,7 +542,7 @@ const bundles = [
542
externals: [],
543
},
544
520
- /******* ESLint Plugin for Hooks (proposal) *******/
545
+ /******* ESLint Plugin for Hooks *******/
546
{
547
// TODO: it's awkward to create a bundle for this but if we don't, the package
548
// won't get copied. We also can't create just DEV bundle because it contains a
scripts/rollup/forks.js
+21
-17
@@ -1,23 +1,23 @@
1
'use strict';
2
3
-const bundleTypes = require('./bundles').bundleTypes;
4
-const moduleTypes = require('./bundles').moduleTypes;
3
+const {bundleTypes, moduleTypes} = require('./bundles');
4
const inlinedHostConfigs = require('../shared/inlinedHostConfigs');
5
7
-const UMD_DEV = bundleTypes.UMD_DEV;
8
-const UMD_PROD = bundleTypes.UMD_PROD;
9
-const UMD_PROFILING = bundleTypes.UMD_PROFILING;
10
-const FB_WWW_DEV = bundleTypes.FB_WWW_DEV;
11
-const FB_WWW_PROD = bundleTypes.FB_WWW_PROD;
12
-const FB_WWW_PROFILING = bundleTypes.FB_WWW_PROFILING;
13
-const RN_OSS_DEV = bundleTypes.RN_OSS_DEV;
14
-const RN_OSS_PROD = bundleTypes.RN_OSS_PROD;
15
-const RN_OSS_PROFILING = bundleTypes.RN_OSS_PROFILING;
16
-const RN_FB_DEV = bundleTypes.RN_FB_DEV;
17
-const RN_FB_PROD = bundleTypes.RN_FB_PROD;
18
-const RN_FB_PROFILING = bundleTypes.RN_FB_PROFILING;
19
-const RENDERER = moduleTypes.RENDERER;
20
-const RECONCILER = moduleTypes.RECONCILER;
6
+const {
7
+ UMD_DEV,
8
+ UMD_PROD,
9
+ UMD_PROFILING,
10
+ FB_WWW_DEV,
11
+ FB_WWW_PROD,
12
+ FB_WWW_PROFILING,
13
+ RN_OSS_DEV,
14
+ RN_OSS_PROD,
15
+ RN_OSS_PROFILING,
16
+ RN_FB_DEV,
17
+ RN_FB_PROD,
18
+ RN_FB_PROFILING,
19
+} = bundleTypes;
20
+const {RENDERER, RECONCILER} = moduleTypes;
21
22
// If you need to replace a file with another file for a specific environment,
23
// add it to this list with the logic for choosing the right replacement.
@@ -46,7 +46,7 @@ const forks = Object.freeze({
46
// Without this fork, importing `shared/ReactSharedInternals` inside
47
// the `react` package itself would not work due to a cyclical dependency.
48
'shared/ReactSharedInternals': (bundleType, entry, dependencies) => {
49
- if (entry === 'react') {
49
+ if (entry === 'react' || entry === 'react/testing') {
50
return 'react/src/ReactSharedInternals';
51
}
52
if (dependencies.indexOf('react') === -1) {
@@ -106,6 +106,10 @@ const forks = Object.freeze({
106
return 'shared/forks/ReactFeatureFlags.test-renderer.www.js';
107
}
108
return 'shared/forks/ReactFeatureFlags.test-renderer.js';
109
+ case 'react-dom/testing':
110
+ return 'shared/forks/ReactFeatureFlags.testing.js';
111
+ case 'react/testing':
112
+ return 'shared/forks/ReactFeatureFlags.testing.js';
113
default:
114
switch (bundleType) {
115
case FB_WWW_DEV:
scripts/rollup/modules.js
+1
-5
@@ -1,11 +1,7 @@
1
'use strict';
2
3
const forks = require('./forks');
4
-const bundleTypes = require('./bundles').bundleTypes;
5
-
6
-const UMD_DEV = bundleTypes.UMD_DEV;
7
-const UMD_PROD = bundleTypes.UMD_PROD;
8
-const UMD_PROFILING = bundleTypes.UMD_PROFILING;
4
+const {UMD_DEV, UMD_PROD, UMD_PROFILING} = require('./bundles').bundleTypes;
5
6
// For any external that is used in a DEV-only condition, explicitly
7
// specify whether it has side effects during import or not. This lets
scripts/rollup/wrappers.js
+20
-18
@@ -1,25 +1,27 @@
1
'use strict';
2
3
-const Bundles = require('./bundles');
3
+const {bundleTypes, moduleTypes} = require('./bundles');
4
const reactVersion = require('../../package.json').version;
5
6
-const UMD_DEV = Bundles.bundleTypes.UMD_DEV;
7
-const UMD_PROD = Bundles.bundleTypes.UMD_PROD;
8
-const UMD_PROFILING = Bundles.bundleTypes.UMD_PROFILING;
9
-const NODE_DEV = Bundles.bundleTypes.NODE_DEV;
10
-const NODE_PROD = Bundles.bundleTypes.NODE_PROD;
11
-const NODE_PROFILING = Bundles.bundleTypes.NODE_PROFILING;
12
-const FB_WWW_DEV = Bundles.bundleTypes.FB_WWW_DEV;
13
-const FB_WWW_PROD = Bundles.bundleTypes.FB_WWW_PROD;
14
-const FB_WWW_PROFILING = Bundles.bundleTypes.FB_WWW_PROFILING;
15
-const RN_OSS_DEV = Bundles.bundleTypes.RN_OSS_DEV;
16
-const RN_OSS_PROD = Bundles.bundleTypes.RN_OSS_PROD;
17
-const RN_OSS_PROFILING = Bundles.bundleTypes.RN_OSS_PROFILING;
18
-const RN_FB_DEV = Bundles.bundleTypes.RN_FB_DEV;
19
-const RN_FB_PROD = Bundles.bundleTypes.RN_FB_PROD;
20
-const RN_FB_PROFILING = Bundles.bundleTypes.RN_FB_PROFILING;
21
-
22
-const RECONCILER = Bundles.moduleTypes.RECONCILER;
6
+const {
7
+ UMD_DEV,
8
+ UMD_PROD,
9
+ UMD_PROFILING,
10
+ NODE_DEV,
11
+ NODE_PROD,
12
+ NODE_PROFILING,
13
+ FB_WWW_DEV,
14
+ FB_WWW_PROD,
15
+ FB_WWW_PROFILING,
16
+ RN_OSS_DEV,
17
+ RN_OSS_PROD,
18
+ RN_OSS_PROFILING,
19
+ RN_FB_DEV,
20
+ RN_FB_PROD,
21
+ RN_FB_PROFILING,
22
+} = bundleTypes;
23
+
24
+const {RECONCILER} = moduleTypes;
25
26
const license = ` * Copyright (c) Facebook, Inc. and its affiliates.
27
*
scripts/shared/inlinedHostConfigs.js
+1
@@ -11,6 +11,7 @@ module.exports = [
11
shortName: 'dom',
12
entryPoints: [
13
'react-dom',
14
+ 'react-dom/testing',
15
'react-dom/unstable-fizz.node',
16
'react-flight-dom-webpack/server.node',
17
'react-flight-dom-webpack',