From 591c2d3a6393ffeebb5b16112087a1475b7729ad Mon Sep 17 00:00:00 2001 From: Sebastian Sebbie Silbermann Date: Thu, 11 Sep 2025 15:09:27 +0200 Subject: [PATCH 1/3] [DevTools] Stop mounting empty roots --- .../src/__tests__/store-test.js | 5 ++- .../src/backend/fiber/renderer.js | 45 +++++++++---------- 2 files changed, 24 insertions(+), 26 deletions(-) diff --git a/packages/react-devtools-shared/src/__tests__/store-test.js b/packages/react-devtools-shared/src/__tests__/store-test.js index fad4622acc1..3b60d5ae093 100644 --- a/packages/react-devtools-shared/src/__tests__/store-test.js +++ b/packages/react-devtools-shared/src/__tests__/store-test.js @@ -2489,7 +2489,7 @@ describe('Store', () => { withErrorsOrWarningsIgnored(['test-only:'], async () => { await act(() => render()); }); - expect(store).toMatchInlineSnapshot(`[root]`); + expect(store).toMatchInlineSnapshot(``); expect(store.componentWithErrorCount).toBe(0); expect(store.componentWithWarningCount).toBe(0); }); @@ -3083,6 +3083,9 @@ describe('Store', () => { it('should handle an empty root', async () => { await actAsync(() => render(null)); + expect(store).toMatchInlineSnapshot(``); + + await actAsync(() => render()); expect(store).toMatchInlineSnapshot(`[root]`); }); }); diff --git a/packages/react-devtools-shared/src/backend/fiber/renderer.js b/packages/react-devtools-shared/src/backend/fiber/renderer.js index 3fe177e0797..e10513fbd84 100644 --- a/packages/react-devtools-shared/src/backend/fiber/renderer.js +++ b/packages/react-devtools-shared/src/backend/fiber/renderer.js @@ -5322,12 +5322,12 @@ export function attach( root: FiberRoot, priorityLevel: void | number, ) { - const current = root.current; + const nextFiber = root.current; let prevFiber: null | Fiber = null; let rootInstance = rootToFiberInstanceMap.get(root); if (!rootInstance) { - rootInstance = createFiberInstance(current); + rootInstance = createFiberInstance(nextFiber); rootToFiberInstanceMap.set(root, rootInstance); idToDevToolsInstanceMap.set(rootInstance.id, rootInstance); } else { @@ -5366,30 +5366,25 @@ export function attach( }; } - if (prevFiber !== null) { - // TODO: relying on this seems a bit fishy. - const wasMounted = - prevFiber.memoizedState != null && - prevFiber.memoizedState.element != null; - const isMounted = - current.memoizedState != null && current.memoizedState.element != null; - if (!wasMounted && isMounted) { - // Mount a new root. - setRootPseudoKey(currentRoot.id, current); - mountFiberRecursively(current, false); - } else if (wasMounted && isMounted) { - // Update an existing root. - updateFiberRecursively(rootInstance, current, prevFiber, false); - } else if (wasMounted && !isMounted) { - // Unmount an existing root. - unmountInstanceRecursively(rootInstance); - removeRootPseudoKey(currentRoot.id); - rootToFiberInstanceMap.delete(root); - } - } else { + const isMounted = nextFiber.child !== null; + const wasMounted = prevFiber !== null && prevFiber.child !== null; + if (!wasMounted && isMounted) { // Mount a new root. - setRootPseudoKey(currentRoot.id, current); - mountFiberRecursively(current, false); + setRootPseudoKey(currentRoot.id, nextFiber); + mountFiberRecursively(nextFiber, false); + } else if (wasMounted && isMounted) { + if (prevFiber === null) { + throw new Error( + 'Expected previous fiber when updating an existing root', + ); + } + // Update an existing root. + updateFiberRecursively(rootInstance, nextFiber, prevFiber, false); + } else if (wasMounted && !isMounted) { + // Unmount an existing root. + unmountInstanceRecursively(rootInstance); + removeRootPseudoKey(currentRoot.id); + rootToFiberInstanceMap.delete(root); } if (isProfiling && isProfilingSupported) { From 999f2fba7868398c54b0f956e22baa7c9001e6d8 Mon Sep 17 00:00:00 2001 From: Sebastian Sebbie Silbermann Date: Thu, 11 Sep 2025 19:11:55 +0200 Subject: [PATCH 2/3] Use same terminology as in other similar checks --- .../src/backend/fiber/renderer.js | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/packages/react-devtools-shared/src/backend/fiber/renderer.js b/packages/react-devtools-shared/src/backend/fiber/renderer.js index e10513fbd84..4477af9ab31 100644 --- a/packages/react-devtools-shared/src/backend/fiber/renderer.js +++ b/packages/react-devtools-shared/src/backend/fiber/renderer.js @@ -5366,13 +5366,13 @@ export function attach( }; } - const isMounted = nextFiber.child !== null; - const wasMounted = prevFiber !== null && prevFiber.child !== null; - if (!wasMounted && isMounted) { + const nextIsMounted = nextFiber.child !== null; + const prevWasMounted = prevFiber !== null && prevFiber.child !== null; + if (!prevWasMounted && nextIsMounted) { // Mount a new root. setRootPseudoKey(currentRoot.id, nextFiber); mountFiberRecursively(nextFiber, false); - } else if (wasMounted && isMounted) { + } else if (prevWasMounted && nextIsMounted) { if (prevFiber === null) { throw new Error( 'Expected previous fiber when updating an existing root', @@ -5380,7 +5380,7 @@ export function attach( } // Update an existing root. updateFiberRecursively(rootInstance, nextFiber, prevFiber, false); - } else if (wasMounted && !isMounted) { + } else if (prevWasMounted && !nextIsMounted) { // Unmount an existing root. unmountInstanceRecursively(rootInstance); removeRootPseudoKey(currentRoot.id); From badf59cc0d40c643e69a220e88641f341cb506ee Mon Sep 17 00:00:00 2001 From: Sebastian Sebbie Silbermann Date: Thu, 11 Sep 2025 19:12:46 +0200 Subject: [PATCH 3/3] error copy --- packages/react-devtools-shared/src/backend/fiber/renderer.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/react-devtools-shared/src/backend/fiber/renderer.js b/packages/react-devtools-shared/src/backend/fiber/renderer.js index 4477af9ab31..aee89e8ca2c 100644 --- a/packages/react-devtools-shared/src/backend/fiber/renderer.js +++ b/packages/react-devtools-shared/src/backend/fiber/renderer.js @@ -5375,7 +5375,7 @@ export function attach( } else if (prevWasMounted && nextIsMounted) { if (prevFiber === null) { throw new Error( - 'Expected previous fiber when updating an existing root', + 'Expected a previous Fiber when updating an existing root.', ); } // Update an existing root.