Skip to content

Commit 5ad4e79

Browse files
committed
[Fiber] Create virtual Fiber when an error occurs during reconcilation (#29804)
This lets us rethrow it in the conceptual place of the child. There's currently a problem when we suspend or throw in the child fiber reconciliation phase. This work is done by the parent component, so if it suspends or errors it is as if that component errored or suspended. However, conceptually it's like a child suspended or errored. In theory any thing can throw but it is really mainly due to either `React.lazy` (both in the element.type position and node position), `Thenable`s or the `Thenable`s that make up `AsyncIterable`s. Mainly this happens because a Server Component that errors turns into a `React.lazy`. In practice this means that if you have a Server Component as the direct child of an Error Boundary. Errors inside of it won't be caught. We used to have the same problem with Thenables and Suspense but because it's now always nested inside an inner Offscreen boundary that shields it by being one level nested. However, when we have raw Offscreen (Activity) boundaries they should also be able to catch the suspense if it's in a hidden state so the problem returns. This fixes it for thrown promises but it doesn't fix it for SuspenseException. I'm not sure this is even the right strategy for Suspense though. It kind of relies on the node never actually mounting/committing. It's conceptually a little tricky because the current component can inspect the children and make decisions based on them. Such as SuspenseList. The other thing that this PR tries to address is that it sets the foundation for dealing with error reporting for Server Components that errored. If something client side errors it'll be a stack like Server (DebugInfo) -> Fiber -> Fiber -> Server -> (DebugInfo) -> Fiber. However, all error reporting relies on it eventually terminating into a Fiber that is responsible for the error. To avoid having to fork too much it would be nice if I could create a Fiber to associate with the error so that even a Server component error in this case ultimately terminates in a Fiber. DiffTrain build for [270229f](270229f)
1 parent fe0295a commit 5ad4e79

34 files changed

+1516
-1198
lines changed

compiled/facebook-www/REVISION

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
01a40570c3cd852593c9bc88978b11cb9a2c5720
1+
270229f0c337dc652f07ef27d2254bb922bfaa9e
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
01a40570c3cd852593c9bc88978b11cb9a2c5720
1+
270229f0c337dc652f07ef27d2254bb922bfaa9e

compiled/facebook-www/React-dev.classic.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1980,7 +1980,7 @@ __DEV__ &&
19801980
exports.useTransition = function () {
19811981
return resolveDispatcher().useTransition();
19821982
};
1983-
exports.version = "19.0.0-www-classic-01a40570c3-20240611";
1983+
exports.version = "19.0.0-www-classic-270229f0c3-20240611";
19841984
"undefined" !== typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ &&
19851985
"function" ===
19861986
typeof __REACT_DEVTOOLS_GLOBAL_HOOK__.registerInternalModuleStop &&

compiled/facebook-www/React-dev.modern.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1960,7 +1960,7 @@ __DEV__ &&
19601960
exports.useTransition = function () {
19611961
return resolveDispatcher().useTransition();
19621962
};
1963-
exports.version = "19.0.0-www-modern-01a40570c3-20240611";
1963+
exports.version = "19.0.0-www-modern-270229f0c3-20240611";
19641964
"undefined" !== typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ &&
19651965
"function" ===
19661966
typeof __REACT_DEVTOOLS_GLOBAL_HOOK__.registerInternalModuleStop &&

compiled/facebook-www/React-prod.classic.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -665,4 +665,4 @@ exports.useSyncExternalStore = function (
665665
exports.useTransition = function () {
666666
return ReactSharedInternals.H.useTransition();
667667
};
668-
exports.version = "19.0.0-www-classic-01a40570c3-20240611";
668+
exports.version = "19.0.0-www-classic-270229f0c3-20240611";

compiled/facebook-www/React-prod.modern.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -665,4 +665,4 @@ exports.useSyncExternalStore = function (
665665
exports.useTransition = function () {
666666
return ReactSharedInternals.H.useTransition();
667667
};
668-
exports.version = "19.0.0-www-modern-01a40570c3-20240611";
668+
exports.version = "19.0.0-www-modern-270229f0c3-20240611";

compiled/facebook-www/React-profiling.classic.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -669,7 +669,7 @@ exports.useSyncExternalStore = function (
669669
exports.useTransition = function () {
670670
return ReactSharedInternals.H.useTransition();
671671
};
672-
exports.version = "19.0.0-www-classic-01a40570c3-20240611";
672+
exports.version = "19.0.0-www-classic-270229f0c3-20240611";
673673
"undefined" !== typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ &&
674674
"function" ===
675675
typeof __REACT_DEVTOOLS_GLOBAL_HOOK__.registerInternalModuleStop &&

compiled/facebook-www/React-profiling.modern.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -669,7 +669,7 @@ exports.useSyncExternalStore = function (
669669
exports.useTransition = function () {
670670
return ReactSharedInternals.H.useTransition();
671671
};
672-
exports.version = "19.0.0-www-modern-01a40570c3-20240611";
672+
exports.version = "19.0.0-www-modern-270229f0c3-20240611";
673673
"undefined" !== typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ &&
674674
"function" ===
675675
typeof __REACT_DEVTOOLS_GLOBAL_HOOK__.registerInternalModuleStop &&

compiled/facebook-www/ReactART-dev.classic.js

Lines changed: 33 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -3842,16 +3842,32 @@ __DEV__ &&
38423842
return deleteRemainingChildren(returnFiber, currentFirstChild);
38433843
}
38443844
return function (returnFiber, currentFirstChild, newChild, lanes) {
3845-
thenableIndexCounter$1 = 0;
3846-
returnFiber = reconcileChildFibersImpl(
3847-
returnFiber,
3848-
currentFirstChild,
3849-
newChild,
3850-
lanes,
3851-
null
3852-
);
3853-
thenableState$1 = null;
3854-
return returnFiber;
3845+
try {
3846+
thenableIndexCounter$1 = 0;
3847+
var firstChildFiber = reconcileChildFibersImpl(
3848+
returnFiber,
3849+
currentFirstChild,
3850+
newChild,
3851+
lanes,
3852+
null
3853+
);
3854+
thenableState$1 = null;
3855+
return firstChildFiber;
3856+
} catch (x) {
3857+
if (
3858+
x === SuspenseException ||
3859+
(!disableLegacyMode &&
3860+
0 === (returnFiber.mode & 1) &&
3861+
"object" === typeof x &&
3862+
null !== x &&
3863+
"function" === typeof x.then)
3864+
)
3865+
throw x;
3866+
currentFirstChild = createFiber(29, x, null, returnFiber.mode);
3867+
currentFirstChild.lanes = lanes;
3868+
currentFirstChild.return = returnFiber;
3869+
return currentFirstChild;
3870+
}
38553871
};
38563872
}
38573873
function pushHiddenContext(fiber, context) {
@@ -8575,6 +8591,9 @@ __DEV__ &&
85758591
: (workInProgress = null),
85768592
workInProgress
85778593
);
8594+
break;
8595+
case 29:
8596+
throw workInProgress.pendingProps;
85788597
}
85798598
throw Error(
85808599
"Unknown unit of work tag (" +
@@ -9588,6 +9607,8 @@ __DEV__ &&
95889607
bubbleProperties(workInProgress)),
95899608
null
95909609
);
9610+
case 29:
9611+
if (!disableLegacyMode) return null;
95919612
}
95929613
throw Error(
95939614
"Unknown unit of work tag (" +
@@ -16922,14 +16943,14 @@ __DEV__ &&
1692216943
scheduleRoot: scheduleRoot,
1692316944
setRefreshHandler: setRefreshHandler,
1692416945
getCurrentFiber: getCurrentFiberForDevTools,
16925-
reconcilerVersion: "19.0.0-www-classic-01a40570c3-20240611"
16946+
reconcilerVersion: "19.0.0-www-classic-270229f0c3-20240611"
1692616947
});
1692716948
})({
1692816949
findFiberByHostInstance: function () {
1692916950
return null;
1693016951
},
1693116952
bundleType: 1,
16932-
version: "19.0.0-www-classic-01a40570c3-20240611",
16953+
version: "19.0.0-www-classic-270229f0c3-20240611",
1693316954
rendererPackageName: "react-art"
1693416955
});
1693516956
var ClippingRectangle = TYPES.CLIPPING_RECTANGLE,

compiled/facebook-www/ReactART-dev.modern.js

Lines changed: 23 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -3741,16 +3741,24 @@ __DEV__ &&
37413741
return deleteRemainingChildren(returnFiber, currentFirstChild);
37423742
}
37433743
return function (returnFiber, currentFirstChild, newChild, lanes) {
3744-
thenableIndexCounter$1 = 0;
3745-
returnFiber = reconcileChildFibersImpl(
3746-
returnFiber,
3747-
currentFirstChild,
3748-
newChild,
3749-
lanes,
3750-
null
3751-
);
3752-
thenableState$1 = null;
3753-
return returnFiber;
3744+
try {
3745+
thenableIndexCounter$1 = 0;
3746+
var firstChildFiber = reconcileChildFibersImpl(
3747+
returnFiber,
3748+
currentFirstChild,
3749+
newChild,
3750+
lanes,
3751+
null
3752+
);
3753+
thenableState$1 = null;
3754+
return firstChildFiber;
3755+
} catch (x) {
3756+
if (x === SuspenseException) throw x;
3757+
currentFirstChild = createFiber(29, x, null, returnFiber.mode);
3758+
currentFirstChild.lanes = lanes;
3759+
currentFirstChild.return = returnFiber;
3760+
return currentFirstChild;
3761+
}
37543762
};
37553763
}
37563764
function pushHiddenContext(fiber, context) {
@@ -8265,6 +8273,9 @@ __DEV__ &&
82658273
: (workInProgress = null),
82668274
workInProgress
82678275
);
8276+
break;
8277+
case 29:
8278+
throw workInProgress.pendingProps;
82688279
}
82698280
throw Error(
82708281
"Unknown unit of work tag (" +
@@ -16362,14 +16373,14 @@ __DEV__ &&
1636216373
scheduleRoot: scheduleRoot,
1636316374
setRefreshHandler: setRefreshHandler,
1636416375
getCurrentFiber: getCurrentFiberForDevTools,
16365-
reconcilerVersion: "19.0.0-www-modern-01a40570c3-20240611"
16376+
reconcilerVersion: "19.0.0-www-modern-270229f0c3-20240611"
1636616377
});
1636716378
})({
1636816379
findFiberByHostInstance: function () {
1636916380
return null;
1637016381
},
1637116382
bundleType: 1,
16372-
version: "19.0.0-www-modern-01a40570c3-20240611",
16383+
version: "19.0.0-www-modern-270229f0c3-20240611",
1637316384
rendererPackageName: "react-art"
1637416385
});
1637516386
var ClippingRectangle = TYPES.CLIPPING_RECTANGLE,

compiled/facebook-www/ReactART-prod.classic.js

Lines changed: 46 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -2454,15 +2454,32 @@ function createChildReconciler(shouldTrackSideEffects) {
24542454
: deleteRemainingChildren(returnFiber, currentFirstChild);
24552455
}
24562456
return function (returnFiber, currentFirstChild, newChild, lanes) {
2457-
thenableIndexCounter$1 = 0;
2458-
returnFiber = reconcileChildFibersImpl(
2459-
returnFiber,
2460-
currentFirstChild,
2461-
newChild,
2462-
lanes
2463-
);
2464-
thenableState$1 = null;
2465-
return returnFiber;
2457+
try {
2458+
thenableIndexCounter$1 = 0;
2459+
var firstChildFiber = reconcileChildFibersImpl(
2460+
returnFiber,
2461+
currentFirstChild,
2462+
newChild,
2463+
lanes,
2464+
null
2465+
);
2466+
thenableState$1 = null;
2467+
return firstChildFiber;
2468+
} catch (x) {
2469+
if (
2470+
x === SuspenseException ||
2471+
(!disableLegacyMode &&
2472+
0 === (returnFiber.mode & 1) &&
2473+
"object" === typeof x &&
2474+
null !== x &&
2475+
"function" === typeof x.then)
2476+
)
2477+
throw x;
2478+
currentFirstChild = createFiber(29, x, null, returnFiber.mode);
2479+
currentFirstChild.lanes = lanes;
2480+
currentFirstChild.return = returnFiber;
2481+
return currentFirstChild;
2482+
}
24662483
};
24672484
}
24682485
var reconcileChildFibers = createChildReconciler(!0),
@@ -6105,6 +6122,9 @@ function beginWork(current, workInProgress, renderLanes) {
61056122
: (workInProgress = null),
61066123
workInProgress
61076124
);
6125+
break;
6126+
case 29:
6127+
throw workInProgress.pendingProps;
61086128
}
61096129
throw Error(formatProdErrorMessage(156, workInProgress.tag));
61106130
}
@@ -6968,6 +6988,8 @@ function completeWork(current, workInProgress, renderLanes) {
69686988
bubbleProperties(workInProgress)),
69696989
null
69706990
);
6991+
case 29:
6992+
if (!disableLegacyMode) return null;
69716993
}
69726994
throw Error(formatProdErrorMessage(156, workInProgress.tag));
69736995
}
@@ -10681,19 +10703,19 @@ var slice = Array.prototype.slice,
1068110703
};
1068210704
return Text;
1068310705
})(React.Component),
10684-
devToolsConfig$jscomp$inline_1159 = {
10706+
devToolsConfig$jscomp$inline_1165 = {
1068510707
findFiberByHostInstance: function () {
1068610708
return null;
1068710709
},
1068810710
bundleType: 0,
10689-
version: "19.0.0-www-classic-01a40570c3-20240611",
10711+
version: "19.0.0-www-classic-270229f0c3-20240611",
1069010712
rendererPackageName: "react-art"
1069110713
};
10692-
var internals$jscomp$inline_1371 = {
10693-
bundleType: devToolsConfig$jscomp$inline_1159.bundleType,
10694-
version: devToolsConfig$jscomp$inline_1159.version,
10695-
rendererPackageName: devToolsConfig$jscomp$inline_1159.rendererPackageName,
10696-
rendererConfig: devToolsConfig$jscomp$inline_1159.rendererConfig,
10714+
var internals$jscomp$inline_1377 = {
10715+
bundleType: devToolsConfig$jscomp$inline_1165.bundleType,
10716+
version: devToolsConfig$jscomp$inline_1165.version,
10717+
rendererPackageName: devToolsConfig$jscomp$inline_1165.rendererPackageName,
10718+
rendererConfig: devToolsConfig$jscomp$inline_1165.rendererConfig,
1069710719
overrideHookState: null,
1069810720
overrideHookStateDeletePath: null,
1069910721
overrideHookStateRenamePath: null,
@@ -10710,26 +10732,26 @@ var internals$jscomp$inline_1371 = {
1071010732
return null === fiber ? null : fiber.stateNode;
1071110733
},
1071210734
findFiberByHostInstance:
10713-
devToolsConfig$jscomp$inline_1159.findFiberByHostInstance ||
10735+
devToolsConfig$jscomp$inline_1165.findFiberByHostInstance ||
1071410736
emptyFindFiberByHostInstance,
1071510737
findHostInstancesForRefresh: null,
1071610738
scheduleRefresh: null,
1071710739
scheduleRoot: null,
1071810740
setRefreshHandler: null,
1071910741
getCurrentFiber: null,
10720-
reconcilerVersion: "19.0.0-www-classic-01a40570c3-20240611"
10742+
reconcilerVersion: "19.0.0-www-classic-270229f0c3-20240611"
1072110743
};
1072210744
if ("undefined" !== typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) {
10723-
var hook$jscomp$inline_1372 = __REACT_DEVTOOLS_GLOBAL_HOOK__;
10745+
var hook$jscomp$inline_1378 = __REACT_DEVTOOLS_GLOBAL_HOOK__;
1072410746
if (
10725-
!hook$jscomp$inline_1372.isDisabled &&
10726-
hook$jscomp$inline_1372.supportsFiber
10747+
!hook$jscomp$inline_1378.isDisabled &&
10748+
hook$jscomp$inline_1378.supportsFiber
1072710749
)
1072810750
try {
10729-
(rendererID = hook$jscomp$inline_1372.inject(
10730-
internals$jscomp$inline_1371
10751+
(rendererID = hook$jscomp$inline_1378.inject(
10752+
internals$jscomp$inline_1377
1073110753
)),
10732-
(injectedHook = hook$jscomp$inline_1372);
10754+
(injectedHook = hook$jscomp$inline_1378);
1073310755
} catch (err) {}
1073410756
}
1073510757
var Path = Mode$1.Path;

0 commit comments

Comments
 (0)