@samitouri / QOS-React / commits / b56907db51

[DevTools] Show Props as Read-only for Suspense/Activity but below (#34695)

Somehow my last commit didn't make it in #34630.

Sebastian Markbåge committed Oct 2, 2025 at 15:29 UTC b56907db515ea518b7c30015d2c5d5641df35942
2 files changed +36 -19
packages/react-devtools-shared/src/devtools/views/Components/InspectedElementPropsTree.js
+7 -11
@@ -20,6 +20,7 @@ import styles from './InspectedElementSharedStyles.css';
20 import {
21 ElementTypeClass,
22 ElementTypeSuspense,
23 + ElementTypeActivity,
24 } from 'react-devtools-shared/src/frontend/types';
25 import {withPermissionsCheck} from 'react-devtools-shared/src/frontend/utils/withPermissionsCheck';
26
@@ -50,20 +51,15 @@ export default function InspectedElementPropsTree({
51 type,
52 } = inspectedElement;
53
53 - if (type === ElementTypeSuspense) {
54 - // Skip showing the props for Suspense. We want to give more real estate to the
55 - // "Suspended by" for Suspense boundaries. We could maybe show it further below
56 - // but in practice, the props of Suspense boundaries are not very useful to
57 - // inspect because the name shows in the tree already. The children in the tree
58 - // will be either the "fallback" or "children" prop which you can already inspect
59 - // but resuspending the tree.
60 - return null;
61 - }
62 -
54 const canDeletePaths =
55 type === ElementTypeClass || canEditFunctionPropsDeletePaths;
56 const canEditValues =
66 - !readOnly && (type === ElementTypeClass || canEditFunctionProps);
57 + !readOnly &&
58 + (type === ElementTypeClass || canEditFunctionProps) &&
59 + // Make it read-only for Suspense to make it a bit cleaner. It's not
60 + // useful to edit children anyway.
61 + type !== ElementTypeSuspense &&
62 + type !== ElementTypeActivity;
63 const canRenamePaths =
64 type === ElementTypeClass || canEditFunctionPropsRenamePaths;
65
packages/react-devtools-shared/src/devtools/views/Components/InspectedElementView.js
+29 -8
@@ -24,6 +24,10 @@ import InspectedElementSourcePanel from './InspectedElementSourcePanel';
24 import StackTraceView from './StackTraceView';
25 import OwnerView from './OwnerView';
26 import Skeleton from './Skeleton';
27 +import {
28 + ElementTypeSuspense,
29 + ElementTypeActivity,
30 +} from 'react-devtools-shared/src/frontend/types';
31
32 import styles from './InspectedElementView.css';
33
@@ -60,6 +64,7 @@ export default function InspectedElementView({
64 rootType,
65 source,
66 nativeTag,
67 + type,
68 } = inspectedElement;
69
70 const bridge = useContext(BridgeContext);
@@ -74,6 +79,17 @@ export default function InspectedElementView({
79 const showRenderedBy =
80 showStack || showOwnersList || rendererLabel !== null || rootType !== null;
81
82 + const propsSection = (
83 + <div className={styles.InspectedElementSection}>
84 + <InspectedElementPropsTree
85 + bridge={bridge}
86 + element={element}
87 + inspectedElement={inspectedElement}
88 + store={store}
89 + />
90 + </div>
91 + );
92 +
93 return (
94 <Fragment>
95 <div className={styles.InspectedElement}>
@@ -85,14 +101,12 @@ export default function InspectedElementView({
101 />
102 </div>
103
88 - <div className={styles.InspectedElementSection}>
89 - <InspectedElementPropsTree
90 - bridge={bridge}
91 - element={element}
92 - inspectedElement={inspectedElement}
93 - store={store}
94 - />
95 - </div>
104 + {
105 + // For Suspense and Activity we show the props further down.
106 + type !== ElementTypeSuspense && type !== ElementTypeActivity
107 + ? propsSection
108 + : null
109 + }
110
111 <div className={styles.InspectedElementSection}>
112 <InspectedElementStateTree
@@ -157,6 +171,13 @@ export default function InspectedElementView({
171 />
172 </div>
173
174 + {
175 + // For Suspense and Activity we show the props below suspended by to give that more priority.
176 + type !== ElementTypeSuspense && type !== ElementTypeActivity
177 + ? null
178 + : propsSection
179 + }
180 +
181 {showRenderedBy && (
182 <div
183 className={styles.InspectedElementSection}