Skip to content

Commit fb3f7bf

Browse files
authored
Avoid importing Scheduler directly (#14757)
* Avoid importing Scheduler directly The reconciler should not depend directly on Scheduler. This adds it to the host config for the renderer instead. (Except for `scheduler/tracing` imports, which are used only by the profiling build. I've left those imports as-is, though I'm open to directing those through the host config, too.) * Make throwaway root id longer to appease Brian
1 parent 81470a0 commit fb3f7bf

File tree

9 files changed

+84
-61
lines changed

9 files changed

+84
-61
lines changed

packages/react-art/src/ReactARTHostConfig.js

+6
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,10 @@
55
* LICENSE file in the root directory of this source tree.
66
*/
77

8+
import {
9+
unstable_scheduleCallback as scheduleDeferredCallback,
10+
unstable_cancelCallback as cancelDeferredCallback,
11+
} from 'scheduler';
812
export {
913
unstable_now as now,
1014
unstable_scheduleCallback as scheduleDeferredCallback,
@@ -337,6 +341,8 @@ export function getChildHostContext() {
337341
export const scheduleTimeout = setTimeout;
338342
export const cancelTimeout = clearTimeout;
339343
export const noTimeout = -1;
344+
export const schedulePassiveEffects = scheduleDeferredCallback;
345+
export const cancelPassiveEffects = cancelDeferredCallback;
340346

341347
export function shouldSetTextContent(type, props) {
342348
return (

packages/react-dom/src/client/ReactDOMHostConfig.js

+6
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,10 @@ export type ChildSet = void; // Unused
6969
export type TimeoutHandle = TimeoutID;
7070
export type NoTimeout = -1;
7171

72+
import {
73+
unstable_scheduleCallback as scheduleDeferredCallback,
74+
unstable_cancelCallback as cancelDeferredCallback,
75+
} from 'scheduler';
7276
export {
7377
unstable_now as now,
7478
unstable_scheduleCallback as scheduleDeferredCallback,
@@ -296,6 +300,8 @@ export const scheduleTimeout =
296300
export const cancelTimeout =
297301
typeof clearTimeout === 'function' ? clearTimeout : (undefined: any);
298302
export const noTimeout = -1;
303+
export const schedulePassiveEffects = scheduleDeferredCallback;
304+
export const cancelPassiveEffects = cancelDeferredCallback;
299305

300306
// -------------------
301307
// Mutation

packages/react-native-renderer/src/ReactFabricHostConfig.js

+2
Original file line numberDiff line numberDiff line change
@@ -330,6 +330,8 @@ export const shouldYield = ReactNativeFrameSchedulingShouldYield;
330330
export const scheduleTimeout = setTimeout;
331331
export const cancelTimeout = clearTimeout;
332332
export const noTimeout = -1;
333+
export const schedulePassiveEffects = scheduleDeferredCallback;
334+
export const cancelPassiveEffects = cancelDeferredCallback;
333335

334336
// -------------------
335337
// Persistence

packages/react-native-renderer/src/ReactNativeHostConfig.js

+2
Original file line numberDiff line numberDiff line change
@@ -243,6 +243,8 @@ export const shouldYield = ReactNativeFrameSchedulingShouldYield;
243243
export const scheduleTimeout = setTimeout;
244244
export const cancelTimeout = clearTimeout;
245245
export const noTimeout = -1;
246+
export const schedulePassiveEffects = scheduleDeferredCallback;
247+
export const cancelPassiveEffects = cancelDeferredCallback;
246248

247249
export function shouldDeprioritizeSubtree(type: string, props: Props): boolean {
248250
return false;

packages/react-noop-renderer/src/createReactNoop.js

+26
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ if (__DEV__) {
4747
function createReactNoop(reconciler: Function, useMutation: boolean) {
4848
let scheduledCallback = null;
4949
let scheduledCallbackTimeout = -1;
50+
let scheduledPassiveCallback = null;
5051
let instanceCounter = 0;
5152
let hostDiffCounter = 0;
5253
let hostUpdateCounter = 0;
@@ -338,6 +339,21 @@ function createReactNoop(reconciler: Function, useMutation: boolean) {
338339
scheduleTimeout: setTimeout,
339340
cancelTimeout: clearTimeout,
340341
noTimeout: -1,
342+
schedulePassiveEffects(callback) {
343+
if (scheduledCallback) {
344+
throw new Error(
345+
'Scheduling a callback twice is excessive. Instead, keep track of ' +
346+
'whether the callback has already been scheduled.',
347+
);
348+
}
349+
scheduledPassiveCallback = callback;
350+
},
351+
cancelPassiveEffects() {
352+
if (scheduledPassiveCallback === null) {
353+
throw new Error('No passive effects callback is scheduled.');
354+
}
355+
scheduledPassiveCallback = null;
356+
},
341357

342358
prepareForCommit(): void {},
343359

@@ -854,6 +870,16 @@ function createReactNoop(reconciler: Function, useMutation: boolean) {
854870
return yieldedValues;
855871
},
856872

873+
flushPassiveEffects() {
874+
// Trick to flush passive effects without exposing an internal API:
875+
// Create a throwaway root and schedule a dummy update on it.
876+
const rootID = 'bloopandthenmoreletterstoavoidaconflict';
877+
const container = {rootID: rootID, children: []};
878+
rootContainers.set(rootID, container);
879+
const root = NoopRenderer.createContainer(container, true, false);
880+
NoopRenderer.updateContainer(null, root, null, null);
881+
},
882+
857883
// Logs the current state of the tree.
858884
dumpTree(rootID: string = DEFAULT_ROOT_ID) {
859885
const root = roots.get(rootID);

packages/react-reconciler/src/ReactFiberScheduler.js

+6-6
Original file line numberDiff line numberDiff line change
@@ -17,10 +17,6 @@ import {
1717
__subscriberRef,
1818
unstable_wrap as Schedule_tracing_wrap,
1919
} from 'scheduler/tracing';
20-
import {
21-
unstable_scheduleCallback as Schedule_scheduleCallback,
22-
unstable_cancelCallback as Schedule_cancelCallback,
23-
} from 'scheduler';
2420
import {
2521
invokeGuardedCallback,
2622
hasCaughtError,
@@ -83,6 +79,8 @@ import {
8379
scheduleTimeout,
8480
cancelTimeout,
8581
noTimeout,
82+
schedulePassiveEffects,
83+
cancelPassiveEffects,
8684
} from './ReactFiberHostConfig';
8785
import {
8886
markPendingPriorityLevel,
@@ -587,8 +585,10 @@ function markLegacyErrorBoundaryAsFailed(instance: mixed) {
587585
}
588586

589587
function flushPassiveEffects() {
588+
if (passiveEffectCallbackHandle !== null) {
589+
cancelPassiveEffects(passiveEffectCallbackHandle);
590+
}
590591
if (passiveEffectCallback !== null) {
591-
Schedule_cancelCallback(passiveEffectCallbackHandle);
592592
// We call the scheduled callback instead of commitPassiveEffects directly
593593
// to ensure tracing works correctly.
594594
passiveEffectCallback();
@@ -795,7 +795,7 @@ function commitRoot(root: FiberRoot, finishedWork: Fiber): void {
795795
// here because that code is still in flux.
796796
callback = Schedule_tracing_wrap(callback);
797797
}
798-
passiveEffectCallbackHandle = Schedule_scheduleCallback(callback);
798+
passiveEffectCallbackHandle = schedulePassiveEffects(callback);
799799
passiveEffectCallback = callback;
800800
}
801801

0 commit comments

Comments
 (0)