remote-components 0.0.42 → 0.0.43

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.
@@ -1,54 +1,7 @@
1
1
  import * as react_jsx_runtime from 'react/jsx-runtime';
2
2
  import * as react from 'react';
3
- import { L as LoadRemoteComponentProps } from '../../../component-loader-2ca91ad8.js';
4
-
5
- declare module 'react/jsx-runtime' {
6
- namespace JSX {
7
- interface IntrinsicElements {
8
- template: {
9
- shadowrootmode?: 'open' | 'closed';
10
- id?: string;
11
- ref?: React.Ref<HTMLTemplateElement>;
12
- dangerouslySetInnerHTML?: {
13
- __html: string;
14
- };
15
- children?: React.ReactNode;
16
- };
17
- }
18
- }
19
- }
20
- interface RemoteComponentProps {
21
- /** The source URL of the remote component. */
22
- src?: string | URL;
23
- /** Whether to isolate the remote component using a Shadow DOM wrapper. */
24
- isolate?: boolean;
25
- /** The shadow DOM mode to use when isolating the remote component. */
26
- mode?: 'open' | 'closed';
27
- /** Whether to include a CSS reset style in the shadow DOM. Defaults to `false`. */
28
- reset?: boolean;
29
- /** The credentials to use for the fetch request. Defaults to `same-origin`. */
30
- credentials?: RequestCredentials;
31
- name?: string;
32
- /** Shared modules to include in the remote component's context. */
33
- shared?: LoadRemoteComponentProps['shared'];
34
- /** Additional headers to use when fetching the remote component. */
35
- additionalHeaders?: Headers | Record<string, string>;
36
- /** The children to use as a loading fallback until the remote component is loaded. */
37
- children?: React.ReactNode;
38
- /** Called right before a new remote component load starts. */
39
- onBeforeLoad?: (src: string | URL) => void;
40
- /** Called when the remote component has been successfully loaded and mounted. */
41
- onLoad?: (src: string | URL) => void;
42
- /** Called when an error occurs while loading or mounting the remote component. */
43
- onError?: (error: unknown) => void;
44
- /** Called when a different remote component is loaded into the same wrapper. */
45
- onChange?: (info: {
46
- previousSrc: string | URL | null;
47
- nextSrc: string | URL | null;
48
- previousName: string | undefined;
49
- nextName: string | undefined;
50
- }) => void;
51
- }
3
+ import { RemoteComponentProps } from '../../../react/index.js';
4
+ import '../../../component-loader-2ca91ad8.js';
52
5
 
53
6
  /**
54
7
  * RemoteComponent - Client-side component for rendering remote components
@@ -7,10 +7,11 @@ import * as Image from "next/image";
7
7
  import {
8
8
  startTransition,
9
9
  useEffect,
10
- useLayoutEffect,
10
+ useId,
11
+ useLayoutEffect as useLayoutEffect2,
11
12
  useMemo,
12
- useRef,
13
- useState
13
+ useRef as useRef2,
14
+ useState as useState2
14
15
  } from "react";
15
16
  import { createPortal } from "react-dom";
16
17
 
@@ -598,6 +599,7 @@ function getBundleKey(bundle) {
598
599
  // src/shared/client/chunk-loader.ts
599
600
  function createChunkLoader(runtime) {
600
601
  return function __turbopack_chunk_load__(chunkId, scriptBundle) {
602
+ logDebug("ChunkLoader", `Loading chunk: "${chunkId}"`);
601
603
  const self = globalThis;
602
604
  const {
603
605
  bundle,
@@ -607,8 +609,14 @@ function createChunkLoader(runtime) {
607
609
  bundle: scriptBundle ?? "",
608
610
  id: chunkId
609
611
  };
612
+ logDebug(
613
+ "ChunkLoader",
614
+ `Parsed chunk - bundle: "${bundle}", path: "${path}", prefix: "${prefix}"`
615
+ );
610
616
  const remoteRuntime = self.__remote_webpack_require__?.[bundle ?? "default"] ? self.__remote_webpack_require__[bundle ?? "default"]?.type || "webpack" : runtime;
617
+ logDebug("ChunkLoader", `Remote runtime: "${remoteRuntime}"`);
611
618
  if (remoteRuntime === RUNTIME_WEBPACK) {
619
+ logDebug("ChunkLoader", "Skipping chunk load - webpack runtime detected");
612
620
  return Promise.resolve(void 0);
613
621
  }
614
622
  const url = new URL(
@@ -619,14 +627,17 @@ function createChunkLoader(runtime) {
619
627
  self.__remote_bundle_url__?.[bundle ?? "default"] ?? new URL(location.origin)
620
628
  ).href;
621
629
  if (url.endsWith(".css")) {
630
+ logDebug("ChunkLoader", `Skipping CSS file: "${url}"`);
622
631
  return;
623
632
  }
624
633
  if (!self.__remote_components_turbopack_chunk_loader_promise__) {
625
634
  self.__remote_components_turbopack_chunk_loader_promise__ = {};
626
635
  }
627
636
  if (self.__remote_components_turbopack_chunk_loader_promise__[url]) {
637
+ logDebug("ChunkLoader", `Returning cached promise for: "${url}"`);
628
638
  return self.__remote_components_turbopack_chunk_loader_promise__[url];
629
639
  }
640
+ logDebug("ChunkLoader", `Fetching chunk from: "${url}"`);
630
641
  self.__remote_components_turbopack_chunk_loader_promise__[url] = new Promise((resolve, reject) => {
631
642
  fetch(url).then((res) => res.text()).then((code) => {
632
643
  if (code.includes("globalThis.TURBOPACK")) {
@@ -638,7 +649,12 @@ function createChunkLoader(runtime) {
638
649
  };
639
650
  }
640
651
  async function handleTurbopackChunk(code, bundle, url) {
652
+ logDebug(
653
+ "ChunkLoader",
654
+ `Handling Turbopack chunk - bundle: "${bundle}", url: "${url}"`
655
+ );
641
656
  if (/importScripts\(\.\.\.self.TURBOPACK_NEXT_CHUNK_URLS/.test(code)) {
657
+ logDebug("ChunkLoader", `Skipping worker chunk: "${url}"`);
642
658
  const preloadLinks = document.querySelectorAll(
643
659
  `link[rel="preload"][href="${new URL(url).pathname}"]`
644
660
  );
@@ -647,6 +663,7 @@ async function handleTurbopackChunk(code, bundle, url) {
647
663
  }
648
664
  const self = globalThis;
649
665
  const bundleKey = getBundleKey(bundle);
666
+ logDebug("ChunkLoader", `Bundle key: "${bundleKey}"`);
650
667
  const transformedCode = code.replace(/globalThis\.TURBOPACK/g, `globalThis.TURBOPACK_${bundleKey}`).replace(
651
668
  /TURBOPACK_WORKER_LOCATION/g,
652
669
  `TURBOPACK_WORKER_LOCATION_${bundleKey}`
@@ -666,6 +683,7 @@ async function handleTurbopackChunk(code, bundle, url) {
666
683
  )
667
684
  ).href}$1$2.js.map`
668
685
  );
686
+ logDebug("ChunkLoader", `Creating blob script for: "${url}"`);
669
687
  await new Promise((scriptResolve, scriptReject) => {
670
688
  const blob = new Blob([transformedCode], {
671
689
  type: "application/javascript; charset=UTF-8"
@@ -692,10 +710,18 @@ async function handleTurbopackChunk(code, bundle, url) {
692
710
  document.head.appendChild(script);
693
711
  });
694
712
  const chunkLists = self[`TURBOPACK_${bundleKey}_CHUNK_LISTS`];
713
+ logDebug(
714
+ "ChunkLoader",
715
+ `Processing chunk lists for bundle "${bundle}": ${chunkLists?.length ?? 0} lists`
716
+ );
695
717
  const loadChunkLists = [];
696
718
  while (chunkLists?.length) {
697
719
  const { chunks } = chunkLists.shift() ?? { chunks: [] };
698
720
  if (chunks.length > 0) {
721
+ logDebug(
722
+ "ChunkLoader",
723
+ `Loading ${chunks.length} additional chunks for bundle "${bundle}": [${chunks.join(", ")}]`
724
+ );
699
725
  chunks.forEach((id) => {
700
726
  const chunkLoadResult = self.__webpack_chunk_load__?.(
701
727
  `[${bundle}] ${url.slice(0, url.indexOf("/_next"))}/_next/${id}`
@@ -707,6 +733,10 @@ async function handleTurbopackChunk(code, bundle, url) {
707
733
  }
708
734
  }
709
735
  if (loadChunkLists.length > 0) {
736
+ logDebug(
737
+ "ChunkLoader",
738
+ `Waiting for ${loadChunkLists.length} additional chunks to load`
739
+ );
710
740
  await Promise.all(loadChunkLists);
711
741
  }
712
742
  }
@@ -1424,9 +1454,57 @@ function getClientOrServerUrl(src, serverFallback) {
1424
1454
  return typeof src === "string" ? new URL(src, fallback) : src;
1425
1455
  }
1426
1456
 
1427
- // src/react/index.tsx
1428
- import { Fragment, jsx as jsx2, jsxs } from "react/jsx-runtime";
1429
- import { createElement as createElement2 } from "react";
1457
+ // src/react/hooks/use-shadow-root.ts
1458
+ import { useLayoutEffect, useRef, useState } from "react";
1459
+ function useShadowRoot({
1460
+ isolate,
1461
+ mode,
1462
+ keySuffix
1463
+ }) {
1464
+ const shadowRootContainerRef = useRef(null);
1465
+ const [shadowRoot, setShadowRoot] = useState(() => {
1466
+ const self = globalThis;
1467
+ const shadowRootKey = `__remote_components_shadowroot_${keySuffix}`;
1468
+ const ssrShadowRoot = typeof document !== "undefined" ? document.querySelector(
1469
+ `[data-remote-component-id="shadowroot_${keySuffix}"]`
1470
+ )?.shadowRoot ?? self[shadowRootKey] ?? null : null;
1471
+ self[shadowRootKey] = null;
1472
+ return ssrShadowRoot;
1473
+ });
1474
+ useLayoutEffect(() => {
1475
+ if (isolate !== false && typeof document !== "undefined" && (!shadowRoot || !shadowRoot.isConnected)) {
1476
+ const self = globalThis;
1477
+ const shadowRootKey = `__remote_components_shadowroot_${keySuffix}`;
1478
+ let shadowRootElement = null;
1479
+ const element = document.querySelector(
1480
+ `[data-remote-component-id="shadowroot_${keySuffix}"]`
1481
+ );
1482
+ shadowRootElement = self[shadowRootKey] ?? element?.shadowRoot ?? null;
1483
+ if (!shadowRootElement && element) {
1484
+ try {
1485
+ shadowRootElement = element.attachShadow({ mode });
1486
+ self[shadowRootKey] = shadowRootElement;
1487
+ } catch {
1488
+ }
1489
+ }
1490
+ if (shadowRootElement) {
1491
+ shadowRootElement.querySelectorAll("*:not(link)").forEach((node) => {
1492
+ node.remove();
1493
+ });
1494
+ setShadowRoot(shadowRootElement);
1495
+ }
1496
+ } else if (isolate === false && shadowRoot) {
1497
+ const self = globalThis;
1498
+ const shadowRootKey = `__remote_components_shadowroot_${keySuffix}`;
1499
+ self[shadowRootKey] = null;
1500
+ setShadowRoot(null);
1501
+ }
1502
+ }, [isolate, shadowRoot, mode, keySuffix]);
1503
+ return { shadowRoot, shadowRootContainerRef };
1504
+ }
1505
+
1506
+ // src/react/utils/parse-remote-html.ts
1507
+ var DUMMY_FALLBACK = "http://remote-components-dummy-fallback";
1430
1508
  function getRemoteComponentHtml(html) {
1431
1509
  if (typeof document === "undefined")
1432
1510
  return html;
@@ -1446,7 +1524,10 @@ function getRemoteComponentHtml(html) {
1446
1524
  }
1447
1525
  return "";
1448
1526
  }
1449
- var DUMMY_FALLBACK = "http://remote-components-dummy-fallback";
1527
+
1528
+ // src/react/index.tsx
1529
+ import { Fragment, jsx as jsx2, jsxs } from "react/jsx-runtime";
1530
+ import { createElement as createElement2 } from "react";
1450
1531
  function RemoteComponent({
1451
1532
  src,
1452
1533
  isolate,
@@ -1462,6 +1543,7 @@ function RemoteComponent({
1462
1543
  onError,
1463
1544
  onChange
1464
1545
  }) {
1546
+ const instanceId = useId();
1465
1547
  const name = useMemo(() => {
1466
1548
  if (typeof src === "string") {
1467
1549
  const url2 = new URL(
@@ -1476,28 +1558,23 @@ function RemoteComponent({
1476
1558
  }
1477
1559
  return nameProp;
1478
1560
  }, [src, nameProp]);
1479
- const [data, setData] = useState(null);
1561
+ const [data, setData] = useState2(null);
1480
1562
  const url = useMemo(() => getClientOrServerUrl(src, DUMMY_FALLBACK), [src]);
1481
1563
  const id = url.origin === (typeof location !== "undefined" ? location.origin : DUMMY_FALLBACK) ? url.pathname : url.href;
1482
- const keySuffix = `${escapeString(id)}_${escapeString(data?.name ?? name)}`;
1483
- const [remoteComponent, setRemoteComponent] = useState(null);
1484
- const shadowRootContainerRef = useRef(null);
1485
- const [shadowRoot, setShadowRoot] = useState(() => {
1486
- const self = globalThis;
1487
- const shadowRootKey = `__remote_components_shadowroot_${keySuffix}`;
1488
- const ssrShadowRoot = typeof document !== "undefined" ? document.querySelector(
1489
- `[data-remote-component-id="shadowroot_${keySuffix}"]`
1490
- )?.shadowRoot ?? self[shadowRootKey] ?? null : null;
1491
- self[shadowRootKey] = null;
1492
- return ssrShadowRoot;
1564
+ const keySuffix = `${escapeString(id)}_${escapeString(data?.name ?? name)}_${escapeString(instanceId)}`;
1565
+ const [remoteComponent, setRemoteComponent] = useState2(null);
1566
+ const { shadowRoot, shadowRootContainerRef } = useShadowRoot({
1567
+ isolate,
1568
+ mode,
1569
+ keySuffix
1493
1570
  });
1494
- const htmlRef = useRef(
1571
+ const htmlRef = useRef2(
1495
1572
  typeof document !== "undefined" ? document.querySelector(
1496
1573
  `[data-remote-component-id="shadowroot_${keySuffix}"]`
1497
1574
  )?.shadowRoot?.innerHTML ?? document.getElementById(`__REMOTE_COMPONENT${name}`)?.innerHTML ?? document.querySelector(`div[data-bundle][data-route][id^="${name}"]`)?.innerHTML ?? document.querySelector("div[data-bundle][data-route]")?.innerHTML : null
1498
1575
  );
1499
- const endTemplateRef = useRef(null);
1500
- const childrenRef = useRef(
1576
+ const endTemplateRef = useRef2(null);
1577
+ const childrenRef = useRef2(
1501
1578
  typeof document !== "undefined" ? (() => {
1502
1579
  let el = document.querySelector(`template[id="${name}_start"]`);
1503
1580
  const elements = [];
@@ -1510,44 +1587,28 @@ function RemoteComponent({
1510
1587
  return elements;
1511
1588
  })() : []
1512
1589
  );
1513
- const prevSrcRef = useRef(null);
1514
- const componentHydrationHtml = useRef(null);
1515
- const prevIsRemoteComponentRef = useRef(false);
1516
- const prevUrlRef = useRef(null);
1517
- const prevRemoteComponentContainerRef = useRef(null);
1518
- const unmountRef = useRef(null);
1519
- const prevNameRef = useRef(void 0);
1520
- useLayoutEffect(() => {
1590
+ const prevSrcRef = useRef2(null);
1591
+ const componentHydrationHtml = useRef2(null);
1592
+ const prevIsRemoteComponentRef = useRef2(false);
1593
+ const prevUrlRef = useRef2(null);
1594
+ const prevRemoteComponentContainerRef = useRef2(null);
1595
+ const unmountRef = useRef2(null);
1596
+ const prevNameRef = useRef2(void 0);
1597
+ useLayoutEffect2(() => {
1598
+ const shadowRootKey = `__remote_components_shadowroot_${keySuffix}`;
1599
+ return () => {
1600
+ delete globalThis[shadowRootKey];
1601
+ };
1602
+ }, [keySuffix]);
1603
+ useLayoutEffect2(() => {
1521
1604
  if (childrenRef.current.length > 0 && remoteComponent) {
1522
1605
  childrenRef.current.forEach((el) => {
1523
1606
  el.remove();
1524
1607
  });
1525
1608
  childrenRef.current = [];
1526
1609
  }
1527
- if (isolate !== false && typeof document !== "undefined" && (!shadowRoot || !shadowRoot.isConnected)) {
1528
- const self = globalThis;
1529
- const shadowRootKey = `__remote_components_shadowroot_${keySuffix}`;
1530
- let shadowRootElement = null;
1531
- const element = document.querySelector(
1532
- `[data-remote-component-id="shadowroot_${keySuffix}"]`
1533
- );
1534
- shadowRootElement = self[shadowRootKey] ?? element?.shadowRoot ?? null;
1535
- if (!shadowRootElement && element) {
1536
- try {
1537
- shadowRootElement = element.attachShadow({ mode });
1538
- self[shadowRootKey] = shadowRootElement;
1539
- } catch {
1540
- }
1541
- }
1542
- if (shadowRootElement) {
1543
- shadowRootElement.querySelectorAll("*:not(link)").forEach((node) => {
1544
- node.remove();
1545
- });
1546
- setShadowRoot(shadowRootElement);
1547
- }
1548
- }
1549
- }, [isolate, shadowRoot, remoteComponent, mode, keySuffix]);
1550
- useLayoutEffect(() => {
1610
+ }, [remoteComponent]);
1611
+ useLayoutEffect2(() => {
1551
1612
  if (shadowRoot && remoteComponent) {
1552
1613
  const resetStyles = shadowRoot.querySelectorAll(
1553
1614
  "style[data-remote-components-reset]"