Skip to content

Commit

Permalink
Clear finished discrete updates during commit phase
Browse files Browse the repository at this point in the history
If a root is finished at a priority lower than that of the latest pending discrete
updates on it, these updates must have been finished so we can clear them now.
Otherwise, a later call of `flushDiscreteUpdates` would start a new empty render
pass which may cause a scheduled timeout to be cancelled.
  • Loading branch information
jddxf authored and acdlite committed Apr 7, 2020
1 parent 86adec4 commit 60321ba
Show file tree
Hide file tree
Showing 2 changed files with 13 additions and 1 deletion.
13 changes: 13 additions & 0 deletions packages/react-reconciler/src/ReactFiberWorkLoop.js
Original file line number Diff line number Diff line change
Expand Up @@ -1782,6 +1782,19 @@ function commitRootImpl(root, renderPriorityLevel) {
remainingExpirationTimeBeforeCommit,
);

// Clear already finished discrete updates in case that a later call of
// `flushDiscreteUpdates` starts a useless render pass which may cancels
// a scheduled timeout.
if (rootsWithPendingDiscreteUpdates !== null) {
const lastDiscreteTime = rootsWithPendingDiscreteUpdates.get(root);
if (
lastDiscreteTime !== undefined &&
remainingExpirationTimeBeforeCommit < lastDiscreteTime
) {
rootsWithPendingDiscreteUpdates.delete(root);
}
}

if (root === workInProgressRoot) {
// We can reset these now that they are finished.
workInProgressRoot = null;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3634,7 +3634,6 @@ describe('ReactSuspenseWithNoopRenderer', () => {
// Triggers erstwhile bug where flushDiscreteUpdates caused an empty render
// at a previously committed level
ReactNoop.flushDiscreteUpdates();
expect(Scheduler).toFlushAndYield(['A', 'Suspend! [B]', 'Loading...']);

// Commit the placeholder
Scheduler.unstable_advanceTime(2000);
Expand Down

0 comments on commit 60321ba

Please sign in to comment.