bippy 0.7.2 → 0.7.3-dev.a6ed02c
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +8 -68
- package/dist/core.cjs +1 -1
- package/dist/core.js +1 -1
- package/dist/errors.d.cts +56 -9
- package/dist/errors.d.ts +56 -9
- package/dist/index.cjs +1 -1
- package/dist/index.d.cts +8 -35
- package/dist/index.d.ts +8 -35
- package/dist/index.js +1 -1
- package/dist/install-hook-only.cjs +1 -1
- package/dist/install-hook-only.js +1 -1
- package/dist/rdt-hook.cjs +1 -1
- package/dist/rdt-hook.js +1 -1
- package/dist/source.cjs +10 -9
- package/dist/source.d.cts +36 -9
- package/dist/source.d.ts +36 -9
- package/dist/source.js +13 -12
- package/package.json +7 -7
- package/src/core.ts +134 -56
- package/src/rdt-hook.ts +126 -70
- package/src/react-internals/types.ts +33 -6
- package/src/react.ts +1 -0
- package/src/source/constants.ts +1 -3
- package/src/source/get-display-name-from-source.ts +10 -3
- package/src/source/get-source.ts +39 -19
- package/src/source/index.ts +17 -3
- package/src/source/inspect-hooks.ts +169 -28
- package/src/source/owner-stack.ts +43 -35
- package/src/source/parse-debug-stack.ts +1 -1
- package/src/source/parse-hook-names.ts +15 -8
- package/src/source/parse-stack.ts +3 -1
- package/src/source/renderer-dispatchers.ts +9 -4
- package/src/source/symbolication.ts +53 -32
package/src/core.ts
CHANGED
|
@@ -10,19 +10,19 @@ import type {
|
|
|
10
10
|
} from "./react-internals/index.js";
|
|
11
11
|
|
|
12
12
|
import {
|
|
13
|
-
_onActiveListeners,
|
|
14
13
|
BIPPY_INSTRUMENTATION_STRING,
|
|
15
14
|
createUnsubscribe,
|
|
16
15
|
getRDTHook,
|
|
17
16
|
hasRDTHook,
|
|
17
|
+
isFiberRootUnmounted,
|
|
18
18
|
isReactRefresh,
|
|
19
19
|
isRealReactDevtools,
|
|
20
20
|
onRDTHookReplace,
|
|
21
|
+
removeActiveListener,
|
|
21
22
|
} from "./rdt-hook.js";
|
|
22
|
-
import type { Unsubscribe } from "./rdt-hook.js";
|
|
23
|
+
import type { ReactDevToolsTarget, Unsubscribe } from "./rdt-hook.js";
|
|
23
24
|
import {
|
|
24
25
|
getReactWorkTagsForFiber,
|
|
25
|
-
MutationMask,
|
|
26
26
|
ReactBuildType,
|
|
27
27
|
ReactFiberFlags,
|
|
28
28
|
ReactSymbols,
|
|
@@ -152,16 +152,6 @@ export const didFiberRender = (fiber: Fiber): boolean => {
|
|
|
152
152
|
}
|
|
153
153
|
};
|
|
154
154
|
|
|
155
|
-
/**
|
|
156
|
-
* Returns `true` if the {@link Fiber} has committed. Note that this does not mean the fiber has committed in the current commit, just that it has committed in the past.
|
|
157
|
-
*/
|
|
158
|
-
export const didFiberCommit = (fiber: Fiber): boolean => {
|
|
159
|
-
return Boolean(
|
|
160
|
-
(fiber.flags & (MutationMask | ReactFiberFlags.Cloned)) !== 0 ||
|
|
161
|
-
(fiber.subtreeFlags & (MutationMask | ReactFiberFlags.Cloned)) !== 0,
|
|
162
|
-
);
|
|
163
|
-
};
|
|
164
|
-
|
|
165
155
|
/**
|
|
166
156
|
* Returns `true` if the {@link Fiber} should be filtered out during reconciliation.
|
|
167
157
|
*/
|
|
@@ -312,10 +302,7 @@ export const getDisplayName = (type: unknown): null | string => {
|
|
|
312
302
|
*/
|
|
313
303
|
export const detectReactBuildType = (renderer: ReactRenderer): "development" | "production" => {
|
|
314
304
|
try {
|
|
315
|
-
if (
|
|
316
|
-
typeof renderer.version === "string" &&
|
|
317
|
-
renderer.bundleType === ReactBuildType.Development
|
|
318
|
-
) {
|
|
305
|
+
if (typeof renderer.version === "string" && renderer.bundleType > ReactBuildType.Production) {
|
|
319
306
|
return "development";
|
|
320
307
|
}
|
|
321
308
|
} catch {}
|
|
@@ -325,8 +312,8 @@ export const detectReactBuildType = (renderer: ReactRenderer): "development" | "
|
|
|
325
312
|
/**
|
|
326
313
|
* Returns `true` if bippy's instrumentation is active.
|
|
327
314
|
*/
|
|
328
|
-
export const isInstrumentationActive = (): boolean => {
|
|
329
|
-
const rdtHook =
|
|
315
|
+
export const isInstrumentationActive = (target: ReactDevToolsTarget = globalThis): boolean => {
|
|
316
|
+
const rdtHook = target.__REACT_DEVTOOLS_GLOBAL_HOOK__;
|
|
330
317
|
return (
|
|
331
318
|
Boolean(rdtHook?._instrumentationIsActive) ||
|
|
332
319
|
isRealReactDevtools(rdtHook) ||
|
|
@@ -336,6 +323,7 @@ export const isInstrumentationActive = (): boolean => {
|
|
|
336
323
|
|
|
337
324
|
export const _fiberRoots = new Set<FiberRoot>();
|
|
338
325
|
const rootRendererIds = new WeakMap<FiberRoot, number>();
|
|
326
|
+
const rootHooks = new WeakMap<FiberRoot, ReactDevToolsGlobalHook>();
|
|
339
327
|
|
|
340
328
|
/**
|
|
341
329
|
* Returns the latest fiber (since it may be double-buffered).
|
|
@@ -370,29 +358,61 @@ export const getLatestFiber = (fiber: Fiber): Fiber => {
|
|
|
370
358
|
/**
|
|
371
359
|
* Returns the renderer that owns the {@link Fiber}.
|
|
372
360
|
*/
|
|
373
|
-
export const getRenderer = (
|
|
374
|
-
|
|
375
|
-
|
|
361
|
+
export const getRenderer = (
|
|
362
|
+
fiber: Fiber,
|
|
363
|
+
target: ReactDevToolsTarget = globalThis,
|
|
364
|
+
): ReactRenderer | null => {
|
|
376
365
|
let rootFiber = fiber;
|
|
377
|
-
while (rootFiber.return)
|
|
378
|
-
rootFiber = rootFiber.return;
|
|
379
|
-
}
|
|
380
|
-
|
|
366
|
+
while (rootFiber.return) rootFiber = rootFiber.return;
|
|
381
367
|
const fiberRoot = rootFiber.stateNode;
|
|
382
368
|
if (!isFiberRoot(fiberRoot)) return null;
|
|
383
369
|
|
|
384
|
-
const
|
|
385
|
-
|
|
386
|
-
|
|
370
|
+
const trackedRendererId = rootRendererIds.get(fiberRoot);
|
|
371
|
+
const trackedHook = rootHooks.get(fiberRoot);
|
|
372
|
+
if (trackedRendererId !== undefined && trackedHook) {
|
|
373
|
+
return trackedHook.renderers.get(trackedRendererId) ?? null;
|
|
374
|
+
}
|
|
375
|
+
|
|
376
|
+
const rdtHook = target.__REACT_DEVTOOLS_GLOBAL_HOOK__;
|
|
377
|
+
if (!rdtHook?.getFiberRoots) return null;
|
|
378
|
+
for (const [rendererId, renderer] of rdtHook.renderers) {
|
|
379
|
+
if (!rdtHook.getFiberRoots(rendererId).has(fiberRoot)) continue;
|
|
380
|
+
_fiberRoots.add(fiberRoot);
|
|
381
|
+
rootRendererIds.set(fiberRoot, rendererId);
|
|
382
|
+
rootHooks.set(fiberRoot, rdtHook);
|
|
383
|
+
setReactWorkTagsForFiber(fiberRoot.current, renderer);
|
|
384
|
+
return renderer;
|
|
385
|
+
}
|
|
386
|
+
return null;
|
|
387
387
|
};
|
|
388
388
|
|
|
389
389
|
export type RenderPhase = "mount" | "unmount" | "update";
|
|
390
390
|
|
|
391
|
+
interface FiberReference {
|
|
392
|
+
deref: () => Fiber | undefined;
|
|
393
|
+
}
|
|
394
|
+
|
|
391
395
|
let nextFiberId = 0;
|
|
392
396
|
const fiberIdMap = new WeakMap<Fiber, number>();
|
|
397
|
+
const fiberByIdMap = new Map<number, FiberReference>();
|
|
398
|
+
const fiberIdFinalizationRegistry =
|
|
399
|
+
typeof FinalizationRegistry === "function"
|
|
400
|
+
? new FinalizationRegistry<number>((fiberId) => {
|
|
401
|
+
if (!fiberByIdMap.get(fiberId)?.deref()) fiberByIdMap.delete(fiberId);
|
|
402
|
+
})
|
|
403
|
+
: null;
|
|
404
|
+
|
|
405
|
+
const createFiberReference = (fiber: Fiber): FiberReference =>
|
|
406
|
+
typeof WeakRef === "function" ? new WeakRef(fiber) : { deref: () => fiber };
|
|
393
407
|
|
|
394
408
|
export const setFiberId = (fiber: Fiber, fiberId: number = nextFiberId++): void => {
|
|
409
|
+
const previousFiberId = fiberIdMap.get(fiber);
|
|
410
|
+
if (previousFiberId !== undefined && previousFiberId !== fiberId) {
|
|
411
|
+
fiberByIdMap.delete(previousFiberId);
|
|
412
|
+
}
|
|
395
413
|
fiberIdMap.set(fiber, fiberId);
|
|
414
|
+
fiberByIdMap.set(fiberId, createFiberReference(fiber));
|
|
415
|
+
fiberIdFinalizationRegistry?.register(fiber, fiberId);
|
|
396
416
|
if (Number.isSafeInteger(fiberId) && fiberId >= nextFiberId) {
|
|
397
417
|
nextFiberId = fiberId + 1;
|
|
398
418
|
}
|
|
@@ -402,6 +422,7 @@ export const getFiberId = (fiber: Fiber): number => {
|
|
|
402
422
|
let currentFiberId = fiberIdMap.get(fiber);
|
|
403
423
|
if (currentFiberId === undefined && fiber.alternate) {
|
|
404
424
|
currentFiberId = fiberIdMap.get(fiber.alternate);
|
|
425
|
+
if (currentFiberId !== undefined) setFiberId(fiber, currentFiberId);
|
|
405
426
|
}
|
|
406
427
|
if (currentFiberId === undefined) {
|
|
407
428
|
currentFiberId = nextFiberId++;
|
|
@@ -410,6 +431,33 @@ export const getFiberId = (fiber: Fiber): number => {
|
|
|
410
431
|
return currentFiberId;
|
|
411
432
|
};
|
|
412
433
|
|
|
434
|
+
export const getFiberById = (fiberId: number): Fiber | null => {
|
|
435
|
+
const fiber = fiberByIdMap.get(fiberId)?.deref();
|
|
436
|
+
if (!fiber) {
|
|
437
|
+
fiberByIdMap.delete(fiberId);
|
|
438
|
+
return null;
|
|
439
|
+
}
|
|
440
|
+
return getLatestFiber(fiber);
|
|
441
|
+
};
|
|
442
|
+
|
|
443
|
+
const releaseFiberId = (fiber: Fiber): void => {
|
|
444
|
+
const relatedFibers = fiber.alternate ? [fiber, fiber.alternate] : [fiber];
|
|
445
|
+
const fiberIds = new Set<number>();
|
|
446
|
+
|
|
447
|
+
for (const relatedFiber of relatedFibers) {
|
|
448
|
+
const fiberId = fiberIdMap.get(relatedFiber);
|
|
449
|
+
if (fiberId !== undefined) fiberIds.add(fiberId);
|
|
450
|
+
fiberIdMap.delete(relatedFiber);
|
|
451
|
+
}
|
|
452
|
+
|
|
453
|
+
for (const fiberId of fiberIds) {
|
|
454
|
+
const assignedFiber = fiberByIdMap.get(fiberId)?.deref();
|
|
455
|
+
if (!assignedFiber || relatedFibers.includes(assignedFiber)) {
|
|
456
|
+
fiberByIdMap.delete(fiberId);
|
|
457
|
+
}
|
|
458
|
+
}
|
|
459
|
+
};
|
|
460
|
+
|
|
413
461
|
const mountFiberRecursively = (
|
|
414
462
|
onRender: RenderHandler,
|
|
415
463
|
firstChild: Fiber,
|
|
@@ -635,6 +683,7 @@ export const traverseRenderedFibers = (root: Fiber | FiberRoot, onRender: Render
|
|
|
635
683
|
|
|
636
684
|
export interface InstrumentationOptions {
|
|
637
685
|
name?: string;
|
|
686
|
+
target?: ReactDevToolsTarget;
|
|
638
687
|
onActive?: () => unknown;
|
|
639
688
|
onCommitFiberRoot?: (
|
|
640
689
|
rendererID: number,
|
|
@@ -649,6 +698,7 @@ export interface InstrumentationOptions {
|
|
|
649
698
|
|
|
650
699
|
interface InstrumentationSubscription {
|
|
651
700
|
options: InstrumentationOptions;
|
|
701
|
+
target: ReactDevToolsTarget;
|
|
652
702
|
}
|
|
653
703
|
|
|
654
704
|
const instrumentationSubscriptions = new Set<InstrumentationSubscription>();
|
|
@@ -661,6 +711,7 @@ interface HookDispatchers {
|
|
|
661
711
|
}
|
|
662
712
|
|
|
663
713
|
const hookDispatchers = new WeakMap<ReactDevToolsGlobalHook, Partial<HookDispatchers>>();
|
|
714
|
+
const hookTargets = new WeakMap<ReactDevToolsGlobalHook, ReactDevToolsTarget>();
|
|
664
715
|
let didSubscribeToHookReplacements = false;
|
|
665
716
|
|
|
666
717
|
// each hook event is dispatched from a single re-installable wrapper. If
|
|
@@ -690,20 +741,17 @@ const setHookEventDispatchers = (rdtHook: ReactDevToolsGlobalHook): void => {
|
|
|
690
741
|
setReactWorkTagsForFiber(root.current, rdtHook.renderers.get(rendererID));
|
|
691
742
|
// Custom renderers and test harnesses commit roots without a memoizedState;
|
|
692
743
|
// those must stay tracked, so only explicit unmount evidence removes a root.
|
|
693
|
-
|
|
694
|
-
const isUnmounting =
|
|
695
|
-
rootMemoizedState === null ||
|
|
696
|
-
(rootMemoizedState !== undefined &&
|
|
697
|
-
(rootMemoizedState.element === null || rootMemoizedState.element === undefined));
|
|
698
|
-
if (isUnmounting) {
|
|
744
|
+
if (isFiberRootUnmounted(root)) {
|
|
699
745
|
_fiberRoots.delete(root);
|
|
700
746
|
rootRendererIds.delete(root);
|
|
747
|
+
rootHooks.delete(root);
|
|
701
748
|
} else {
|
|
702
749
|
_fiberRoots.add(root);
|
|
703
750
|
rootRendererIds.set(root, rendererID);
|
|
751
|
+
rootHooks.set(root, rdtHook);
|
|
704
752
|
}
|
|
705
|
-
for (const { options } of instrumentationSubscriptions) {
|
|
706
|
-
if (options.onCommitFiberRoot) {
|
|
753
|
+
for (const { options, target } of instrumentationSubscriptions) {
|
|
754
|
+
if (target === hookTargets.get(rdtHook) && options.onCommitFiberRoot) {
|
|
707
755
|
options.onCommitFiberRoot(rendererID, root, priority, didError);
|
|
708
756
|
}
|
|
709
757
|
}
|
|
@@ -728,10 +776,14 @@ const setHookEventDispatchers = (rdtHook: ReactDevToolsGlobalHook): void => {
|
|
|
728
776
|
if (hookDispatchers.get(rdtHook)?.onCommitFiberUnmount !== dispatchCommitFiberUnmount) {
|
|
729
777
|
return;
|
|
730
778
|
}
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
options.onCommitFiberUnmount
|
|
779
|
+
try {
|
|
780
|
+
for (const { options, target } of instrumentationSubscriptions) {
|
|
781
|
+
if (target === hookTargets.get(rdtHook) && options.onCommitFiberUnmount) {
|
|
782
|
+
options.onCommitFiberUnmount(rendererID, fiber);
|
|
783
|
+
}
|
|
734
784
|
}
|
|
785
|
+
} finally {
|
|
786
|
+
releaseFiberId(fiber);
|
|
735
787
|
}
|
|
736
788
|
};
|
|
737
789
|
dispatchers.onCommitFiberUnmount = dispatchCommitFiberUnmount;
|
|
@@ -753,8 +805,8 @@ const setHookEventDispatchers = (rdtHook: ReactDevToolsGlobalHook): void => {
|
|
|
753
805
|
if (hookDispatchers.get(rdtHook)?.onPostCommitFiberRoot !== dispatchPostCommitFiberRoot) {
|
|
754
806
|
return;
|
|
755
807
|
}
|
|
756
|
-
for (const { options } of instrumentationSubscriptions) {
|
|
757
|
-
if (options.onPostCommitFiberRoot) {
|
|
808
|
+
for (const { options, target } of instrumentationSubscriptions) {
|
|
809
|
+
if (target === hookTargets.get(rdtHook) && options.onPostCommitFiberRoot) {
|
|
758
810
|
options.onPostCommitFiberRoot(rendererID, root);
|
|
759
811
|
}
|
|
760
812
|
}
|
|
@@ -777,8 +829,8 @@ const setHookEventDispatchers = (rdtHook: ReactDevToolsGlobalHook): void => {
|
|
|
777
829
|
prevOnScheduleFiberRoot.call(rdtHook, rendererID, root, children);
|
|
778
830
|
}
|
|
779
831
|
if (hookDispatchers.get(rdtHook)?.onScheduleFiberRoot !== dispatchScheduleFiberRoot) return;
|
|
780
|
-
for (const { options } of instrumentationSubscriptions) {
|
|
781
|
-
if (options.onScheduleFiberRoot) {
|
|
832
|
+
for (const { options, target } of instrumentationSubscriptions) {
|
|
833
|
+
if (target === hookTargets.get(rdtHook) && options.onScheduleFiberRoot) {
|
|
782
834
|
options.onScheduleFiberRoot(rendererID, root, children);
|
|
783
835
|
}
|
|
784
836
|
}
|
|
@@ -788,11 +840,23 @@ const setHookEventDispatchers = (rdtHook: ReactDevToolsGlobalHook): void => {
|
|
|
788
840
|
}
|
|
789
841
|
};
|
|
790
842
|
|
|
791
|
-
const
|
|
843
|
+
const handleHookReplacement = (
|
|
844
|
+
rdtHook: ReactDevToolsGlobalHook,
|
|
845
|
+
target: ReactDevToolsTarget,
|
|
846
|
+
): void => {
|
|
847
|
+
hookTargets.set(rdtHook, target);
|
|
848
|
+
setHookEventDispatchers(rdtHook);
|
|
849
|
+
};
|
|
850
|
+
|
|
851
|
+
const wireHookEventDispatchers = (
|
|
852
|
+
rdtHook: ReactDevToolsGlobalHook,
|
|
853
|
+
target: ReactDevToolsTarget = globalThis,
|
|
854
|
+
): void => {
|
|
792
855
|
if (!didSubscribeToHookReplacements) {
|
|
793
|
-
onRDTHookReplace(
|
|
856
|
+
onRDTHookReplace(handleHookReplacement);
|
|
794
857
|
didSubscribeToHookReplacements = true;
|
|
795
858
|
}
|
|
859
|
+
hookTargets.set(rdtHook, target);
|
|
796
860
|
setHookEventDispatchers(rdtHook);
|
|
797
861
|
};
|
|
798
862
|
|
|
@@ -822,15 +886,16 @@ try {
|
|
|
822
886
|
* unsubscribe();
|
|
823
887
|
*/
|
|
824
888
|
export const instrument = (options: InstrumentationOptions): Unsubscribe => {
|
|
825
|
-
const
|
|
889
|
+
const target = options.target ?? globalThis;
|
|
890
|
+
const rdtHook = getRDTHook(options.onActive, target);
|
|
826
891
|
rdtHook._instrumentationSource = options.name ?? BIPPY_INSTRUMENTATION_STRING;
|
|
827
892
|
|
|
828
|
-
wireHookEventDispatchers(rdtHook);
|
|
829
|
-
const subscription: InstrumentationSubscription = { options };
|
|
893
|
+
wireHookEventDispatchers(rdtHook, target);
|
|
894
|
+
const subscription: InstrumentationSubscription = { options, target };
|
|
830
895
|
instrumentationSubscriptions.add(subscription);
|
|
831
896
|
|
|
832
897
|
return createUnsubscribe(() => {
|
|
833
|
-
if (options.onActive)
|
|
898
|
+
if (options.onActive) removeActiveListener(options.onActive, target);
|
|
834
899
|
instrumentationSubscriptions.delete(subscription);
|
|
835
900
|
});
|
|
836
901
|
};
|
|
@@ -874,9 +939,12 @@ const getPublicHostInstance = (stateNode: unknown): unknown => {
|
|
|
874
939
|
return typeof nativeTag === "number" ? nativeTag : stateNode;
|
|
875
940
|
};
|
|
876
941
|
|
|
877
|
-
export const getFiber = <
|
|
878
|
-
|
|
879
|
-
|
|
942
|
+
export const getFiber = <HostInstance>(
|
|
943
|
+
hostInstance: HostInstance,
|
|
944
|
+
target: ReactDevToolsTarget = globalThis,
|
|
945
|
+
): Fiber | null => {
|
|
946
|
+
const rdtHook = target.__REACT_DEVTOOLS_GLOBAL_HOOK__;
|
|
947
|
+
if (rdtHook) {
|
|
880
948
|
for (const renderer of rdtHook.renderers.values()) {
|
|
881
949
|
try {
|
|
882
950
|
const fiber = renderer.findFiberByHostInstance?.(hostInstance);
|
|
@@ -908,10 +976,20 @@ export const getFiber = <T>(hostInstance: T): Fiber | null => {
|
|
|
908
976
|
|
|
909
977
|
if (
|
|
910
978
|
hostInstance !== null &&
|
|
911
|
-
hostInstance !== undefined &&
|
|
912
979
|
(typeof hostInstance === "object" || typeof hostInstance === "number")
|
|
913
980
|
) {
|
|
981
|
+
const targetFiberRoots = new Set<FiberRoot>();
|
|
982
|
+
if (rdtHook?.getFiberRoots) {
|
|
983
|
+
for (const rendererId of rdtHook.renderers.keys()) {
|
|
984
|
+
for (const fiberRoot of rdtHook.getFiberRoots(rendererId)) {
|
|
985
|
+
targetFiberRoots.add(fiberRoot);
|
|
986
|
+
}
|
|
987
|
+
}
|
|
988
|
+
}
|
|
914
989
|
for (const fiberRoot of _fiberRoots) {
|
|
990
|
+
if (rootHooks.get(fiberRoot) === rdtHook) targetFiberRoots.add(fiberRoot);
|
|
991
|
+
}
|
|
992
|
+
for (const fiberRoot of targetFiberRoots) {
|
|
915
993
|
const fiber = traverseFiber(
|
|
916
994
|
fiberRoot.current,
|
|
917
995
|
(candidateFiber) =>
|
|
@@ -928,16 +1006,16 @@ export const getFiberFromHostInstance = getFiber;
|
|
|
928
1006
|
|
|
929
1007
|
export {
|
|
930
1008
|
BIPPY_INSTRUMENTATION_STRING,
|
|
931
|
-
_onActiveListeners,
|
|
932
1009
|
_renderers,
|
|
933
1010
|
getRDTHook,
|
|
934
1011
|
hasRDTHook,
|
|
935
1012
|
installRDTHook,
|
|
1013
|
+
isFiberRootUnmounted,
|
|
936
1014
|
isReactRefresh,
|
|
937
1015
|
isRealReactDevtools,
|
|
938
1016
|
onRendererInject,
|
|
939
1017
|
patchRDTHook,
|
|
940
1018
|
version,
|
|
941
1019
|
} from "./rdt-hook.js";
|
|
942
|
-
export type { Unsubscribe } from "./rdt-hook.js";
|
|
1020
|
+
export type { ReactDevToolsTarget, Unsubscribe } from "./rdt-hook.js";
|
|
943
1021
|
export * from "./react-internals/index.js";
|