Add Modern WWW build (#18028)
* Build both stable and experimental WWW builds * Flip already experimental WWW flags to true * Remove FB-specific internals from modern FB builds We think we're not going to need these. * Disable classic features in modern WWW builds * Disable legacy ReactDOM API for modern WWW build * Don’t include user timing in prod * Fix bad copy paste and add missing flags to test renderer * Add testing WWW feature flag file We need it because WWW has a different meaning of experimental now.
Dan Abramov committed
Feb 13, 2020 at 20:33 UTC
8777b44e982e7ddedda62aee02f1fd370795db44
14 files changed
+143
-49
packages/react-dom/src/client/ReactDOM.js
+8
-6
@@ -56,6 +56,7 @@ import ReactVersion from 'shared/ReactVersion';
56
import invariant from 'shared/invariant';
57
import {
58
exposeConcurrentModeAPIs,
59
+ disableLegacyReactDOMAPIs,
60
disableUnstableCreatePortal,
61
disableUnstableRenderSubtreeIntoContainer,
62
warnUnstableRenderSubtreeIntoContainer,
@@ -133,12 +134,6 @@ function createPortal(
134
const ReactDOM: Object = {
135
createPortal,
136
136
- // Legacy
137
- findDOMNode,
138
- hydrate,
139
- render,
140
- unmountComponentAtNode,
141
-
137
unstable_batchedUpdates: batchedUpdates,
138
139
flushSync: flushSync,
@@ -166,6 +161,13 @@ const ReactDOM: Object = {
161
version: ReactVersion,
162
};
163
164
+if (!disableLegacyReactDOMAPIs) {
165
+ ReactDOM.findDOMNode = findDOMNode;
166
+ ReactDOM.hydrate = hydrate;
167
+ ReactDOM.render = render;
168
+ ReactDOM.unmountComponentAtNode = unmountComponentAtNode;
169
+}
170
+
171
if (exposeConcurrentModeAPIs) {
172
ReactDOM.createRoot = createRoot;
173
ReactDOM.createBlockingRoot = createBlockingRoot;
packages/react-dom/src/client/ReactDOMFB.js
+18
-13
@@ -13,19 +13,24 @@ import ReactDOM from './ReactDOM';
13
import {isEnabled} from '../events/ReactBrowserEventEmitter';
14
import {getClosestInstanceFromNode} from './ReactDOMComponentTree';
15
16
-Object.assign(
17
- (ReactDOM.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: any),
18
- {
19
- // These are real internal dependencies that are trickier to remove:
20
- ReactBrowserEventEmitter: {
21
- isEnabled,
16
+if (__EXPERIMENTAL__) {
17
+ // This is a modern WWW build.
18
+ // It should be the same as open source. Don't add new things here.
19
+} else {
20
+ // For classic WWW builds, include a few internals that are already in use.
21
+ Object.assign(
22
+ (ReactDOM.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: any),
23
+ {
24
+ ReactBrowserEventEmitter: {
25
+ isEnabled,
26
+ },
27
+ ReactDOMComponentTree: {
28
+ getClosestInstanceFromNode,
29
+ },
30
+ // Perf experiment
31
+ addUserTimingListener,
32
},
23
- ReactDOMComponentTree: {
24
- getClosestInstanceFromNode,
25
- },
26
- // Perf experiment
27
- addUserTimingListener,
28
- },
29
-);
33
+ );
34
+}
35
36
export default ReactDOM;
packages/react-reconciler/src/ReactFiber.js
+6
-2
@@ -425,7 +425,9 @@ export function createWorkInProgress(
425
426
if (__DEV__) {
427
// DEV-only fields
428
- workInProgress._debugID = current._debugID;
428
+ if (enableUserTimingAPI) {
429
+ workInProgress._debugID = current._debugID;
430
+ }
431
workInProgress._debugSource = current._debugSource;
432
workInProgress._debugOwner = current._debugOwner;
433
workInProgress._debugHookTypes = current._debugHookTypes;
@@ -958,7 +960,9 @@ export function assignFiberPropertiesInDEV(
960
target.selfBaseDuration = source.selfBaseDuration;
961
target.treeBaseDuration = source.treeBaseDuration;
962
}
961
- target._debugID = source._debugID;
963
+ if (enableUserTimingAPI) {
964
+ target._debugID = source._debugID;
965
+ }
966
target._debugSource = source._debugSource;
967
target._debugOwner = source._debugOwner;
968
target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
packages/shared/ReactFeatureFlags.js
+3
@@ -114,6 +114,9 @@ export const disableLegacyContext = false;
114
// Disables React.createFactory
115
export const disableCreateFactory = false;
116
117
+// Disables hydrate, render, findDOMNode, unmountComponentAtNode
118
+export const disableLegacyReactDOMAPIs = false;
119
+
120
// Disables children for <textarea> elements
121
export const disableTextareaChildren = false;
122
packages/shared/forks/ReactFeatureFlags.native-fb.js
+3
-2
@@ -10,7 +10,7 @@
10
import invariant from 'shared/invariant';
11
12
import typeof * as FeatureFlagsType from 'shared/ReactFeatureFlags';
13
-import typeof * as FeatureFlagsShimType from './ReactFeatureFlags.native-fb';
13
+import typeof * as ExportsType from './ReactFeatureFlags.native-fb';
14
15
// Uncomment to re-export dynamic flags from the fbsource version.
16
export const {
@@ -46,6 +46,7 @@ export const disableSchedulerTimeoutBasedOnReactExpirationTime = false;
46
export const enableTrainModelFix = true;
47
export const enableTrustedTypesIntegration = false;
48
export const disableCreateFactory = false;
49
+export const disableLegacyReactDOMAPIs = false;
50
export const disableTextareaChildren = false;
51
export const disableMapsAsChildren = false;
52
export const disableUnstableRenderSubtreeIntoContainer = false;
@@ -63,4 +64,4 @@ export function addUserTimingListener() {
64
// eslint-disable-next-line no-unused-vars
65
type Check<_X, Y: _X, X: Y = _X> = null;
66
// eslint-disable-next-line no-unused-expressions
66
-(null: Check<FeatureFlagsShimType, FeatureFlagsType>);
67
+(null: Check<ExportsType, FeatureFlagsType>);
packages/shared/forks/ReactFeatureFlags.native-oss.js
+3
-2
@@ -10,7 +10,7 @@
10
import invariant from 'shared/invariant';
11
12
import typeof * as FeatureFlagsType from 'shared/ReactFeatureFlags';
13
-import typeof * as FeatureFlagsShimType from './ReactFeatureFlags.native-oss';
13
+import typeof * as ExportsType from './ReactFeatureFlags.native-oss';
14
15
export const debugRenderPhaseSideEffectsForStrictMode = false;
16
export const enableUserTimingAPI = __DEV__;
@@ -41,6 +41,7 @@ export const enableTrainModelFix = true;
41
export const enableTrustedTypesIntegration = false;
42
export const enableNativeTargetAsInstance = false;
43
export const disableCreateFactory = false;
44
+export const disableLegacyReactDOMAPIs = false;
45
export const disableTextareaChildren = false;
46
export const disableMapsAsChildren = false;
47
export const disableUnstableRenderSubtreeIntoContainer = false;
@@ -58,4 +59,4 @@ export function addUserTimingListener() {
59
// eslint-disable-next-line no-unused-vars
60
type Check<_X, Y: _X, X: Y = _X> = null;
61
// eslint-disable-next-line no-unused-expressions
61
-(null: Check<FeatureFlagsShimType, FeatureFlagsType>);
62
+(null: Check<ExportsType, FeatureFlagsType>);
packages/shared/forks/ReactFeatureFlags.persistent.js
+3
-2
@@ -10,7 +10,7 @@
10
import invariant from 'shared/invariant';
11
12
import typeof * as FeatureFlagsType from 'shared/ReactFeatureFlags';
13
-import typeof * as PersistentFeatureFlagsType from './ReactFeatureFlags.persistent';
13
+import typeof * as ExportsType from './ReactFeatureFlags.persistent';
14
15
export const debugRenderPhaseSideEffectsForStrictMode = false;
16
export const enableUserTimingAPI = __DEV__;
@@ -41,6 +41,7 @@ export const enableTrainModelFix = true;
41
export const enableTrustedTypesIntegration = false;
42
export const enableNativeTargetAsInstance = false;
43
export const disableCreateFactory = false;
44
+export const disableLegacyReactDOMAPIs = false;
45
export const disableTextareaChildren = false;
46
export const disableMapsAsChildren = false;
47
export const disableUnstableRenderSubtreeIntoContainer = false;
@@ -58,4 +59,4 @@ export function addUserTimingListener() {
59
// eslint-disable-next-line no-unused-vars
60
type Check<_X, Y: _X, X: Y = _X> = null;
61
// eslint-disable-next-line no-unused-expressions
61
-(null: Check<PersistentFeatureFlagsType, FeatureFlagsType>);
62
+(null: Check<ExportsType, FeatureFlagsType>);
packages/shared/forks/ReactFeatureFlags.test-renderer.js
+3
-2
@@ -10,7 +10,7 @@
10
import invariant from 'shared/invariant';
11
12
import typeof * as FeatureFlagsType from 'shared/ReactFeatureFlags';
13
-import typeof * as PersistentFeatureFlagsType from './ReactFeatureFlags.persistent';
13
+import typeof * as ExportsType from './ReactFeatureFlags.test-renderer';
14
15
export const debugRenderPhaseSideEffectsForStrictMode = false;
16
export const enableUserTimingAPI = __DEV__;
@@ -41,6 +41,7 @@ export const enableTrainModelFix = true;
41
export const enableTrustedTypesIntegration = false;
42
export const enableNativeTargetAsInstance = false;
43
export const disableCreateFactory = false;
44
+export const disableLegacyReactDOMAPIs = false;
45
export const disableTextareaChildren = false;
46
export const disableMapsAsChildren = false;
47
export const disableUnstableRenderSubtreeIntoContainer = false;
@@ -58,4 +59,4 @@ export function addUserTimingListener() {
59
// eslint-disable-next-line no-unused-vars
60
type Check<_X, Y: _X, X: Y = _X> = null;
61
// eslint-disable-next-line no-unused-expressions
61
-(null: Check<PersistentFeatureFlagsType, FeatureFlagsType>);
62
+(null: Check<ExportsType, FeatureFlagsType>);
packages/shared/forks/ReactFeatureFlags.test-renderer.www.js
+5
-2
@@ -10,7 +10,7 @@
10
import invariant from 'shared/invariant';
11
12
import typeof * as FeatureFlagsType from 'shared/ReactFeatureFlags';
13
-import typeof * as PersistentFeatureFlagsType from './ReactFeatureFlags.persistent';
13
+import typeof * as ExportsType from './ReactFeatureFlags.test-renderer.www';
14
15
export const debugRenderPhaseSideEffectsForStrictMode = false;
16
export const enableUserTimingAPI = __DEV__;
@@ -22,8 +22,10 @@ export const enableSuspenseServerRenderer = false;
22
export const enableSelectiveHydration = false;
23
export const enableChunksAPI = false;
24
export const exposeConcurrentModeAPIs = __EXPERIMENTAL__;
25
+export const warnAboutShorthandPropertyCollision = true;
26
export const enableSchedulerDebugging = false;
27
export const disableJavaScriptURLs = false;
28
+export const disableInputAttributeSyncing = false;
29
export const enableDeprecatedFlareAPI = true;
30
export const enableFundamentalAPI = false;
31
export const enableScopeAPI = true;
@@ -39,6 +41,7 @@ export const enableTrainModelFix = true;
41
export const enableTrustedTypesIntegration = false;
42
export const enableNativeTargetAsInstance = false;
43
export const disableCreateFactory = false;
44
+export const disableLegacyReactDOMAPIs = false;
45
export const disableTextareaChildren = false;
46
export const disableMapsAsChildren = false;
47
export const disableUnstableRenderSubtreeIntoContainer = false;
@@ -56,4 +59,4 @@ export function addUserTimingListener() {
59
// eslint-disable-next-line no-unused-vars
60
type Check<_X, Y: _X, X: Y = _X> = null;
61
// eslint-disable-next-line no-unused-expressions
59
-(null: Check<PersistentFeatureFlagsType, FeatureFlagsType>);
62
+(null: Check<ExportsType, FeatureFlagsType>);
packages/shared/forks/ReactFeatureFlags.testing.js
+3
-2
@@ -10,7 +10,7 @@
10
import invariant from 'shared/invariant';
11
12
import typeof * as FeatureFlagsType from 'shared/ReactFeatureFlags';
13
-import typeof * as PersistentFeatureFlagsType from './ReactFeatureFlags.persistent';
13
+import typeof * as ExportsType from './ReactFeatureFlags.testing';
14
15
export const debugRenderPhaseSideEffectsForStrictMode = false;
16
export const enableUserTimingAPI = __DEV__;
@@ -41,6 +41,7 @@ export const enableTrainModelFix = true;
41
export const enableTrustedTypesIntegration = false;
42
export const enableNativeTargetAsInstance = false;
43
export const disableCreateFactory = false;
44
+export const disableLegacyReactDOMAPIs = false;
45
export const disableTextareaChildren = false;
46
export const disableMapsAsChildren = false;
47
export const disableUnstableRenderSubtreeIntoContainer = false;
@@ -58,4 +59,4 @@ export function addUserTimingListener() {
59
// eslint-disable-next-line no-unused-vars
60
type Check<_X, Y: _X, X: Y = _X> = null;
61
// eslint-disable-next-line no-unused-expressions
61
-(null: Check<PersistentFeatureFlagsType, FeatureFlagsType>);
62
+(null: Check<ExportsType, FeatureFlagsType>);
packages/shared/forks/ReactFeatureFlags.testing.www.js
new
+62
@@ -0,0 +1,62 @@
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 ExportsType from './ReactFeatureFlags.testing.www';
14
+
15
+export const debugRenderPhaseSideEffectsForStrictMode = false;
16
+export const enableUserTimingAPI = false;
17
+export const warnAboutDeprecatedLifecycles = true;
18
+export const replayFailedUnitOfWorkWithInvokeGuardedCallback = false;
19
+export const enableProfilerTimer = false;
20
+export const enableSchedulerTracing = false;
21
+export const enableSuspenseServerRenderer = true;
22
+export const enableSelectiveHydration = true;
23
+export const enableChunksAPI = true;
24
+export const disableJavaScriptURLs = true;
25
+export const disableInputAttributeSyncing = false;
26
+export const exposeConcurrentModeAPIs = true;
27
+export const warnAboutShorthandPropertyCollision = true;
28
+export const enableSchedulerDebugging = false;
29
+export const enableDeprecatedFlareAPI = true;
30
+export const enableFundamentalAPI = false;
31
+export const enableScopeAPI = true;
32
+export const enableJSXTransformAPI = true;
33
+export const warnAboutUnmockedScheduler = true;
34
+export const flushSuspenseFallbacksInTests = true;
35
+export const enableSuspenseCallback = true;
36
+export const warnAboutDefaultPropsOnFunctionComponents = false;
37
+export const warnAboutStringRefs = false;
38
+export const disableLegacyContext = __EXPERIMENTAL__;
39
+export const disableSchedulerTimeoutBasedOnReactExpirationTime = false;
40
+export const enableTrainModelFix = true;
41
+export const enableTrustedTypesIntegration = false;
42
+export const enableNativeTargetAsInstance = false;
43
+export const disableCreateFactory = __EXPERIMENTAL__;
44
+export const disableLegacyReactDOMAPIs = __EXPERIMENTAL__;
45
+export const disableTextareaChildren = __EXPERIMENTAL__;
46
+export const disableMapsAsChildren = __EXPERIMENTAL__;
47
+export const disableUnstableRenderSubtreeIntoContainer = __EXPERIMENTAL__;
48
+export const warnUnstableRenderSubtreeIntoContainer = false;
49
+export const disableUnstableCreatePortal = __EXPERIMENTAL__;
50
+export const deferPassiveEffectCleanupDuringUnmount = false;
51
+export const isTestEnvironment = true;
52
+
53
+// Only used in www builds.
54
+export function addUserTimingListener() {
55
+ invariant(false, 'Not implemented.');
56
+}
57
+
58
+// Flow magic to verify the exports of this file match the original version.
59
+// eslint-disable-next-line no-unused-vars
60
+type Check<_X, Y: _X, X: Y = _X> = null;
61
+// eslint-disable-next-line no-unused-expressions
62
+(null: Check<ExportsType, FeatureFlagsType>);
packages/shared/forks/ReactFeatureFlags.www.js
+16
-11
@@ -8,7 +8,7 @@
8
*/
9
10
import typeof * as FeatureFlagsType from 'shared/ReactFeatureFlags';
11
-import typeof * as FeatureFlagsShimType from './ReactFeatureFlags.www';
11
+import typeof * as ExportsType from './ReactFeatureFlags.www';
12
13
// Re-export dynamic flags from the www version.
14
export const {
@@ -19,13 +19,16 @@ export const {
19
warnAboutShorthandPropertyCollision,
20
} = require('ReactFeatureFlags');
21
22
+// On WWW, __EXPERIMENTAL__ is used for a new modern build.
23
+// It's not used anywhere in production yet.
24
+
25
// In www, we have experimental support for gathering data
26
// from User Timing API calls in production. By default, we
27
// only emit performance.mark/measure calls in __DEV__. But if
28
// somebody calls addUserTimingListener() which is exposed as an
29
// experimental FB-only export, we call performance.mark/measure
30
// as long as there is more than a single listener.
28
-export let enableUserTimingAPI = __DEV__;
31
+export let enableUserTimingAPI = __DEV__ && !__EXPERIMENTAL__;
32
33
export const enableProfilerTimer = __PROFILE__;
34
export const enableSchedulerTracing = __PROFILE__;
@@ -33,19 +36,19 @@ export const enableSchedulerDebugging = true;
36
37
export const replayFailedUnitOfWorkWithInvokeGuardedCallback = false;
38
export const warnAboutDeprecatedLifecycles = true;
36
-export const disableLegacyContext = false;
39
+export const disableLegacyContext = __EXPERIMENTAL__;
40
export const warnAboutStringRefs = false;
41
export const warnAboutDefaultPropsOnFunctionComponents = false;
42
export const disableSchedulerTimeoutBasedOnReactExpirationTime = false;
43
44
export const enableTrainModelFix = true;
45
43
-export const exposeConcurrentModeAPIs = __EXPERIMENTAL__;
46
+export const exposeConcurrentModeAPIs = true;
47
48
export const enableSuspenseServerRenderer = true;
49
export const enableSelectiveHydration = true;
50
48
-export const enableChunksAPI = __EXPERIMENTAL__;
51
+export const enableChunksAPI = true;
52
53
export const disableJavaScriptURLs = true;
54
@@ -92,17 +95,19 @@ export const flushSuspenseFallbacksInTests = true;
95
96
export const enableNativeTargetAsInstance = false;
97
95
-export const disableCreateFactory = false;
98
+export const disableCreateFactory = __EXPERIMENTAL__;
99
+
100
+export const disableLegacyReactDOMAPIs = __EXPERIMENTAL__;
101
97
-export const disableTextareaChildren = false;
102
+export const disableTextareaChildren = __EXPERIMENTAL__;
103
99
-export const disableMapsAsChildren = false;
104
+export const disableMapsAsChildren = __EXPERIMENTAL__;
105
101
-export const disableUnstableRenderSubtreeIntoContainer = false;
106
+export const disableUnstableRenderSubtreeIntoContainer = __EXPERIMENTAL__;
107
108
export const warnUnstableRenderSubtreeIntoContainer = false;
109
105
-export const disableUnstableCreatePortal = false;
110
+export const disableUnstableCreatePortal = __EXPERIMENTAL__;
111
112
export const isTestEnvironment = false;
113
@@ -110,4 +115,4 @@ export const isTestEnvironment = false;
115
// eslint-disable-next-line no-unused-vars
116
type Check<_X, Y: _X, X: Y = _X> = null;
117
// eslint-disable-next-line no-unused-expressions
113
-(null: Check<FeatureFlagsShimType, FeatureFlagsType>);
118
+(null: Check<ExportsType, FeatureFlagsType>);
scripts/rollup/build.js
+4
-4
@@ -679,17 +679,17 @@ async function buildEverything() {
679
[bundle, NODE_DEV],
680
[bundle, NODE_PROD],
681
[bundle, NODE_PROFILING],
682
+ [bundle, FB_WWW_DEV],
683
+ [bundle, FB_WWW_PROD],
684
+ [bundle, FB_WWW_PROFILING],
685
[bundle, RN_OSS_DEV],
686
[bundle, RN_OSS_PROD],
687
[bundle, RN_OSS_PROFILING]
688
);
689
690
if (__EXPERIMENTAL__) {
688
- // FB specific builds are experimental-only.
691
+ // FB-specific RN builds are experimental-only.
692
bundles.push(
690
- [bundle, FB_WWW_DEV],
691
- [bundle, FB_WWW_PROD],
692
- [bundle, FB_WWW_PROFILING],
693
[bundle, RN_FB_DEV],
694
[bundle, RN_FB_PROD],
695
[bundle, RN_FB_PROFILING]
scripts/rollup/forks.js
+6
-1
@@ -107,8 +107,13 @@ const forks = Object.freeze({
107
}
108
return 'shared/forks/ReactFeatureFlags.test-renderer.js';
109
case 'react-dom/testing':
110
- return 'shared/forks/ReactFeatureFlags.testing.js';
110
case 'react/testing':
111
+ switch (bundleType) {
112
+ case FB_WWW_DEV:
113
+ case FB_WWW_PROD:
114
+ case FB_WWW_PROFILING:
115
+ return 'shared/forks/ReactFeatureFlags.testing.www.js';
116
+ }
117
return 'shared/forks/ReactFeatureFlags.testing.js';
118
default:
119
switch (bundleType) {