remote-components 0.1.2 → 0.2.0
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/dist/{next/config.cjs → config/nextjs.cjs} +76 -101
- package/dist/config/nextjs.cjs.map +1 -0
- package/dist/{next/config.d.ts → config/nextjs.d.ts} +4 -4
- package/dist/{next/config.js → config/nextjs.js} +72 -97
- package/dist/config/nextjs.js.map +1 -0
- package/dist/{webpack.cjs → config/webpack.cjs} +13 -29
- package/dist/config/webpack.cjs.map +1 -0
- package/dist/{webpack.js → config/webpack.js} +12 -28
- package/dist/config/webpack.js.map +1 -0
- package/dist/{shared/remote → host/defaults}/app.cjs +2 -2
- package/dist/host/defaults/app.cjs.map +1 -0
- package/dist/host/defaults/app.js +8 -0
- package/dist/host/defaults/app.js.map +1 -0
- package/dist/{shared/remote → host/defaults}/pages.cjs +2 -2
- package/dist/host/defaults/pages.cjs.map +1 -0
- package/dist/host/defaults/pages.js +8 -0
- package/dist/host/defaults/pages.js.map +1 -0
- package/dist/{html/host.cjs → host/html.cjs} +1012 -1075
- package/dist/host/html.cjs.map +1 -0
- package/dist/{html/host.d.ts → host/html.d.ts} +0 -2
- package/dist/{html/host.js → host/html.js} +1009 -1071
- package/dist/host/html.js.map +1 -0
- package/dist/{next/host/client/index.cjs → host/nextjs/app/client-only.cjs} +681 -617
- package/dist/host/nextjs/app/client-only.cjs.map +1 -0
- package/dist/host/nextjs/app/client-only.d.ts +16 -0
- package/dist/{next/host/client/index.js → host/nextjs/app/client-only.js} +682 -611
- package/dist/host/nextjs/app/client-only.js.map +1 -0
- package/dist/{next/host/app-router-server.cjs → host/nextjs/app.cjs} +11 -10
- package/dist/host/nextjs/app.cjs.map +1 -0
- package/dist/host/nextjs/app.d.ts +29 -0
- package/dist/{next/host/app-router-server.js → host/nextjs/app.js} +7 -6
- package/dist/host/nextjs/app.js.map +1 -0
- package/dist/{next/host/pages-router-client.cjs → host/nextjs/pages/client-only.cjs} +8 -8
- package/dist/host/nextjs/pages/client-only.cjs.map +1 -0
- package/dist/host/nextjs/pages/client-only.d.ts +31 -0
- package/dist/{next/host/pages-router-client.js → host/nextjs/pages/client-only.js} +4 -4
- package/dist/host/nextjs/pages/client-only.js.map +1 -0
- package/dist/{next/host/pages-router-server.cjs → host/nextjs/pages.cjs} +44 -55
- package/dist/host/nextjs/pages.cjs.map +1 -0
- package/dist/{next/host/pages-router-server.d.ts → host/nextjs/pages.d.ts} +11 -13
- package/dist/{next/host/pages-router-server.js → host/nextjs/pages.js} +38 -49
- package/dist/host/nextjs/pages.js.map +1 -0
- package/dist/host/proxy/client.cjs +57 -0
- package/dist/host/proxy/client.cjs.map +1 -0
- package/dist/host/proxy/client.d.ts +31 -0
- package/dist/host/proxy/client.js +30 -0
- package/dist/host/proxy/client.js.map +1 -0
- package/dist/{shared/host/proxy.cjs → host/proxy/protected-fetch.cjs} +6 -6
- package/dist/host/proxy/protected-fetch.cjs.map +1 -0
- package/dist/{shared/host/proxy.js → host/proxy/protected-fetch.js} +3 -3
- package/dist/host/proxy/protected-fetch.js.map +1 -0
- package/dist/{next → host}/proxy.cjs +12 -92
- package/dist/host/proxy.cjs.map +1 -0
- package/dist/host/proxy.d.ts +30 -0
- package/dist/{next → host}/proxy.js +11 -88
- package/dist/host/proxy.js.map +1 -0
- package/dist/{react/index.cjs → host/react.cjs} +515 -548
- package/dist/host/react.cjs.map +1 -0
- package/dist/{component-loader-21865da3.d.ts → host/react.d.ts} +141 -99
- package/dist/{react/index.js → host/react.js} +514 -545
- package/dist/host/react.js.map +1 -0
- package/dist/internal/{webpack/shared-modules.cjs → config/webpack/apply-shared-modules.cjs} +12 -15
- package/dist/internal/config/webpack/apply-shared-modules.cjs.map +1 -0
- package/dist/internal/{webpack/shared-modules.js → config/webpack/apply-shared-modules.js} +9 -12
- package/dist/internal/config/webpack/apply-shared-modules.js.map +1 -0
- package/dist/internal/{webpack → config/webpack}/next-client-pages-loader.cjs +1 -1
- package/dist/internal/config/webpack/next-client-pages-loader.cjs.map +1 -0
- package/dist/internal/{webpack → config/webpack}/next-client-pages-loader.js +1 -1
- package/dist/internal/config/webpack/next-client-pages-loader.js.map +1 -0
- package/dist/internal/{next/host/app-router-client.cjs → host/nextjs/app-client.cjs} +29 -24
- package/dist/internal/host/nextjs/app-client.cjs.map +1 -0
- package/dist/internal/host/nextjs/app-client.d.ts +25 -0
- package/dist/internal/{next/host/app-router-client.js → host/nextjs/app-client.js} +19 -19
- package/dist/internal/host/nextjs/app-client.js.map +1 -0
- package/dist/internal/{next/host/app-router-compat.cjs → host/nextjs/app-compat.cjs} +5 -22
- package/dist/internal/host/nextjs/app-compat.cjs.map +1 -0
- package/dist/internal/{next/host/app-router-compat.d.ts → host/nextjs/app-compat.d.ts} +1 -7
- package/dist/internal/{next/host/app-router-compat.js → host/nextjs/app-compat.js} +2 -18
- package/dist/internal/host/nextjs/app-compat.js.map +1 -0
- package/dist/internal/host/nextjs/dom-flight.cjs.map +1 -0
- package/dist/internal/host/nextjs/dom-flight.d.ts +39 -0
- package/dist/internal/host/nextjs/dom-flight.js.map +1 -0
- package/dist/internal/host/nextjs/image-impl.cjs +60 -0
- package/dist/internal/host/nextjs/image-impl.cjs.map +1 -0
- package/dist/internal/host/nextjs/image-impl.d.ts +10 -0
- package/dist/internal/host/nextjs/image-impl.js +36 -0
- package/dist/internal/host/nextjs/image-impl.js.map +1 -0
- package/dist/internal/host/nextjs/image-shared.cjs +43 -0
- package/dist/internal/host/nextjs/image-shared.cjs.map +1 -0
- package/dist/internal/host/nextjs/image-shared.d.ts +9 -0
- package/dist/internal/host/nextjs/image-shared.js +19 -0
- package/dist/internal/host/nextjs/image-shared.js.map +1 -0
- package/dist/internal/{next/host → host/nextjs}/remote-component-links.cjs +2 -2
- package/dist/internal/host/nextjs/remote-component-links.cjs.map +1 -0
- package/dist/internal/{next/host → host/nextjs}/remote-component-links.d.ts +1 -1
- package/dist/internal/{next/host → host/nextjs}/remote-component-links.js +2 -2
- package/dist/internal/host/nextjs/remote-component-links.js.map +1 -0
- package/dist/internal/host/nextjs/skeleton.cjs.map +1 -0
- package/dist/internal/host/nextjs/skeleton.js.map +1 -0
- package/dist/internal/{react → host/react}/context.cjs +3 -3
- package/dist/internal/host/react/context.cjs.map +1 -0
- package/dist/internal/{react → host/react}/context.d.ts +4 -4
- package/dist/internal/{react → host/react}/context.js +2 -2
- package/dist/internal/host/react/context.js.map +1 -0
- package/dist/internal/{react → host/react}/hooks/use-resolve-client-url.cjs +2 -2
- package/dist/internal/host/react/hooks/use-resolve-client-url.cjs.map +1 -0
- package/dist/internal/{react → host/react}/hooks/use-resolve-client-url.d.ts +1 -1
- package/dist/internal/{react → host/react}/hooks/use-resolve-client-url.js +2 -2
- package/dist/internal/host/react/hooks/use-resolve-client-url.js.map +1 -0
- package/dist/internal/host/server/fetch-headers.cjs.map +1 -0
- package/dist/internal/host/server/fetch-headers.js.map +1 -0
- package/dist/internal/{shared/ssr → host/server}/fetch-remote-component.cjs +6 -6
- package/dist/internal/host/server/fetch-remote-component.cjs.map +1 -0
- package/dist/internal/{shared/ssr → host/server}/fetch-remote-component.d.ts +6 -1
- package/dist/internal/{shared/ssr → host/server}/fetch-remote-component.js +9 -9
- package/dist/internal/host/server/fetch-remote-component.js.map +1 -0
- package/dist/internal/{shared/ssr → host/server}/fetch-with-hooks.cjs +11 -15
- package/dist/internal/host/server/fetch-with-hooks.cjs.map +1 -0
- package/dist/internal/host/server/fetch-with-hooks.d.ts +21 -0
- package/dist/internal/{shared/ssr → host/server}/fetch-with-hooks.js +11 -15
- package/dist/internal/host/server/fetch-with-hooks.js.map +1 -0
- package/dist/internal/host/server/get-client-or-server-url.cjs.map +1 -0
- package/dist/internal/host/server/get-client-or-server-url.js.map +1 -0
- package/dist/internal/{shared/client → host/server}/get-client-src.cjs +1 -1
- package/dist/internal/host/server/get-client-src.cjs.map +1 -0
- package/dist/internal/{shared/client → host/server}/get-client-src.js +1 -1
- package/dist/internal/host/server/get-client-src.js.map +1 -0
- package/dist/internal/host/server/get-ssr-relative-path-base-url.cjs.map +1 -0
- package/dist/internal/host/server/get-ssr-relative-path-base-url.js.map +1 -0
- package/dist/{next/remote/server.cjs → internal/host/server/types.cjs} +3 -15
- package/dist/internal/host/server/types.cjs.map +1 -0
- package/dist/internal/host/server/types.d.ts +33 -0
- package/dist/internal/host/server/types.js +1 -0
- package/dist/internal/host/server/types.js.map +1 -0
- package/dist/internal/host/shared/asset-descriptors.cjs +17 -0
- package/dist/internal/host/shared/asset-descriptors.cjs.map +1 -0
- package/dist/internal/host/shared/asset-descriptors.d.ts +21 -0
- package/dist/internal/host/shared/asset-descriptors.js +1 -0
- package/dist/internal/host/shared/asset-descriptors.js.map +1 -0
- package/dist/internal/host/shared/config.cjs +17 -0
- package/dist/internal/host/shared/config.cjs.map +1 -0
- package/dist/{host-config-58cdccea.d.ts → internal/host/shared/config.d.ts} +32 -19
- package/dist/internal/host/shared/config.js +1 -0
- package/dist/internal/host/shared/config.js.map +1 -0
- package/dist/internal/host/shared/fetch-interceptors.cjs +17 -0
- package/dist/internal/host/shared/fetch-interceptors.cjs.map +1 -0
- package/dist/{types-2b26a246.d.ts → internal/host/shared/fetch-interceptors.d.ts} +4 -87
- package/dist/internal/host/shared/fetch-interceptors.js +1 -0
- package/dist/internal/host/shared/fetch-interceptors.js.map +1 -0
- package/dist/internal/{shared/client → host/shared}/polyfill.cjs +7 -6
- package/dist/internal/host/shared/polyfill.cjs.map +1 -0
- package/dist/internal/{shared/client → host/shared}/polyfill.d.ts +2 -1
- package/dist/internal/{shared/client → host/shared}/polyfill.js +7 -6
- package/dist/internal/host/shared/polyfill.js.map +1 -0
- package/dist/internal/host/shared/resolved-data.cjs +17 -0
- package/dist/internal/host/shared/resolved-data.cjs.map +1 -0
- package/dist/internal/host/shared/resolved-data.d.ts +48 -0
- package/dist/internal/host/shared/resolved-data.js +1 -0
- package/dist/internal/host/shared/resolved-data.js.map +1 -0
- package/dist/internal/{shared/contract/host-state.cjs → host/shared/state.cjs} +4 -4
- package/dist/internal/host/shared/state.cjs.map +1 -0
- package/dist/internal/{shared/contract/host-state.js → host/shared/state.js} +1 -1
- package/dist/internal/host/shared/state.js.map +1 -0
- package/dist/internal/host/utils/resolve-name-from-src.cjs.map +1 -0
- package/dist/internal/host/utils/resolve-name-from-src.js.map +1 -0
- package/dist/internal/{next/remote/render-client.cjs → remote/nextjs/app-client.cjs} +8 -8
- package/dist/internal/remote/nextjs/app-client.cjs.map +1 -0
- package/dist/internal/{next/remote/render-client.js → remote/nextjs/app-client.js} +4 -4
- package/dist/internal/remote/nextjs/app-client.js.map +1 -0
- package/dist/internal/runtime/constants.cjs +50 -0
- package/dist/internal/runtime/constants.cjs.map +1 -0
- package/dist/internal/runtime/constants.d.ts +10 -0
- package/dist/internal/runtime/constants.js +20 -0
- package/dist/internal/runtime/constants.js.map +1 -0
- package/dist/internal/{shared/client → runtime/html}/apply-origin.cjs.map +1 -1
- package/dist/internal/{shared/client → runtime/html}/apply-origin.d.ts +1 -1
- package/dist/internal/{shared/client → runtime/html}/apply-origin.js.map +1 -1
- package/dist/internal/runtime/html/parse-remote-html.cjs +140 -0
- package/dist/internal/runtime/html/parse-remote-html.cjs.map +1 -0
- package/dist/internal/runtime/html/parse-remote-html.d.ts +88 -0
- package/dist/internal/runtime/html/parse-remote-html.js +110 -0
- package/dist/internal/runtime/html/parse-remote-html.js.map +1 -0
- package/dist/internal/runtime/html/set-attributes-from-props.cjs +68 -0
- package/dist/internal/runtime/html/set-attributes-from-props.cjs.map +1 -0
- package/dist/internal/runtime/html/set-attributes-from-props.d.ts +3 -0
- package/dist/internal/runtime/html/set-attributes-from-props.js +44 -0
- package/dist/internal/runtime/html/set-attributes-from-props.js.map +1 -0
- package/dist/internal/runtime/loaders/component-loader.cjs +184 -0
- package/dist/internal/runtime/loaders/component-loader.cjs.map +1 -0
- package/dist/internal/runtime/loaders/component-loader.d.ts +31 -0
- package/dist/internal/runtime/loaders/component-loader.js +150 -0
- package/dist/internal/runtime/loaders/component-loader.js.map +1 -0
- package/dist/internal/runtime/loaders/script-loader.cjs +69 -0
- package/dist/internal/runtime/loaders/script-loader.cjs.map +1 -0
- package/dist/internal/runtime/loaders/script-loader.d.ts +10 -0
- package/dist/internal/runtime/loaders/script-loader.js +48 -0
- package/dist/internal/runtime/loaders/script-loader.js.map +1 -0
- package/dist/internal/runtime/loaders/static-loader.cjs +177 -0
- package/dist/internal/runtime/loaders/static-loader.cjs.map +1 -0
- package/dist/internal/runtime/loaders/static-loader.d.ts +10 -0
- package/dist/internal/runtime/loaders/static-loader.js +153 -0
- package/dist/internal/runtime/loaders/static-loader.js.map +1 -0
- package/dist/internal/runtime/metadata.cjs +17 -0
- package/dist/internal/runtime/metadata.cjs.map +1 -0
- package/dist/internal/runtime/metadata.d.ts +16 -0
- package/dist/internal/runtime/metadata.js +1 -0
- package/dist/internal/runtime/metadata.js.map +1 -0
- package/dist/internal/runtime/rsc.cjs +92 -0
- package/dist/internal/runtime/rsc.cjs.map +1 -0
- package/dist/internal/runtime/rsc.d.ts +8 -0
- package/dist/internal/runtime/rsc.js +68 -0
- package/dist/internal/runtime/rsc.js.map +1 -0
- package/dist/internal/runtime/turbopack/chunk-loader.cjs +244 -0
- package/dist/internal/runtime/turbopack/chunk-loader.cjs.map +1 -0
- package/dist/internal/runtime/turbopack/chunk-loader.d.ts +11 -0
- package/dist/internal/runtime/turbopack/chunk-loader.js +227 -0
- package/dist/internal/runtime/turbopack/chunk-loader.js.map +1 -0
- package/dist/internal/runtime/turbopack/module.cjs +257 -0
- package/dist/internal/runtime/turbopack/module.cjs.map +1 -0
- package/dist/internal/runtime/turbopack/module.d.ts +61 -0
- package/dist/internal/runtime/turbopack/module.js +233 -0
- package/dist/internal/runtime/turbopack/module.js.map +1 -0
- package/dist/internal/runtime/turbopack/patterns.cjs +44 -0
- package/dist/internal/runtime/turbopack/patterns.cjs.map +1 -0
- package/dist/internal/runtime/turbopack/patterns.d.ts +109 -0
- package/dist/internal/runtime/turbopack/patterns.js +15 -0
- package/dist/internal/runtime/turbopack/patterns.js.map +1 -0
- package/dist/internal/runtime/turbopack/shared-modules.cjs +152 -0
- package/dist/internal/runtime/turbopack/shared-modules.cjs.map +1 -0
- package/dist/internal/runtime/turbopack/shared-modules.d.ts +17 -0
- package/dist/internal/runtime/turbopack/shared-modules.js +133 -0
- package/dist/internal/runtime/turbopack/shared-modules.js.map +1 -0
- package/dist/internal/runtime/turbopack/webpack-runtime.cjs +137 -0
- package/dist/internal/runtime/turbopack/webpack-runtime.cjs.map +1 -0
- package/dist/internal/runtime/turbopack/webpack-runtime.d.ts +20 -0
- package/dist/internal/runtime/turbopack/webpack-runtime.js +107 -0
- package/dist/internal/runtime/turbopack/webpack-runtime.js.map +1 -0
- package/dist/internal/runtime/types.cjs +17 -0
- package/dist/internal/runtime/types.cjs.map +1 -0
- package/dist/internal/runtime/types.d.ts +40 -0
- package/dist/internal/runtime/types.js +1 -0
- package/dist/internal/runtime/types.js.map +1 -0
- package/dist/internal/{shared/client → runtime/url}/default-resolve-client-url.cjs +2 -2
- package/dist/internal/runtime/url/default-resolve-client-url.cjs.map +1 -0
- package/dist/internal/{shared/client → runtime/url}/default-resolve-client-url.d.ts +1 -1
- package/dist/internal/{shared/client → runtime/url}/default-resolve-client-url.js +1 -1
- package/dist/internal/runtime/url/default-resolve-client-url.js.map +1 -0
- package/dist/internal/{shared/client → runtime/url}/protected-rc-fallback.cjs +1 -1
- package/dist/internal/runtime/url/protected-rc-fallback.cjs.map +1 -0
- package/dist/internal/{shared/client → runtime/url}/protected-rc-fallback.js +1 -1
- package/dist/internal/runtime/url/protected-rc-fallback.js.map +1 -0
- package/dist/internal/{shared/client/proxy-through-host.cjs → runtime/url/resolve-client-url.cjs} +4 -24
- package/dist/internal/runtime/url/resolve-client-url.cjs.map +1 -0
- package/dist/internal/{shared/client/proxy-through-host.d.ts → runtime/url/resolve-client-url.d.ts} +1 -25
- package/dist/internal/runtime/url/resolve-client-url.js +21 -0
- package/dist/internal/runtime/url/resolve-client-url.js.map +1 -0
- package/dist/internal/utils/abort.cjs.map +1 -0
- package/dist/internal/utils/abort.js.map +1 -0
- package/dist/internal/{shared → utils}/constants.cjs +3 -0
- package/dist/internal/utils/constants.cjs.map +1 -0
- package/dist/internal/utils/constants.d.ts +5 -0
- package/dist/internal/{shared → utils}/constants.js +2 -0
- package/dist/internal/utils/constants.js.map +1 -0
- package/dist/internal/{shared → utils}/error.cjs +4 -4
- package/dist/internal/utils/error.cjs.map +1 -0
- package/dist/internal/{shared → utils}/error.js +4 -4
- package/dist/internal/utils/error.js.map +1 -0
- package/dist/internal/{shared/utils → utils}/logger.cjs +3 -3
- package/dist/internal/utils/logger.cjs.map +1 -0
- package/dist/internal/{shared/utils → utils}/logger.d.ts +2 -2
- package/dist/internal/{shared/utils → utils}/logger.js +3 -3
- package/dist/internal/utils/logger.js.map +1 -0
- package/dist/internal/utils.cjs.map +1 -0
- package/dist/internal/utils.js.map +1 -0
- package/dist/{shared/host → remote/defaults}/app.cjs +2 -6
- package/dist/remote/defaults/app.cjs.map +1 -0
- package/dist/remote/defaults/app.js +8 -0
- package/dist/remote/defaults/app.js.map +1 -0
- package/dist/{shared/host → remote/defaults}/pages.cjs +2 -6
- package/dist/remote/defaults/pages.cjs.map +1 -0
- package/dist/remote/defaults/pages.js +8 -0
- package/dist/remote/defaults/pages.js.map +1 -0
- package/dist/{shared/remote → remote/defaults}/wrapper.cjs +12 -10
- package/dist/remote/defaults/wrapper.cjs.map +1 -0
- package/dist/remote/defaults/wrapper.js +27 -0
- package/dist/remote/defaults/wrapper.js.map +1 -0
- package/dist/{html/remote.cjs → remote/html.cjs} +16 -16
- package/dist/remote/html.cjs.map +1 -0
- package/dist/{html/remote.js → remote/html.js} +16 -16
- package/dist/remote/html.js.map +1 -0
- package/dist/{shared/remote/proxy.cjs → remote/middleware.cjs} +37 -12
- package/dist/remote/middleware.cjs.map +1 -0
- package/dist/remote/middleware.d.ts +27 -0
- package/dist/{shared/remote/proxy.js → remote/middleware.js} +32 -5
- package/dist/remote/middleware.js.map +1 -0
- package/dist/{internal/next/remote/render-server.cjs → remote/nextjs/app.cjs} +14 -16
- package/dist/remote/nextjs/app.cjs.map +1 -0
- package/dist/{internal/next/remote/render-server.d.ts → remote/nextjs/app.d.ts} +12 -13
- package/dist/{internal/next/remote/render-server.js → remote/nextjs/app.js} +9 -11
- package/dist/remote/nextjs/app.js.map +1 -0
- package/dist/{next/remote/pages-router.cjs → remote/nextjs/pages.cjs} +8 -8
- package/dist/remote/nextjs/pages.cjs.map +1 -0
- package/dist/{next/remote/pages-router.d.ts → remote/nextjs/pages.d.ts} +8 -8
- package/dist/{next/remote/pages-router.js → remote/nextjs/pages.js} +4 -4
- package/dist/remote/nextjs/pages.js.map +1 -0
- package/dist/server-handoff-8c89b856.d.ts +46 -0
- package/package.json +126 -157
- package/dist/html/host.cjs.map +0 -1
- package/dist/html/host.js.map +0 -1
- package/dist/html/remote.cjs.map +0 -1
- package/dist/html/remote.js.map +0 -1
- package/dist/internal/next/host/app-router-client.cjs.map +0 -1
- package/dist/internal/next/host/app-router-client.d.ts +0 -79
- package/dist/internal/next/host/app-router-client.js.map +0 -1
- package/dist/internal/next/host/app-router-compat.cjs.map +0 -1
- package/dist/internal/next/host/app-router-compat.js.map +0 -1
- package/dist/internal/next/host/remote-component-links.cjs.map +0 -1
- package/dist/internal/next/host/remote-component-links.js.map +0 -1
- package/dist/internal/next/remote/render-client.cjs.map +0 -1
- package/dist/internal/next/remote/render-client.js.map +0 -1
- package/dist/internal/next/remote/render-server.cjs.map +0 -1
- package/dist/internal/next/remote/render-server.js.map +0 -1
- package/dist/internal/react/context.cjs.map +0 -1
- package/dist/internal/react/context.js.map +0 -1
- package/dist/internal/react/hooks/use-resolve-client-url.cjs.map +0 -1
- package/dist/internal/react/hooks/use-resolve-client-url.js.map +0 -1
- package/dist/internal/shared/client/default-resolve-client-url.cjs.map +0 -1
- package/dist/internal/shared/client/default-resolve-client-url.js.map +0 -1
- package/dist/internal/shared/client/get-client-src.cjs.map +0 -1
- package/dist/internal/shared/client/get-client-src.js.map +0 -1
- package/dist/internal/shared/client/polyfill.cjs.map +0 -1
- package/dist/internal/shared/client/polyfill.js.map +0 -1
- package/dist/internal/shared/client/protected-rc-fallback.cjs.map +0 -1
- package/dist/internal/shared/client/protected-rc-fallback.js.map +0 -1
- package/dist/internal/shared/client/proxy-through-host.cjs.map +0 -1
- package/dist/internal/shared/client/proxy-through-host.js +0 -40
- package/dist/internal/shared/client/proxy-through-host.js.map +0 -1
- package/dist/internal/shared/client/remote-component.cjs +0 -1436
- package/dist/internal/shared/client/remote-component.cjs.map +0 -1
- package/dist/internal/shared/client/remote-component.d.ts +0 -62
- package/dist/internal/shared/client/remote-component.js +0 -1385
- package/dist/internal/shared/client/remote-component.js.map +0 -1
- package/dist/internal/shared/constants.cjs.map +0 -1
- package/dist/internal/shared/constants.d.ts +0 -4
- package/dist/internal/shared/constants.js.map +0 -1
- package/dist/internal/shared/contract/host-state.cjs.map +0 -1
- package/dist/internal/shared/contract/host-state.js.map +0 -1
- package/dist/internal/shared/contract/resolve-name-from-src.cjs.map +0 -1
- package/dist/internal/shared/contract/resolve-name-from-src.js.map +0 -1
- package/dist/internal/shared/error.cjs.map +0 -1
- package/dist/internal/shared/error.js.map +0 -1
- package/dist/internal/shared/ssr/dom-flight.cjs.map +0 -1
- package/dist/internal/shared/ssr/dom-flight.d.ts +0 -2
- package/dist/internal/shared/ssr/dom-flight.js.map +0 -1
- package/dist/internal/shared/ssr/fetch-headers.cjs.map +0 -1
- package/dist/internal/shared/ssr/fetch-headers.js.map +0 -1
- package/dist/internal/shared/ssr/fetch-remote-component.cjs.map +0 -1
- package/dist/internal/shared/ssr/fetch-remote-component.js.map +0 -1
- package/dist/internal/shared/ssr/fetch-with-hooks.cjs.map +0 -1
- package/dist/internal/shared/ssr/fetch-with-hooks.d.ts +0 -56
- package/dist/internal/shared/ssr/fetch-with-hooks.js.map +0 -1
- package/dist/internal/shared/ssr/get-client-or-server-url.cjs.map +0 -1
- package/dist/internal/shared/ssr/get-client-or-server-url.js.map +0 -1
- package/dist/internal/shared/ssr/get-ssr-relative-path-base-url.cjs.map +0 -1
- package/dist/internal/shared/ssr/get-ssr-relative-path-base-url.js.map +0 -1
- package/dist/internal/shared/ssr/skeleton.cjs.map +0 -1
- package/dist/internal/shared/ssr/skeleton.js.map +0 -1
- package/dist/internal/shared/utils/abort.cjs.map +0 -1
- package/dist/internal/shared/utils/abort.js.map +0 -1
- package/dist/internal/shared/utils/logger.cjs.map +0 -1
- package/dist/internal/shared/utils/logger.js.map +0 -1
- package/dist/internal/shared/utils.cjs.map +0 -1
- package/dist/internal/shared/utils.js.map +0 -1
- package/dist/internal/webpack/next-client-pages-loader.cjs.map +0 -1
- package/dist/internal/webpack/next-client-pages-loader.js.map +0 -1
- package/dist/internal/webpack/shared-modules.cjs.map +0 -1
- package/dist/internal/webpack/shared-modules.js.map +0 -1
- package/dist/next/config.cjs.map +0 -1
- package/dist/next/config.js.map +0 -1
- package/dist/next/host/app-router-server.cjs.map +0 -1
- package/dist/next/host/app-router-server.d.ts +0 -30
- package/dist/next/host/app-router-server.js.map +0 -1
- package/dist/next/host/client/index.cjs.map +0 -1
- package/dist/next/host/client/index.d.ts +0 -19
- package/dist/next/host/client/index.js.map +0 -1
- package/dist/next/host/pages-router-client.cjs.map +0 -1
- package/dist/next/host/pages-router-client.d.ts +0 -33
- package/dist/next/host/pages-router-client.js.map +0 -1
- package/dist/next/host/pages-router-server.cjs.map +0 -1
- package/dist/next/host/pages-router-server.js.map +0 -1
- package/dist/next/index.cjs +0 -53
- package/dist/next/index.cjs.map +0 -1
- package/dist/next/index.d.ts +0 -30
- package/dist/next/index.js +0 -19
- package/dist/next/index.js.map +0 -1
- package/dist/next/proxy.cjs.map +0 -1
- package/dist/next/proxy.d.ts +0 -56
- package/dist/next/proxy.js.map +0 -1
- package/dist/next/remote/pages-router.cjs.map +0 -1
- package/dist/next/remote/pages-router.js.map +0 -1
- package/dist/next/remote/server.cjs.map +0 -1
- package/dist/next/remote/server.d.ts +0 -5
- package/dist/next/remote/server.js +0 -5
- package/dist/next/remote/server.js.map +0 -1
- package/dist/proxy-through-host-a676a522.d.ts +0 -52
- package/dist/react/index.cjs.map +0 -1
- package/dist/react/index.d.ts +0 -86
- package/dist/react/index.js.map +0 -1
- package/dist/shared/host/app.cjs.map +0 -1
- package/dist/shared/host/app.js +0 -12
- package/dist/shared/host/app.js.map +0 -1
- package/dist/shared/host/pages.cjs.map +0 -1
- package/dist/shared/host/pages.js +0 -12
- package/dist/shared/host/pages.js.map +0 -1
- package/dist/shared/host/proxy.cjs.map +0 -1
- package/dist/shared/host/proxy.js.map +0 -1
- package/dist/shared/remote/app.cjs.map +0 -1
- package/dist/shared/remote/app.js +0 -8
- package/dist/shared/remote/app.js.map +0 -1
- package/dist/shared/remote/pages.cjs.map +0 -1
- package/dist/shared/remote/pages.js +0 -8
- package/dist/shared/remote/pages.js.map +0 -1
- package/dist/shared/remote/proxy.cjs.map +0 -1
- package/dist/shared/remote/proxy.d.ts +0 -44
- package/dist/shared/remote/proxy.js.map +0 -1
- package/dist/shared/remote/wrapper.cjs.map +0 -1
- package/dist/shared/remote/wrapper.js +0 -25
- package/dist/shared/remote/wrapper.js.map +0 -1
- package/dist/webpack.cjs.map +0 -1
- package/dist/webpack.js.map +0 -1
- /package/dist/{webpack.d.ts → config/webpack.d.ts} +0 -0
- /package/dist/{shared/host → host/defaults}/app.d.ts +0 -0
- /package/dist/{shared/host → host/defaults}/pages.d.ts +0 -0
- /package/dist/{shared/host/proxy.d.ts → host/proxy/protected-fetch.d.ts} +0 -0
- /package/dist/internal/{webpack/shared-modules.d.ts → config/webpack/apply-shared-modules.d.ts} +0 -0
- /package/dist/internal/{webpack → config/webpack}/next-client-pages-loader.d.ts +0 -0
- /package/dist/internal/{shared/ssr → host/nextjs}/dom-flight.cjs +0 -0
- /package/dist/internal/{shared/ssr → host/nextjs}/dom-flight.js +0 -0
- /package/dist/internal/{shared/ssr → host/nextjs}/skeleton.cjs +0 -0
- /package/dist/internal/{shared/ssr → host/nextjs}/skeleton.d.ts +0 -0
- /package/dist/internal/{shared/ssr → host/nextjs}/skeleton.js +0 -0
- /package/dist/internal/{shared/ssr → host/server}/fetch-headers.cjs +0 -0
- /package/dist/internal/{shared/ssr → host/server}/fetch-headers.d.ts +0 -0
- /package/dist/internal/{shared/ssr → host/server}/fetch-headers.js +0 -0
- /package/dist/internal/{shared/ssr → host/server}/get-client-or-server-url.cjs +0 -0
- /package/dist/internal/{shared/ssr → host/server}/get-client-or-server-url.d.ts +0 -0
- /package/dist/internal/{shared/ssr → host/server}/get-client-or-server-url.js +0 -0
- /package/dist/internal/{shared/client → host/server}/get-client-src.d.ts +0 -0
- /package/dist/internal/{shared/ssr → host/server}/get-ssr-relative-path-base-url.cjs +0 -0
- /package/dist/internal/{shared/ssr → host/server}/get-ssr-relative-path-base-url.d.ts +0 -0
- /package/dist/internal/{shared/ssr → host/server}/get-ssr-relative-path-base-url.js +0 -0
- /package/dist/internal/{shared/contract/host-state.d.ts → host/shared/state.d.ts} +0 -0
- /package/dist/internal/{shared/contract → host/utils}/resolve-name-from-src.cjs +0 -0
- /package/dist/internal/{shared/contract → host/utils}/resolve-name-from-src.d.ts +0 -0
- /package/dist/internal/{shared/contract → host/utils}/resolve-name-from-src.js +0 -0
- /package/dist/internal/{next/remote/render-client.d.ts → remote/nextjs/app-client.d.ts} +0 -0
- /package/dist/internal/{shared/client → runtime/html}/apply-origin.cjs +0 -0
- /package/dist/internal/{shared/client → runtime/html}/apply-origin.js +0 -0
- /package/dist/internal/{shared/client → runtime/url}/protected-rc-fallback.d.ts +0 -0
- /package/dist/internal/{shared/utils → utils}/abort.cjs +0 -0
- /package/dist/internal/{shared/utils → utils}/abort.d.ts +0 -0
- /package/dist/internal/{shared/utils → utils}/abort.js +0 -0
- /package/dist/internal/{shared → utils}/error.d.ts +0 -0
- /package/dist/internal/{shared/utils.cjs → utils.cjs} +0 -0
- /package/dist/internal/{shared/utils.d.ts → utils.d.ts} +0 -0
- /package/dist/internal/{shared/utils.js → utils.js} +0 -0
- /package/dist/{shared/remote → remote/defaults}/app.d.ts +0 -0
- /package/dist/{shared/remote → remote/defaults}/pages.d.ts +0 -0
- /package/dist/{shared/remote → remote/defaults}/wrapper.d.ts +0 -0
- /package/dist/{html/remote.d.ts → remote/html.d.ts} +0 -0
|
@@ -1,14 +1,18 @@
|
|
|
1
1
|
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
2
|
+
import "remote-components/remote/defaults/wrapper";
|
|
2
3
|
import * as Form from "next/form";
|
|
3
4
|
import * as Image from "next/image";
|
|
4
5
|
import * as Link from "next/link";
|
|
5
6
|
import * as Router from "next/router";
|
|
6
7
|
import * as Script from "next/script";
|
|
7
8
|
import { useEffect } from "react";
|
|
8
|
-
import {
|
|
9
|
-
import {
|
|
10
|
-
import {
|
|
11
|
-
import {
|
|
9
|
+
import { ConsumeRemoteComponent as ConsumeRemoteComponentReact } from "remote-components/host/react";
|
|
10
|
+
import { imageImpl } from "#internal/host/nextjs/image-impl";
|
|
11
|
+
import { createNextImageSharedEntries } from "#internal/host/nextjs/image-shared";
|
|
12
|
+
import { fetchRemoteComponent } from "#internal/host/server/fetch-remote-component";
|
|
13
|
+
import { bindResolveClientUrl } from "#internal/runtime/url/default-resolve-client-url";
|
|
14
|
+
import { RemoteComponentsError } from "#internal/utils/error";
|
|
15
|
+
import { shared as _shared } from "#remote-components/host/defaults/pages";
|
|
12
16
|
const navigationImpl = {
|
|
13
17
|
useRouter: () => Router.useRouter(),
|
|
14
18
|
useSearchParams: () => {
|
|
@@ -20,24 +24,14 @@ const navigationImpl = {
|
|
|
20
24
|
}
|
|
21
25
|
};
|
|
22
26
|
const sharedCache = /* @__PURE__ */ new Map();
|
|
23
|
-
const shared = (bundle) => {
|
|
24
|
-
if (
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
const remoteLoader = ({ src, width, quality }) => {
|
|
28
|
-
const self2 = globalThis;
|
|
29
|
-
const { assetPrefix } = /^(?<assetPrefix>.*?)\/_next\//.exec(src)?.groups ?? {};
|
|
30
|
-
return `${self2.__remote_bundle_url__?.[bundle]?.origin ?? ""}${assetPrefix}/_next/image?url=${encodeURIComponent(src)}&w=${width}&q=${quality || 75}`;
|
|
31
|
-
};
|
|
32
|
-
const imageImpl = (ImageComponent) => {
|
|
33
|
-
function RemoteImage(props) {
|
|
34
|
-
return /* @__PURE__ */ jsx(ImageComponent, { loader: remoteLoader, ...props });
|
|
27
|
+
const shared = (bundle, resolveClientUrl) => {
|
|
28
|
+
if (!resolveClientUrl) {
|
|
29
|
+
if (sharedCache.has(bundle)) {
|
|
30
|
+
return sharedCache.get(bundle);
|
|
35
31
|
}
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
};
|
|
40
|
-
return {
|
|
32
|
+
}
|
|
33
|
+
const ImageComponent = Image.default.default ?? Image.default;
|
|
34
|
+
const result = {
|
|
41
35
|
// polyfill Next.js App Router client API (minimal)
|
|
42
36
|
// some API methods are not available when using a Next.js Pages Router application as host
|
|
43
37
|
"next/navigation": () => Promise.resolve(navigationImpl),
|
|
@@ -48,26 +42,18 @@ const shared = (bundle) => {
|
|
|
48
42
|
"next/form": () => Promise.resolve(Form.default),
|
|
49
43
|
"next/dist/client/script": () => Promise.resolve(Script.default),
|
|
50
44
|
"next/script": () => Promise.resolve(Script.default),
|
|
51
|
-
"next/dist/client/image-component": () => Promise.resolve({
|
|
52
|
-
// @ts-expect-error default.default
|
|
53
|
-
// eslint-disable-next-line
|
|
54
|
-
Image: imageImpl(Image.default.default ?? Image.default)
|
|
55
|
-
}),
|
|
56
|
-
"next/dist/api/image": () => Promise.resolve({
|
|
57
|
-
// @ts-expect-error default.default
|
|
58
|
-
// eslint-disable-next-line
|
|
59
|
-
default: imageImpl(Image.default.default ?? Image.default),
|
|
60
|
-
getImageProps: Image.getImageProps
|
|
61
|
-
}),
|
|
62
45
|
"next/router": () => Promise.resolve(Router),
|
|
63
46
|
..._shared,
|
|
64
|
-
//
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
imageImpl(Image.default.default ?? Image.default)
|
|
47
|
+
// Always override Next.js image modules to use the bundle URL rewriter.
|
|
48
|
+
...createNextImageSharedEntries(
|
|
49
|
+
() => imageImpl(ImageComponent, bundle, resolveClientUrl, true),
|
|
50
|
+
{ getImageProps: Image.getImageProps }
|
|
69
51
|
)
|
|
70
52
|
};
|
|
53
|
+
if (!resolveClientUrl) {
|
|
54
|
+
sharedCache.set(bundle, result);
|
|
55
|
+
}
|
|
56
|
+
return result;
|
|
71
57
|
};
|
|
72
58
|
const REMOTE_COMPONENT_STORE = Symbol("REMOTE_COMPONENT_STORE");
|
|
73
59
|
const REMOTE_COMPONENT_KEY = "__REMOTE_COMPONENT_KEY__";
|
|
@@ -90,20 +76,23 @@ function getComponent(key) {
|
|
|
90
76
|
self[REMOTE_COMPONENT_STORE]?.delete(key);
|
|
91
77
|
return component;
|
|
92
78
|
}
|
|
93
|
-
function
|
|
79
|
+
function ConsumeRemoteComponent(props) {
|
|
94
80
|
const remoteComponent = typeof document !== "undefined" ? null : (
|
|
95
81
|
// retrieve the HTML from the global store
|
|
96
82
|
getComponent(
|
|
97
83
|
props[REMOTE_COMPONENT_KEY] ?? "__vercel_remote_component"
|
|
98
84
|
)
|
|
99
85
|
);
|
|
86
|
+
const src = typeof props.src === "string" ? props.src : props.src.href;
|
|
87
|
+
const resolveClientUrl = props.resolveClientUrl ? bindResolveClientUrl(props.resolveClientUrl, src) : void 0;
|
|
88
|
+
const sharedResult = shared(props.bundle ?? "default", resolveClientUrl);
|
|
100
89
|
useEffect(() => {
|
|
101
90
|
const clientSelf = globalThis;
|
|
102
|
-
clientSelf.__remote_component_shared__ =
|
|
103
|
-
}, [
|
|
91
|
+
clientSelf.__remote_component_shared__ = sharedResult;
|
|
92
|
+
}, [sharedResult]);
|
|
104
93
|
if (!props[REMOTE_COMPONENT_KEY]) {
|
|
105
94
|
return /* @__PURE__ */ jsx(
|
|
106
|
-
|
|
95
|
+
ConsumeRemoteComponentReact,
|
|
107
96
|
{
|
|
108
97
|
isolate: props.isolate,
|
|
109
98
|
mode: props.mode,
|
|
@@ -116,14 +105,14 @@ function RemoteComponent(props) {
|
|
|
116
105
|
onResponse: props.onResponse,
|
|
117
106
|
resolveClientUrl: props.resolveClientUrl,
|
|
118
107
|
reset: props.reset,
|
|
119
|
-
shared:
|
|
108
|
+
shared: sharedResult,
|
|
120
109
|
src: props.src,
|
|
121
110
|
children: props.children
|
|
122
111
|
}
|
|
123
112
|
);
|
|
124
113
|
}
|
|
125
114
|
return /* @__PURE__ */ jsx(
|
|
126
|
-
|
|
115
|
+
ConsumeRemoteComponentReact,
|
|
127
116
|
{
|
|
128
117
|
isolate: props.isolate,
|
|
129
118
|
mode: props.mode,
|
|
@@ -136,16 +125,16 @@ function RemoteComponent(props) {
|
|
|
136
125
|
onResponse: props.onResponse,
|
|
137
126
|
resolveClientUrl: props.resolveClientUrl,
|
|
138
127
|
reset: props.reset,
|
|
139
|
-
shared:
|
|
128
|
+
shared: sharedResult,
|
|
140
129
|
src: props.src,
|
|
141
130
|
children: remoteComponent
|
|
142
131
|
}
|
|
143
132
|
);
|
|
144
133
|
}
|
|
145
|
-
async function
|
|
134
|
+
async function getConsumeRemoteComponentProps(src, options) {
|
|
146
135
|
if (typeof document !== "undefined") {
|
|
147
136
|
throw new RemoteComponentsError(
|
|
148
|
-
"`
|
|
137
|
+
"`getConsumeRemoteComponentProps()` can only be used on the server side."
|
|
149
138
|
);
|
|
150
139
|
}
|
|
151
140
|
const {
|
|
@@ -198,7 +187,7 @@ async function getRemoteComponentProps(src, options) {
|
|
|
198
187
|
};
|
|
199
188
|
}
|
|
200
189
|
export {
|
|
201
|
-
|
|
202
|
-
|
|
190
|
+
ConsumeRemoteComponent,
|
|
191
|
+
getConsumeRemoteComponentProps
|
|
203
192
|
};
|
|
204
|
-
//# sourceMappingURL=pages
|
|
193
|
+
//# sourceMappingURL=pages.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../src/host/nextjs/pages.tsx"],"sourcesContent":["import 'remote-components/remote/defaults/wrapper';\nimport * as Form from 'next/form';\nimport * as Image from 'next/image';\nimport * as Link from 'next/link';\nimport * as Router from 'next/router';\nimport * as Script from 'next/script';\nimport { useEffect } from 'react';\nimport { ConsumeRemoteComponent as ConsumeRemoteComponentReact } from 'remote-components/host/react';\nimport { imageImpl } from '#internal/host/nextjs/image-impl';\nimport { createNextImageSharedEntries } from '#internal/host/nextjs/image-shared';\nimport { fetchRemoteComponent } from '#internal/host/server/fetch-remote-component';\nimport type { ConsumeRemoteComponentConfig } from '#internal/host/shared/config';\nimport type {\n OnRequestHook,\n OnResponseHook,\n} from '#internal/host/shared/fetch-interceptors';\nimport { bindResolveClientUrl } from '#internal/runtime/url/default-resolve-client-url';\nimport type { InternalResolveClientUrl } from '#internal/runtime/url/resolve-client-url';\nimport { RemoteComponentsError } from '#internal/utils/error';\nimport { shared as _shared } from '#remote-components/host/defaults/pages';\n\nconst navigationImpl = {\n useRouter: () => Router.useRouter(),\n useSearchParams: () => {\n const router = Router.useRouter();\n return {\n get: (key: string) => router.query[key],\n has: (key: string) => key in router.query,\n };\n },\n};\n\nconst sharedCache = new Map<string, Record<string, () => Promise<unknown>>>();\nconst shared = (\n bundle: string,\n resolveClientUrl?: InternalResolveClientUrl,\n) => {\n // Skip cache when resolveClientUrl is provided — different resolver instances\n // must not share a cache entry, since imageImpl closes over the resolver.\n if (!resolveClientUrl) {\n if (sharedCache.has(bundle)) {\n return sharedCache.get(bundle);\n }\n }\n\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const ImageComponent: typeof Image.default =\n (Image.default as any).default ?? Image.default;\n const result = {\n // polyfill Next.js App Router client API (minimal)\n // some API methods are not available when using a Next.js Pages Router application as host\n 'next/navigation': () =>\n Promise.resolve(navigationImpl) as Promise<unknown>,\n 'next/dist/client/components/navigation': () =>\n Promise.resolve(navigationImpl) as Promise<unknown>,\n 'next/dist/client/app-dir/link': () =>\n Promise.resolve(Link.default) as Promise<unknown>,\n 'next/link': () => Promise.resolve(Link.default) as Promise<unknown>,\n 'next/dist/client/app-dir/form': () =>\n Promise.resolve(Form.default) as Promise<unknown>,\n 'next/form': () => Promise.resolve(Form.default) as Promise<unknown>,\n 'next/dist/client/script': () =>\n Promise.resolve(Script.default) as Promise<unknown>,\n 'next/script': () => Promise.resolve(Script.default) as Promise<unknown>,\n 'next/router': () => Promise.resolve(Router) as Promise<unknown>,\n ..._shared,\n // Always override Next.js image modules to use the bundle URL rewriter.\n ...createNextImageSharedEntries(\n () => imageImpl(ImageComponent, bundle, resolveClientUrl, true),\n { getImageProps: Image.getImageProps },\n ),\n };\n\n if (!resolveClientUrl) {\n sharedCache.set(bundle, result);\n }\n\n return result;\n};\n\n// internal symbols to access global store\nconst REMOTE_COMPONENT_STORE = Symbol('REMOTE_COMPONENT_STORE');\nconst REMOTE_COMPONENT_KEY = '__REMOTE_COMPONENT_KEY__';\n\n// temporary global store for remote component HTML\n// the store is used to save the HTML of remote components for SSR without sending the content to the client\nconst self = globalThis as typeof globalThis & {\n [REMOTE_COMPONENT_STORE]?: Map<string, React.ReactNode>;\n};\n\nfunction getKey({\n bundle,\n route,\n name,\n}: {\n bundle?: string;\n route?: string;\n name?: string;\n}): string {\n return `${bundle ?? '__next'}:${route ?? '/'}:${\n name ?? '__vercel_remote_component'\n }__${crypto.randomUUID()}`;\n}\n\nfunction setComponent(key: string, component: React.ReactNode): void {\n if (!self[REMOTE_COMPONENT_STORE]) {\n self[REMOTE_COMPONENT_STORE] = new Map();\n }\n self[REMOTE_COMPONENT_STORE].set(key, component);\n}\n\nfunction getComponent(key: string): React.ReactNode | undefined {\n const component = self[REMOTE_COMPONENT_STORE]?.get(key);\n // remove the component from the store after retrieving it to prevent memory leaks\n // storing the HTML in the global store is only needed for SSR and it's temporary only used for a single render\n self[REMOTE_COMPONENT_STORE]?.delete(key);\n return component;\n}\n\n/**\n * Props for the Next.js Pages Router remote component host.\n *\n * Extends {@link ConsumeRemoteComponentConfig} with Pages Router–specific `bundle` and\n * `route` props used for SSR hydration.\n */\nexport interface ConsumeRemoteComponentProps\n extends ConsumeRemoteComponentConfig {\n /** The source URL of the remote component. Required for server rendering. */\n src: string | URL;\n /** The Webpack bundle name for the remote component. */\n bundle?: string;\n /** The page route of the remote component. */\n route?: string;\n /** Loading fallback content displayed while the remote component is being fetched. */\n children?: React.ReactNode;\n [REMOTE_COMPONENT_KEY]?: string;\n}\n\n/**\n * This component handles the rendering of remote microfrontends.\n *\n * @param props - The properties for the remote component.\n * @returns A React component that renders the remote component.\n */\nexport function ConsumeRemoteComponent(props: ConsumeRemoteComponentProps) {\n const remoteComponent =\n typeof document !== 'undefined'\n ? null\n : // retrieve the HTML from the global store\n getComponent(\n props[REMOTE_COMPONENT_KEY] ?? '__vercel_remote_component',\n );\n\n const src =\n typeof props.src === 'string' ? props.src : (props.src as URL).href;\n const resolveClientUrl = props.resolveClientUrl\n ? bindResolveClientUrl(props.resolveClientUrl, src)\n : undefined;\n const sharedResult = shared(props.bundle ?? 'default', resolveClientUrl);\n\n useEffect(() => {\n const clientSelf = globalThis as typeof globalThis & {\n __remote_component_shared__?: Record<string, () => Promise<unknown>>;\n };\n // eslint-disable-next-line camelcase\n clientSelf.__remote_component_shared__ = sharedResult;\n }, [sharedResult]);\n\n if (!props[REMOTE_COMPONENT_KEY]) {\n return (\n <ConsumeRemoteComponentReact\n isolate={props.isolate}\n mode={props.mode}\n name={props.name}\n onBeforeLoad={props.onBeforeLoad}\n onChange={props.onChange}\n onError={props.onError}\n onLoad={props.onLoad}\n onRequest={props.onRequest}\n onResponse={props.onResponse}\n resolveClientUrl={props.resolveClientUrl}\n reset={props.reset}\n shared={sharedResult}\n src={props.src}\n >\n {props.children}\n </ConsumeRemoteComponentReact>\n );\n }\n\n return (\n <ConsumeRemoteComponentReact\n isolate={props.isolate}\n mode={props.mode}\n name={props.name}\n onBeforeLoad={props.onBeforeLoad}\n onChange={props.onChange}\n onError={props.onError}\n onLoad={props.onLoad}\n onRequest={props.onRequest}\n onResponse={props.onResponse}\n resolveClientUrl={props.resolveClientUrl}\n reset={props.reset}\n shared={sharedResult}\n src={props.src}\n >\n {remoteComponent}\n </ConsumeRemoteComponentReact>\n );\n}\n\n/**\n * Fetches the remote component properties from the server. You need to pass these properties to the `<ConsumeRemoteComponent>` component to render the fetched remote component.\n *\n * @param src - The source URL of the remote component. When using the Vercel Microfrontends solution, you can use relative paths, e.g. `/nextjs-app-remote/components/header`. Absolute URLs are also supported.\n * @param headers - The HTTP headers used for supporting the Vercel Microfrontends proxy.\n * @returns The properties of the remote component.\n *\n * @example\n *\n * ```tsx\n * import { getRemoteComponentProps } from 'remote-components/next/host/pages';\n * import type { GetServerSideProps } from 'next';\n *\n * export const getServerSideProps: GetServerSideProps<PageProps> = async function getServerSideProps({ req }) {\n * const myRemoteComponent = await getConsumeRemoteComponentProps(\n * '/nextjs-app-remote/components/header',\n * req.headers,\n * );\n * return {\n * props: {\n * remoteComponents: {\n * myRemoteComponent,\n * },\n * },\n * };\n * }\n * ```\n */\nexport async function getConsumeRemoteComponentProps(\n src: string,\n options?: {\n /**\n * Called when a fetch request is made to retrieve the remote component payload.\n * Can be used to intercept requests, modify headers, or provide a custom response.\n */\n onRequest?: OnRequestHook;\n /**\n * Called after a fetch completes to retrieve the remote component payload.\n * Can be used to inspect the response (e.g., check for redirects) or transform it.\n */\n onResponse?: OnResponseHook;\n /**\n * The name of the exposed remote component. Used to identify the remote component\n * when multiple remote components are exposed on a page.\n */\n name?: string;\n },\n): Promise<ConsumeRemoteComponentProps> {\n if (typeof document !== 'undefined') {\n throw new RemoteComponentsError(\n '`getConsumeRemoteComponentProps()` can only be used on the server side.',\n );\n }\n\n const {\n metadata: { bundle, route },\n name,\n links,\n component,\n nextData,\n remoteShared,\n } = await fetchRemoteComponent(src, {\n rsc: true,\n ...options,\n });\n\n const props: ConsumeRemoteComponentProps = {\n src,\n bundle,\n name,\n route,\n };\n\n const key = getKey(props);\n\n // do not render the HTML in development mode when remote is using Next.js Pages Router\n // this behavior is emulating the Next.js Pages Router FOUC as the styles are only applied on the client when running in development mode\n if (nextData?.buildId !== 'development') {\n // store the HTML in a global store\n setComponent(\n key,\n <>\n <script\n data-remote-components-shared=\"\"\n id={`${name}_shared`}\n type=\"application/json\"\n >\n {JSON.stringify(remoteShared)}\n </script>\n {links.map((link) => (\n <link\n key={`${link.as}_${link.href}`}\n {...link}\n precedence={undefined}\n />\n ))}\n {component}\n </>,\n );\n }\n\n return {\n ...props,\n // add remote component key to the props\n [REMOTE_COMPONENT_KEY]: key,\n };\n}\n"],"mappings":"AA0KM,SA0HA,UA1HA,KA0HA,YA1HA;AA1KN,OAAO;AACP,YAAY,UAAU;AACtB,YAAY,WAAW;AACvB,YAAY,UAAU;AACtB,YAAY,YAAY;AACxB,YAAY,YAAY;AACxB,SAAS,iBAAiB;AAC1B,SAAS,0BAA0B,mCAAmC;AACtE,SAAS,iBAAiB;AAC1B,SAAS,oCAAoC;AAC7C,SAAS,4BAA4B;AAMrC,SAAS,4BAA4B;AAErC,SAAS,6BAA6B;AACtC,SAAS,UAAU,eAAe;AAElC,MAAM,iBAAiB;AAAA,EACrB,WAAW,MAAM,OAAO,UAAU;AAAA,EAClC,iBAAiB,MAAM;AACrB,UAAM,SAAS,OAAO,UAAU;AAChC,WAAO;AAAA,MACL,KAAK,CAAC,QAAgB,OAAO,MAAM,GAAG;AAAA,MACtC,KAAK,CAAC,QAAgB,OAAO,OAAO;AAAA,IACtC;AAAA,EACF;AACF;AAEA,MAAM,cAAc,oBAAI,IAAoD;AAC5E,MAAM,SAAS,CACb,QACA,qBACG;AAGH,MAAI,CAAC,kBAAkB;AACrB,QAAI,YAAY,IAAI,MAAM,GAAG;AAC3B,aAAO,YAAY,IAAI,MAAM;AAAA,IAC/B;AAAA,EACF;AAGA,QAAM,iBACH,MAAM,QAAgB,WAAW,MAAM;AAC1C,QAAM,SAAS;AAAA;AAAA;AAAA,IAGb,mBAAmB,MACjB,QAAQ,QAAQ,cAAc;AAAA,IAChC,0CAA0C,MACxC,QAAQ,QAAQ,cAAc;AAAA,IAChC,iCAAiC,MAC/B,QAAQ,QAAQ,KAAK,OAAO;AAAA,IAC9B,aAAa,MAAM,QAAQ,QAAQ,KAAK,OAAO;AAAA,IAC/C,iCAAiC,MAC/B,QAAQ,QAAQ,KAAK,OAAO;AAAA,IAC9B,aAAa,MAAM,QAAQ,QAAQ,KAAK,OAAO;AAAA,IAC/C,2BAA2B,MACzB,QAAQ,QAAQ,OAAO,OAAO;AAAA,IAChC,eAAe,MAAM,QAAQ,QAAQ,OAAO,OAAO;AAAA,IACnD,eAAe,MAAM,QAAQ,QAAQ,MAAM;AAAA,IAC3C,GAAG;AAAA;AAAA,IAEH,GAAG;AAAA,MACD,MAAM,UAAU,gBAAgB,QAAQ,kBAAkB,IAAI;AAAA,MAC9D,EAAE,eAAe,MAAM,cAAc;AAAA,IACvC;AAAA,EACF;AAEA,MAAI,CAAC,kBAAkB;AACrB,gBAAY,IAAI,QAAQ,MAAM;AAAA,EAChC;AAEA,SAAO;AACT;AAGA,MAAM,yBAAyB,OAAO,wBAAwB;AAC9D,MAAM,uBAAuB;AAI7B,MAAM,OAAO;AAIb,SAAS,OAAO;AAAA,EACd;AAAA,EACA;AAAA,EACA;AACF,GAIW;AACT,SAAO,GAAG,UAAU,YAAY,SAAS,OACvC,QAAQ,gCACL,OAAO,WAAW;AACzB;AAEA,SAAS,aAAa,KAAa,WAAkC;AACnE,MAAI,CAAC,KAAK,sBAAsB,GAAG;AACjC,SAAK,sBAAsB,IAAI,oBAAI,IAAI;AAAA,EACzC;AACA,OAAK,sBAAsB,EAAE,IAAI,KAAK,SAAS;AACjD;AAEA,SAAS,aAAa,KAA0C;AAC9D,QAAM,YAAY,KAAK,sBAAsB,GAAG,IAAI,GAAG;AAGvD,OAAK,sBAAsB,GAAG,OAAO,GAAG;AACxC,SAAO;AACT;AA2BO,SAAS,uBAAuB,OAAoC;AACzE,QAAM,kBACJ,OAAO,aAAa,cAChB;AAAA;AAAA,IAEA;AAAA,MACE,MAAM,oBAAoB,KAAK;AAAA,IACjC;AAAA;AAEN,QAAM,MACJ,OAAO,MAAM,QAAQ,WAAW,MAAM,MAAO,MAAM,IAAY;AACjE,QAAM,mBAAmB,MAAM,mBAC3B,qBAAqB,MAAM,kBAAkB,GAAG,IAChD;AACJ,QAAM,eAAe,OAAO,MAAM,UAAU,WAAW,gBAAgB;AAEvE,YAAU,MAAM;AACd,UAAM,aAAa;AAInB,eAAW,8BAA8B;AAAA,EAC3C,GAAG,CAAC,YAAY,CAAC;AAEjB,MAAI,CAAC,MAAM,oBAAoB,GAAG;AAChC,WACE;AAAA,MAAC;AAAA;AAAA,QACC,SAAS,MAAM;AAAA,QACf,MAAM,MAAM;AAAA,QACZ,MAAM,MAAM;AAAA,QACZ,cAAc,MAAM;AAAA,QACpB,UAAU,MAAM;AAAA,QAChB,SAAS,MAAM;AAAA,QACf,QAAQ,MAAM;AAAA,QACd,WAAW,MAAM;AAAA,QACjB,YAAY,MAAM;AAAA,QAClB,kBAAkB,MAAM;AAAA,QACxB,OAAO,MAAM;AAAA,QACb,QAAQ;AAAA,QACR,KAAK,MAAM;AAAA,QAEV,gBAAM;AAAA;AAAA,IACT;AAAA,EAEJ;AAEA,SACE;AAAA,IAAC;AAAA;AAAA,MACC,SAAS,MAAM;AAAA,MACf,MAAM,MAAM;AAAA,MACZ,MAAM,MAAM;AAAA,MACZ,cAAc,MAAM;AAAA,MACpB,UAAU,MAAM;AAAA,MAChB,SAAS,MAAM;AAAA,MACf,QAAQ,MAAM;AAAA,MACd,WAAW,MAAM;AAAA,MACjB,YAAY,MAAM;AAAA,MAClB,kBAAkB,MAAM;AAAA,MACxB,OAAO,MAAM;AAAA,MACb,QAAQ;AAAA,MACR,KAAK,MAAM;AAAA,MAEV;AAAA;AAAA,EACH;AAEJ;AA8BA,eAAsB,+BACpB,KACA,SAiBsC;AACtC,MAAI,OAAO,aAAa,aAAa;AACnC,UAAM,IAAI;AAAA,MACR;AAAA,IACF;AAAA,EACF;AAEA,QAAM;AAAA,IACJ,UAAU,EAAE,QAAQ,MAAM;AAAA,IAC1B;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF,IAAI,MAAM,qBAAqB,KAAK;AAAA,IAClC,KAAK;AAAA,IACL,GAAG;AAAA,EACL,CAAC;AAED,QAAM,QAAqC;AAAA,IACzC;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AAEA,QAAM,MAAM,OAAO,KAAK;AAIxB,MAAI,UAAU,YAAY,eAAe;AAEvC;AAAA,MACE;AAAA,MACA,iCACE;AAAA;AAAA,UAAC;AAAA;AAAA,YACC,iCAA8B;AAAA,YAC9B,IAAI,GAAG;AAAA,YACP,MAAK;AAAA,YAEJ,eAAK,UAAU,YAAY;AAAA;AAAA,QAC9B;AAAA,QACC,MAAM,IAAI,CAAC,SACV;AAAA,UAAC;AAAA;AAAA,YAEE,GAAG;AAAA,YACJ,YAAY;AAAA;AAAA,UAFP,GAAG,KAAK,MAAM,KAAK;AAAA,QAG1B,CACD;AAAA,QACA;AAAA,SACH;AAAA,IACF;AAAA,EACF;AAEA,SAAO;AAAA,IACL,GAAG;AAAA;AAAA,IAEH,CAAC,oBAAoB,GAAG;AAAA,EAC1B;AACF;","names":[]}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
6
|
+
var __export = (target, all) => {
|
|
7
|
+
for (var name in all)
|
|
8
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
9
|
+
};
|
|
10
|
+
var __copyProps = (to, from, except, desc) => {
|
|
11
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
12
|
+
for (let key of __getOwnPropNames(from))
|
|
13
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
14
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
15
|
+
}
|
|
16
|
+
return to;
|
|
17
|
+
};
|
|
18
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
19
|
+
|
|
20
|
+
// src/host/proxy/client.ts
|
|
21
|
+
var client_exports = {};
|
|
22
|
+
__export(client_exports, {
|
|
23
|
+
routeThroughHostProxy: () => routeThroughHostProxy
|
|
24
|
+
});
|
|
25
|
+
module.exports = __toCommonJS(client_exports);
|
|
26
|
+
|
|
27
|
+
// src/utils/constants.ts
|
|
28
|
+
var RC_PROTECTED_REMOTE_FETCH_PATHNAME = "/rc-fetch-protected-remote";
|
|
29
|
+
|
|
30
|
+
// src/runtime/url/protected-rc-fallback.ts
|
|
31
|
+
function generateProtectedRcFallbackSrc(url) {
|
|
32
|
+
return `${RC_PROTECTED_REMOTE_FETCH_PATHNAME}?url=${encodeURIComponent(url)}`;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
// src/host/proxy/client.ts
|
|
36
|
+
var routeThroughHostProxy = (remoteSrc, url) => {
|
|
37
|
+
if (typeof location === "undefined") {
|
|
38
|
+
return void 0;
|
|
39
|
+
}
|
|
40
|
+
const remoteOrigin = new URL(remoteSrc, location.href).origin;
|
|
41
|
+
if (remoteOrigin === location.origin) {
|
|
42
|
+
return void 0;
|
|
43
|
+
}
|
|
44
|
+
try {
|
|
45
|
+
const parsed = new URL(url, location.href);
|
|
46
|
+
if (parsed.origin === remoteOrigin) {
|
|
47
|
+
return generateProtectedRcFallbackSrc(url);
|
|
48
|
+
}
|
|
49
|
+
} catch {
|
|
50
|
+
}
|
|
51
|
+
return void 0;
|
|
52
|
+
};
|
|
53
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
54
|
+
0 && (module.exports = {
|
|
55
|
+
routeThroughHostProxy
|
|
56
|
+
});
|
|
57
|
+
//# sourceMappingURL=client.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../src/host/proxy/client.ts","../../../src/utils/constants.ts","../../../src/runtime/url/protected-rc-fallback.ts"],"sourcesContent":["import { generateProtectedRcFallbackSrc } from '../../runtime/url/protected-rc-fallback';\n\n/**\n * Called before each asset fetch (scripts, styles, chunks, images) for a remote component.\n * Return a rewritten URL string to redirect the fetch, or undefined to use the original URL.\n *\n * @param remoteSrc - The `src` of the remote component\n * @param url - The asset URL about to be fetched\n */\nexport type ResolveClientUrl = (\n remoteSrc: string,\n url: string,\n) => string | undefined;\n\n/**\n * A `ResolveClientUrl` that routes cross-origin remote component asset requests\n * through the host's `/rc-fetch-protected-remote` endpoint. Same-origin URLs pass through unchanged.\n *\n * Use this on Vercel preview deployments where deployment protection would otherwise\n * block direct cross-origin fetches — routing through the host means requests carry\n * the host's auth cookies.\n *\n * Requires `withRemoteComponentsHostProxy` on the host side to handle the proxied requests.\n *\n * @example\n * ```tsx\n * import { routeThroughHostProxy } from 'remote-components/host/proxy/client';\n *\n * <ConsumeRemoteComponent\n * src=\"https://remote-app.com/components/header\"\n * resolveClientUrl={routeThroughHostProxy}\n * />\n * ```\n */\nexport const routeThroughHostProxy: ResolveClientUrl = (remoteSrc, url) => {\n if (typeof location === 'undefined') {\n return undefined;\n }\n const remoteOrigin = new URL(remoteSrc, location.href).origin;\n if (remoteOrigin === location.origin) {\n return undefined;\n }\n try {\n const parsed = new URL(url, location.href);\n if (parsed.origin === remoteOrigin) {\n return generateProtectedRcFallbackSrc(url);\n }\n } catch {\n // If URL parsing fails, return undefined to use the original\n }\n return undefined;\n};\n","export const RC_PROTECTED_REMOTE_FETCH_PATHNAME = '/rc-fetch-protected-remote';\n\nexport const MISSING_SHARED_MODULES_MESSAGE =\n 'Remote Components shared modules not found. Did you forget to wrap your config with `withRemoteComponentsConfig` on both host and remote?';\n\nexport const CORS_DOCS_URL =\n 'https://vercel.com/docs/remote-components/concepts/cors-external-urls#accessing-cross-site-protected-remote-components';\n","import { RC_PROTECTED_REMOTE_FETCH_PATHNAME } from '#internal/utils/constants';\n\n/**\n * Generates a fallback URL that proxies the request through the host's protected remote fetch endpoint\n */\nexport function generateProtectedRcFallbackSrc(url: string): string {\n return `${RC_PROTECTED_REMOTE_FETCH_PATHNAME}?url=${encodeURIComponent(url)}`;\n}\n\nexport function isProxiedUrl(url: string): boolean {\n try {\n return (\n new URL(url, location.href).pathname ===\n RC_PROTECTED_REMOTE_FETCH_PATHNAME\n );\n } catch {\n return false;\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACAO,IAAM,qCAAqC;;;ACK3C,SAAS,+BAA+B,KAAqB;AAClE,SAAO,GAAG,0CAA0C,mBAAmB,GAAG;AAC5E;;;AF2BO,IAAM,wBAA0C,CAAC,WAAW,QAAQ;AACzE,MAAI,OAAO,aAAa,aAAa;AACnC,WAAO;AAAA,EACT;AACA,QAAM,eAAe,IAAI,IAAI,WAAW,SAAS,IAAI,EAAE;AACvD,MAAI,iBAAiB,SAAS,QAAQ;AACpC,WAAO;AAAA,EACT;AACA,MAAI;AACF,UAAM,SAAS,IAAI,IAAI,KAAK,SAAS,IAAI;AACzC,QAAI,OAAO,WAAW,cAAc;AAClC,aAAO,+BAA+B,GAAG;AAAA,IAC3C;AAAA,EACF,QAAE;AAAA,EAEF;AACA,SAAO;AACT;","names":[]}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Called before each asset fetch (scripts, styles, chunks, images) for a remote component.
|
|
3
|
+
* Return a rewritten URL string to redirect the fetch, or undefined to use the original URL.
|
|
4
|
+
*
|
|
5
|
+
* @param remoteSrc - The `src` of the remote component
|
|
6
|
+
* @param url - The asset URL about to be fetched
|
|
7
|
+
*/
|
|
8
|
+
type ResolveClientUrl = (remoteSrc: string, url: string) => string | undefined;
|
|
9
|
+
/**
|
|
10
|
+
* A `ResolveClientUrl` that routes cross-origin remote component asset requests
|
|
11
|
+
* through the host's `/rc-fetch-protected-remote` endpoint. Same-origin URLs pass through unchanged.
|
|
12
|
+
*
|
|
13
|
+
* Use this on Vercel preview deployments where deployment protection would otherwise
|
|
14
|
+
* block direct cross-origin fetches — routing through the host means requests carry
|
|
15
|
+
* the host's auth cookies.
|
|
16
|
+
*
|
|
17
|
+
* Requires `withRemoteComponentsHostProxy` on the host side to handle the proxied requests.
|
|
18
|
+
*
|
|
19
|
+
* @example
|
|
20
|
+
* ```tsx
|
|
21
|
+
* import { routeThroughHostProxy } from 'remote-components/host/proxy/client';
|
|
22
|
+
*
|
|
23
|
+
* <ConsumeRemoteComponent
|
|
24
|
+
* src="https://remote-app.com/components/header"
|
|
25
|
+
* resolveClientUrl={routeThroughHostProxy}
|
|
26
|
+
* />
|
|
27
|
+
* ```
|
|
28
|
+
*/
|
|
29
|
+
declare const routeThroughHostProxy: ResolveClientUrl;
|
|
30
|
+
|
|
31
|
+
export { ResolveClientUrl, routeThroughHostProxy };
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
// src/utils/constants.ts
|
|
2
|
+
var RC_PROTECTED_REMOTE_FETCH_PATHNAME = "/rc-fetch-protected-remote";
|
|
3
|
+
|
|
4
|
+
// src/runtime/url/protected-rc-fallback.ts
|
|
5
|
+
function generateProtectedRcFallbackSrc(url) {
|
|
6
|
+
return `${RC_PROTECTED_REMOTE_FETCH_PATHNAME}?url=${encodeURIComponent(url)}`;
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
// src/host/proxy/client.ts
|
|
10
|
+
var routeThroughHostProxy = (remoteSrc, url) => {
|
|
11
|
+
if (typeof location === "undefined") {
|
|
12
|
+
return void 0;
|
|
13
|
+
}
|
|
14
|
+
const remoteOrigin = new URL(remoteSrc, location.href).origin;
|
|
15
|
+
if (remoteOrigin === location.origin) {
|
|
16
|
+
return void 0;
|
|
17
|
+
}
|
|
18
|
+
try {
|
|
19
|
+
const parsed = new URL(url, location.href);
|
|
20
|
+
if (parsed.origin === remoteOrigin) {
|
|
21
|
+
return generateProtectedRcFallbackSrc(url);
|
|
22
|
+
}
|
|
23
|
+
} catch {
|
|
24
|
+
}
|
|
25
|
+
return void 0;
|
|
26
|
+
};
|
|
27
|
+
export {
|
|
28
|
+
routeThroughHostProxy
|
|
29
|
+
};
|
|
30
|
+
//# sourceMappingURL=client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../src/utils/constants.ts","../../../src/runtime/url/protected-rc-fallback.ts","../../../src/host/proxy/client.ts"],"sourcesContent":["export const RC_PROTECTED_REMOTE_FETCH_PATHNAME = '/rc-fetch-protected-remote';\n\nexport const MISSING_SHARED_MODULES_MESSAGE =\n 'Remote Components shared modules not found. Did you forget to wrap your config with `withRemoteComponentsConfig` on both host and remote?';\n\nexport const CORS_DOCS_URL =\n 'https://vercel.com/docs/remote-components/concepts/cors-external-urls#accessing-cross-site-protected-remote-components';\n","import { RC_PROTECTED_REMOTE_FETCH_PATHNAME } from '#internal/utils/constants';\n\n/**\n * Generates a fallback URL that proxies the request through the host's protected remote fetch endpoint\n */\nexport function generateProtectedRcFallbackSrc(url: string): string {\n return `${RC_PROTECTED_REMOTE_FETCH_PATHNAME}?url=${encodeURIComponent(url)}`;\n}\n\nexport function isProxiedUrl(url: string): boolean {\n try {\n return (\n new URL(url, location.href).pathname ===\n RC_PROTECTED_REMOTE_FETCH_PATHNAME\n );\n } catch {\n return false;\n }\n}\n","import { generateProtectedRcFallbackSrc } from '../../runtime/url/protected-rc-fallback';\n\n/**\n * Called before each asset fetch (scripts, styles, chunks, images) for a remote component.\n * Return a rewritten URL string to redirect the fetch, or undefined to use the original URL.\n *\n * @param remoteSrc - The `src` of the remote component\n * @param url - The asset URL about to be fetched\n */\nexport type ResolveClientUrl = (\n remoteSrc: string,\n url: string,\n) => string | undefined;\n\n/**\n * A `ResolveClientUrl` that routes cross-origin remote component asset requests\n * through the host's `/rc-fetch-protected-remote` endpoint. Same-origin URLs pass through unchanged.\n *\n * Use this on Vercel preview deployments where deployment protection would otherwise\n * block direct cross-origin fetches — routing through the host means requests carry\n * the host's auth cookies.\n *\n * Requires `withRemoteComponentsHostProxy` on the host side to handle the proxied requests.\n *\n * @example\n * ```tsx\n * import { routeThroughHostProxy } from 'remote-components/host/proxy/client';\n *\n * <ConsumeRemoteComponent\n * src=\"https://remote-app.com/components/header\"\n * resolveClientUrl={routeThroughHostProxy}\n * />\n * ```\n */\nexport const routeThroughHostProxy: ResolveClientUrl = (remoteSrc, url) => {\n if (typeof location === 'undefined') {\n return undefined;\n }\n const remoteOrigin = new URL(remoteSrc, location.href).origin;\n if (remoteOrigin === location.origin) {\n return undefined;\n }\n try {\n const parsed = new URL(url, location.href);\n if (parsed.origin === remoteOrigin) {\n return generateProtectedRcFallbackSrc(url);\n }\n } catch {\n // If URL parsing fails, return undefined to use the original\n }\n return undefined;\n};\n"],"mappings":";AAAO,IAAM,qCAAqC;;;ACK3C,SAAS,+BAA+B,KAAqB;AAClE,SAAO,GAAG,0CAA0C,mBAAmB,GAAG;AAC5E;;;AC2BO,IAAM,wBAA0C,CAAC,WAAW,QAAQ;AACzE,MAAI,OAAO,aAAa,aAAa;AACnC,WAAO;AAAA,EACT;AACA,QAAM,eAAe,IAAI,IAAI,WAAW,SAAS,IAAI,EAAE;AACvD,MAAI,iBAAiB,SAAS,QAAQ;AACpC,WAAO;AAAA,EACT;AACA,MAAI;AACF,UAAM,SAAS,IAAI,IAAI,KAAK,SAAS,IAAI;AACzC,QAAI,OAAO,WAAW,cAAc;AAClC,aAAO,+BAA+B,GAAG;AAAA,IAC3C;AAAA,EACF,QAAE;AAAA,EAEF;AACA,SAAO;AACT;","names":[]}
|
|
@@ -16,13 +16,13 @@ var __copyProps = (to, from, except, desc) => {
|
|
|
16
16
|
return to;
|
|
17
17
|
};
|
|
18
18
|
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
19
|
-
var
|
|
20
|
-
__export(
|
|
19
|
+
var protected_fetch_exports = {};
|
|
20
|
+
__export(protected_fetch_exports, {
|
|
21
21
|
handleProtectedRemoteFetchRequest: () => handleProtectedRemoteFetchRequest
|
|
22
22
|
});
|
|
23
|
-
module.exports = __toCommonJS(
|
|
24
|
-
var
|
|
25
|
-
var
|
|
23
|
+
module.exports = __toCommonJS(protected_fetch_exports);
|
|
24
|
+
var import_fetch_headers = require("#internal/host/server/fetch-headers");
|
|
25
|
+
var import_constants = require("#internal/utils/constants");
|
|
26
26
|
async function handleProtectedRemoteFetchRequest(requestUrl, options) {
|
|
27
27
|
const url = new URL(requestUrl, "https://fallback.com");
|
|
28
28
|
if (url.pathname !== import_constants.RC_PROTECTED_REMOTE_FETCH_PATHNAME) {
|
|
@@ -105,4 +105,4 @@ async function handleProtectedRemoteFetchRequest(requestUrl, options) {
|
|
|
105
105
|
0 && (module.exports = {
|
|
106
106
|
handleProtectedRemoteFetchRequest
|
|
107
107
|
});
|
|
108
|
-
//# sourceMappingURL=
|
|
108
|
+
//# sourceMappingURL=protected-fetch.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../src/host/proxy/protected-fetch.ts"],"sourcesContent":["/**\n * Proxy utilities for host applications that consume remote components.\n *\n * Hosts do NOT handle CORS - that's the remote's responsibility.\n * Hosts only handle protected fetch proxying.\n */\n\nimport { remoteFetchHeaders } from '#internal/host/server/fetch-headers';\nimport {\n CORS_DOCS_URL,\n RC_PROTECTED_REMOTE_FETCH_PATHNAME,\n} from '#internal/utils/constants';\n\nexport interface HostProxyOptions {\n /**\n * List of allowed URL patterns (as regex strings) that can be proxied.\n * These patterns are combined with REMOTE_COMPONENTS_ALLOWED_PROXY_URLS env var if both are set.\n * If neither is set, all URLs are blocked.\n */\n allowedProxyUrls?: string[];\n}\n\n/**\n * Handles protected remote component fetch requests by proxying them with\n * authentication headers. This is needed for accessing Vercel-protected remote\n * component deployments from client-side code.\n *\n * @param requestUrl - The full request URL\n * @param options - Host proxy configuration options\n * @returns Response object if this is a protected fetch request, or null if not\n */\nexport async function handleProtectedRemoteFetchRequest(\n requestUrl: string,\n options?: HostProxyOptions,\n): Promise<Response | null> {\n const url = new URL(requestUrl, 'https://fallback.com');\n\n if (url.pathname !== RC_PROTECTED_REMOTE_FETCH_PATHNAME) {\n return null;\n }\n\n const targetUrl = url.searchParams.get('url');\n if (!targetUrl) {\n return new Response('Bad request, missing url query param', {\n status: 400,\n });\n }\n\n // Only allow http/https URLs to prevent SSRF via file://, data:, etc.\n let parsedTargetUrl: URL;\n try {\n parsedTargetUrl = new URL(targetUrl);\n } catch {\n return new Response('Bad request: invalid URL', { status: 400 });\n }\n\n if (\n parsedTargetUrl.protocol !== 'https:' &&\n parsedTargetUrl.protocol !== 'http:'\n ) {\n return new Response('Bad request: only http/https URLs are supported', {\n status: 400,\n });\n }\n\n const envPatterns = process.env.REMOTE_COMPONENTS_ALLOWED_PROXY_URLS?.split(\n ',',\n ).map((p) => p.trim());\n const optionPatterns = options?.allowedProxyUrls;\n\n // Combine both sources if both are specified\n const allowedPatterns = [...(optionPatterns || []), ...(envPatterns || [])];\n\n if (allowedPatterns.length === 0) {\n return new Response(\n `Forbidden: no allowedProxyUrls or REMOTE_COMPONENTS_ALLOWED_PROXY_URLS configured. ` +\n `See: ${CORS_DOCS_URL}`,\n {\n status: 403,\n },\n );\n }\n\n // Validate the target URL against allowed patterns to prevent SSRF.\n // matchTarget is origin + pathname (no query string or fragment).\n const matchTarget = parsedTargetUrl.origin + parsedTargetUrl.pathname;\n const isUrlAllowed = allowedPatterns.some((pattern) => {\n try {\n const anchored = pattern.startsWith('^') ? pattern : `^${pattern}`;\n const bounded = anchored.endsWith('$') ? anchored : `${anchored}(/|$)`;\n const regex = new RegExp(bounded);\n return regex.test(matchTarget);\n } catch (error) {\n console.error(\n `Invalid regex pattern in allowedProxyUrls: ${pattern}`,\n error,\n );\n return false;\n }\n });\n\n if (!isUrlAllowed) {\n return new Response(\n `Forbidden: origin \"${parsedTargetUrl.origin}\" does not match any allowedProxyUrls. ` +\n `Add a matching pattern to REMOTE_COMPONENTS_ALLOWED_PROXY_URLS or the allowedProxyUrls option. ` +\n `See: ${CORS_DOCS_URL}`,\n {\n status: 403,\n },\n );\n }\n\n // Fetch the remote resource\n const response = await fetch(targetUrl, { headers: remoteFetchHeaders() });\n\n // Only forward safe headers — no set-cookie, CORS, or encoding headers.\n // content-length is excluded because fetch() auto-decompresses the upstream\n // response, making the original content-length incorrect for the decoded body.\n const SAFE_HEADERS = [\n 'content-type',\n 'cache-control',\n 'etag',\n 'last-modified',\n ] as const;\n const headers = new Headers();\n for (const name of SAFE_HEADERS) {\n const value = response.headers.get(name);\n if (value) {\n headers.set(name, value);\n }\n }\n\n return new Response(response.body, {\n status: response.status,\n statusText: response.statusText,\n headers,\n });\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAOA,2BAAmC;AACnC,uBAGO;AAoBP,eAAsB,kCACpB,YACA,SAC0B;AAC1B,QAAM,MAAM,IAAI,IAAI,YAAY,sBAAsB;AAEtD,MAAI,IAAI,aAAa,qDAAoC;AACvD,WAAO;AAAA,EACT;AAEA,QAAM,YAAY,IAAI,aAAa,IAAI,KAAK;AAC5C,MAAI,CAAC,WAAW;AACd,WAAO,IAAI,SAAS,wCAAwC;AAAA,MAC1D,QAAQ;AAAA,IACV,CAAC;AAAA,EACH;AAGA,MAAI;AACJ,MAAI;AACF,sBAAkB,IAAI,IAAI,SAAS;AAAA,EACrC,QAAE;AACA,WAAO,IAAI,SAAS,4BAA4B,EAAE,QAAQ,IAAI,CAAC;AAAA,EACjE;AAEA,MACE,gBAAgB,aAAa,YAC7B,gBAAgB,aAAa,SAC7B;AACA,WAAO,IAAI,SAAS,mDAAmD;AAAA,MACrE,QAAQ;AAAA,IACV,CAAC;AAAA,EACH;AAEA,QAAM,cAAc,QAAQ,IAAI,sCAAsC;AAAA,IACpE;AAAA,EACF,EAAE,IAAI,CAAC,MAAM,EAAE,KAAK,CAAC;AACrB,QAAM,iBAAiB,SAAS;AAGhC,QAAM,kBAAkB,CAAC,GAAI,kBAAkB,CAAC,GAAI,GAAI,eAAe,CAAC,CAAE;AAE1E,MAAI,gBAAgB,WAAW,GAAG;AAChC,WAAO,IAAI;AAAA,MACT,2FACU;AAAA,MACV;AAAA,QACE,QAAQ;AAAA,MACV;AAAA,IACF;AAAA,EACF;AAIA,QAAM,cAAc,gBAAgB,SAAS,gBAAgB;AAC7D,QAAM,eAAe,gBAAgB,KAAK,CAAC,YAAY;AACrD,QAAI;AACF,YAAM,WAAW,QAAQ,WAAW,GAAG,IAAI,UAAU,IAAI;AACzD,YAAM,UAAU,SAAS,SAAS,GAAG,IAAI,WAAW,GAAG;AACvD,YAAM,QAAQ,IAAI,OAAO,OAAO;AAChC,aAAO,MAAM,KAAK,WAAW;AAAA,IAC/B,SAAS,OAAP;AACA,cAAQ;AAAA,QACN,8CAA8C;AAAA,QAC9C;AAAA,MACF;AACA,aAAO;AAAA,IACT;AAAA,EACF,CAAC;AAED,MAAI,CAAC,cAAc;AACjB,WAAO,IAAI;AAAA,MACT,sBAAsB,gBAAgB,oJAE5B;AAAA,MACV;AAAA,QACE,QAAQ;AAAA,MACV;AAAA,IACF;AAAA,EACF;AAGA,QAAM,WAAW,MAAM,MAAM,WAAW,EAAE,aAAS,yCAAmB,EAAE,CAAC;AAKzE,QAAM,eAAe;AAAA,IACnB;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACA,QAAM,UAAU,IAAI,QAAQ;AAC5B,aAAW,QAAQ,cAAc;AAC/B,UAAM,QAAQ,SAAS,QAAQ,IAAI,IAAI;AACvC,QAAI,OAAO;AACT,cAAQ,IAAI,MAAM,KAAK;AAAA,IACzB;AAAA,EACF;AAEA,SAAO,IAAI,SAAS,SAAS,MAAM;AAAA,IACjC,QAAQ,SAAS;AAAA,IACjB,YAAY,SAAS;AAAA,IACrB;AAAA,EACF,CAAC;AACH;","names":[]}
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
+
import { remoteFetchHeaders } from "#internal/host/server/fetch-headers";
|
|
1
2
|
import {
|
|
2
3
|
CORS_DOCS_URL,
|
|
3
4
|
RC_PROTECTED_REMOTE_FETCH_PATHNAME
|
|
4
|
-
} from "#internal/
|
|
5
|
-
import { remoteFetchHeaders } from "#internal/shared/ssr/fetch-headers";
|
|
5
|
+
} from "#internal/utils/constants";
|
|
6
6
|
async function handleProtectedRemoteFetchRequest(requestUrl, options) {
|
|
7
7
|
const url = new URL(requestUrl, "https://fallback.com");
|
|
8
8
|
if (url.pathname !== RC_PROTECTED_REMOTE_FETCH_PATHNAME) {
|
|
@@ -84,4 +84,4 @@ async function handleProtectedRemoteFetchRequest(requestUrl, options) {
|
|
|
84
84
|
export {
|
|
85
85
|
handleProtectedRemoteFetchRequest
|
|
86
86
|
};
|
|
87
|
-
//# sourceMappingURL=
|
|
87
|
+
//# sourceMappingURL=protected-fetch.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../../src/host/proxy/protected-fetch.ts"],"sourcesContent":["/**\n * Proxy utilities for host applications that consume remote components.\n *\n * Hosts do NOT handle CORS - that's the remote's responsibility.\n * Hosts only handle protected fetch proxying.\n */\n\nimport { remoteFetchHeaders } from '#internal/host/server/fetch-headers';\nimport {\n CORS_DOCS_URL,\n RC_PROTECTED_REMOTE_FETCH_PATHNAME,\n} from '#internal/utils/constants';\n\nexport interface HostProxyOptions {\n /**\n * List of allowed URL patterns (as regex strings) that can be proxied.\n * These patterns are combined with REMOTE_COMPONENTS_ALLOWED_PROXY_URLS env var if both are set.\n * If neither is set, all URLs are blocked.\n */\n allowedProxyUrls?: string[];\n}\n\n/**\n * Handles protected remote component fetch requests by proxying them with\n * authentication headers. This is needed for accessing Vercel-protected remote\n * component deployments from client-side code.\n *\n * @param requestUrl - The full request URL\n * @param options - Host proxy configuration options\n * @returns Response object if this is a protected fetch request, or null if not\n */\nexport async function handleProtectedRemoteFetchRequest(\n requestUrl: string,\n options?: HostProxyOptions,\n): Promise<Response | null> {\n const url = new URL(requestUrl, 'https://fallback.com');\n\n if (url.pathname !== RC_PROTECTED_REMOTE_FETCH_PATHNAME) {\n return null;\n }\n\n const targetUrl = url.searchParams.get('url');\n if (!targetUrl) {\n return new Response('Bad request, missing url query param', {\n status: 400,\n });\n }\n\n // Only allow http/https URLs to prevent SSRF via file://, data:, etc.\n let parsedTargetUrl: URL;\n try {\n parsedTargetUrl = new URL(targetUrl);\n } catch {\n return new Response('Bad request: invalid URL', { status: 400 });\n }\n\n if (\n parsedTargetUrl.protocol !== 'https:' &&\n parsedTargetUrl.protocol !== 'http:'\n ) {\n return new Response('Bad request: only http/https URLs are supported', {\n status: 400,\n });\n }\n\n const envPatterns = process.env.REMOTE_COMPONENTS_ALLOWED_PROXY_URLS?.split(\n ',',\n ).map((p) => p.trim());\n const optionPatterns = options?.allowedProxyUrls;\n\n // Combine both sources if both are specified\n const allowedPatterns = [...(optionPatterns || []), ...(envPatterns || [])];\n\n if (allowedPatterns.length === 0) {\n return new Response(\n `Forbidden: no allowedProxyUrls or REMOTE_COMPONENTS_ALLOWED_PROXY_URLS configured. ` +\n `See: ${CORS_DOCS_URL}`,\n {\n status: 403,\n },\n );\n }\n\n // Validate the target URL against allowed patterns to prevent SSRF.\n // matchTarget is origin + pathname (no query string or fragment).\n const matchTarget = parsedTargetUrl.origin + parsedTargetUrl.pathname;\n const isUrlAllowed = allowedPatterns.some((pattern) => {\n try {\n const anchored = pattern.startsWith('^') ? pattern : `^${pattern}`;\n const bounded = anchored.endsWith('$') ? anchored : `${anchored}(/|$)`;\n const regex = new RegExp(bounded);\n return regex.test(matchTarget);\n } catch (error) {\n console.error(\n `Invalid regex pattern in allowedProxyUrls: ${pattern}`,\n error,\n );\n return false;\n }\n });\n\n if (!isUrlAllowed) {\n return new Response(\n `Forbidden: origin \"${parsedTargetUrl.origin}\" does not match any allowedProxyUrls. ` +\n `Add a matching pattern to REMOTE_COMPONENTS_ALLOWED_PROXY_URLS or the allowedProxyUrls option. ` +\n `See: ${CORS_DOCS_URL}`,\n {\n status: 403,\n },\n );\n }\n\n // Fetch the remote resource\n const response = await fetch(targetUrl, { headers: remoteFetchHeaders() });\n\n // Only forward safe headers — no set-cookie, CORS, or encoding headers.\n // content-length is excluded because fetch() auto-decompresses the upstream\n // response, making the original content-length incorrect for the decoded body.\n const SAFE_HEADERS = [\n 'content-type',\n 'cache-control',\n 'etag',\n 'last-modified',\n ] as const;\n const headers = new Headers();\n for (const name of SAFE_HEADERS) {\n const value = response.headers.get(name);\n if (value) {\n headers.set(name, value);\n }\n }\n\n return new Response(response.body, {\n status: response.status,\n statusText: response.statusText,\n headers,\n });\n}\n"],"mappings":"AAOA,SAAS,0BAA0B;AACnC;AAAA,EACE;AAAA,EACA;AAAA,OACK;AAoBP,eAAsB,kCACpB,YACA,SAC0B;AAC1B,QAAM,MAAM,IAAI,IAAI,YAAY,sBAAsB;AAEtD,MAAI,IAAI,aAAa,oCAAoC;AACvD,WAAO;AAAA,EACT;AAEA,QAAM,YAAY,IAAI,aAAa,IAAI,KAAK;AAC5C,MAAI,CAAC,WAAW;AACd,WAAO,IAAI,SAAS,wCAAwC;AAAA,MAC1D,QAAQ;AAAA,IACV,CAAC;AAAA,EACH;AAGA,MAAI;AACJ,MAAI;AACF,sBAAkB,IAAI,IAAI,SAAS;AAAA,EACrC,QAAE;AACA,WAAO,IAAI,SAAS,4BAA4B,EAAE,QAAQ,IAAI,CAAC;AAAA,EACjE;AAEA,MACE,gBAAgB,aAAa,YAC7B,gBAAgB,aAAa,SAC7B;AACA,WAAO,IAAI,SAAS,mDAAmD;AAAA,MACrE,QAAQ;AAAA,IACV,CAAC;AAAA,EACH;AAEA,QAAM,cAAc,QAAQ,IAAI,sCAAsC;AAAA,IACpE;AAAA,EACF,EAAE,IAAI,CAAC,MAAM,EAAE,KAAK,CAAC;AACrB,QAAM,iBAAiB,SAAS;AAGhC,QAAM,kBAAkB,CAAC,GAAI,kBAAkB,CAAC,GAAI,GAAI,eAAe,CAAC,CAAE;AAE1E,MAAI,gBAAgB,WAAW,GAAG;AAChC,WAAO,IAAI;AAAA,MACT,2FACU;AAAA,MACV;AAAA,QACE,QAAQ;AAAA,MACV;AAAA,IACF;AAAA,EACF;AAIA,QAAM,cAAc,gBAAgB,SAAS,gBAAgB;AAC7D,QAAM,eAAe,gBAAgB,KAAK,CAAC,YAAY;AACrD,QAAI;AACF,YAAM,WAAW,QAAQ,WAAW,GAAG,IAAI,UAAU,IAAI;AACzD,YAAM,UAAU,SAAS,SAAS,GAAG,IAAI,WAAW,GAAG;AACvD,YAAM,QAAQ,IAAI,OAAO,OAAO;AAChC,aAAO,MAAM,KAAK,WAAW;AAAA,IAC/B,SAAS,OAAP;AACA,cAAQ;AAAA,QACN,8CAA8C;AAAA,QAC9C;AAAA,MACF;AACA,aAAO;AAAA,IACT;AAAA,EACF,CAAC;AAED,MAAI,CAAC,cAAc;AACjB,WAAO,IAAI;AAAA,MACT,sBAAsB,gBAAgB,oJAE5B;AAAA,MACV;AAAA,QACE,QAAQ;AAAA,MACV;AAAA,IACF;AAAA,EACF;AAGA,QAAM,WAAW,MAAM,MAAM,WAAW,EAAE,SAAS,mBAAmB,EAAE,CAAC;AAKzE,QAAM,eAAe;AAAA,IACnB;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACA,QAAM,UAAU,IAAI,QAAQ;AAC5B,aAAW,QAAQ,cAAc;AAC/B,UAAM,QAAQ,SAAS,QAAQ,IAAI,IAAI;AACvC,QAAI,OAAO;AACT,cAAQ,IAAI,MAAM,KAAK;AAAA,IACzB;AAAA,EACF;AAEA,SAAO,IAAI,SAAS,SAAS,MAAM;AAAA,IACjC,QAAQ,SAAS;AAAA,IACjB,YAAY,SAAS;AAAA,IACrB;AAAA,EACF,CAAC;AACH;","names":[]}
|
|
@@ -17,98 +17,15 @@ var __copyProps = (to, from, except, desc) => {
|
|
|
17
17
|
};
|
|
18
18
|
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
19
19
|
|
|
20
|
-
// src/
|
|
20
|
+
// src/host/proxy/index.ts
|
|
21
21
|
var proxy_exports = {};
|
|
22
22
|
__export(proxy_exports, {
|
|
23
|
-
|
|
24
|
-
withRemoteComponentsHost: () => withRemoteComponentsHost
|
|
23
|
+
withConsumeRemoteComponentsProxy: () => withConsumeRemoteComponentsProxy
|
|
25
24
|
});
|
|
26
25
|
module.exports = __toCommonJS(proxy_exports);
|
|
27
|
-
|
|
28
|
-
// src/next/proxy/withRemoteComponents.ts
|
|
29
26
|
var import_server = require("next/server");
|
|
30
27
|
|
|
31
|
-
// src/
|
|
32
|
-
function getHeader(headers, name) {
|
|
33
|
-
if (headers instanceof Headers) {
|
|
34
|
-
return headers.get(name) ?? void 0;
|
|
35
|
-
}
|
|
36
|
-
const value = headers[name];
|
|
37
|
-
return Array.isArray(value) ? value[0] : value;
|
|
38
|
-
}
|
|
39
|
-
function getCorsHeaders(options, requestHeaders) {
|
|
40
|
-
if (options === false) {
|
|
41
|
-
return {};
|
|
42
|
-
}
|
|
43
|
-
const originHeader = getHeader(requestHeaders, "origin");
|
|
44
|
-
const refererHeader = getHeader(requestHeaders, "referer");
|
|
45
|
-
const origin = originHeader ?? (refererHeader ? new URL(refererHeader).origin : "*");
|
|
46
|
-
const ALLOWED_ORIGINS = (process.env.REMOTE_COMPONENTS_ALLOWED_ORIGINS || (Array.isArray(options?.origin) ? options.origin.join(",") : options?.origin) || "*").split(",").map((allowedOrigin) => allowedOrigin.trim());
|
|
47
|
-
const isAllowed = ALLOWED_ORIGINS.includes("*") || ALLOWED_ORIGINS.includes(origin);
|
|
48
|
-
const allowedHeaders = process.env.REMOTE_COMPONENTS_ALLOW_HEADERS || (Array.isArray(options?.headers) ? options.headers.map((h) => h.trim()).join(",") : options?.headers) || getHeader(requestHeaders, "access-control-request-headers");
|
|
49
|
-
const CORS_HEADERS = isAllowed ? {
|
|
50
|
-
"Access-Control-Allow-Origin": origin,
|
|
51
|
-
"Access-Control-Allow-Methods": process.env.REMOTE_COMPONENTS_ALLOW_METHODS || (Array.isArray(options?.method) ? options.method.map((m) => m.trim()).join(",") : options?.method) || "GET,HEAD,POST,PUT,PATCH,DELETE,OPTIONS",
|
|
52
|
-
...allowedHeaders ? { "Access-Control-Allow-Headers": allowedHeaders } : {},
|
|
53
|
-
...process.env.REMOTE_COMPONENTS_ALLOW_CREDENTIALS || options?.credentials ? {
|
|
54
|
-
"Access-Control-Allow-Credentials": process.env.REMOTE_COMPONENTS_ALLOW_CREDENTIALS || "true"
|
|
55
|
-
} : {},
|
|
56
|
-
"Access-Control-Max-Age": options?.maxAge || "600",
|
|
57
|
-
Vary: "Origin"
|
|
58
|
-
} : {};
|
|
59
|
-
return CORS_HEADERS;
|
|
60
|
-
}
|
|
61
|
-
function getSecurityHeaders() {
|
|
62
|
-
return {
|
|
63
|
-
"Content-Security-Policy": "frame-ancestors 'none'",
|
|
64
|
-
"X-Frame-Options": "DENY"
|
|
65
|
-
};
|
|
66
|
-
}
|
|
67
|
-
function handleCorsPreflightRequest(method, headers, options) {
|
|
68
|
-
if (method !== "OPTIONS" || options === false) {
|
|
69
|
-
return null;
|
|
70
|
-
}
|
|
71
|
-
const corsHeaders = getCorsHeaders(options, headers);
|
|
72
|
-
return new Response(void 0, {
|
|
73
|
-
status: 200,
|
|
74
|
-
headers: { ...corsHeaders, ...getSecurityHeaders() }
|
|
75
|
-
});
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
// src/next/proxy/withRemoteComponents.ts
|
|
79
|
-
function withRemoteComponents(proxy, options) {
|
|
80
|
-
return async (request) => {
|
|
81
|
-
const preflightResponse = handleCorsPreflightRequest(
|
|
82
|
-
request.method,
|
|
83
|
-
request.headers,
|
|
84
|
-
options?.cors
|
|
85
|
-
);
|
|
86
|
-
if (preflightResponse) {
|
|
87
|
-
return preflightResponse;
|
|
88
|
-
}
|
|
89
|
-
const response = typeof proxy === "function" ? await proxy(request) : import_server.NextResponse.next();
|
|
90
|
-
if (options?.cors !== false) {
|
|
91
|
-
const corsHeaders = getCorsHeaders(options?.cors, request.headers);
|
|
92
|
-
Object.entries(corsHeaders).forEach(
|
|
93
|
-
([k, v]) => response.headers.set(k, v)
|
|
94
|
-
);
|
|
95
|
-
}
|
|
96
|
-
const securityHeaders = getSecurityHeaders();
|
|
97
|
-
Object.entries(securityHeaders).forEach(
|
|
98
|
-
([k, v]) => response.headers.set(k, v)
|
|
99
|
-
);
|
|
100
|
-
return response;
|
|
101
|
-
};
|
|
102
|
-
}
|
|
103
|
-
|
|
104
|
-
// src/next/proxy/withRemoteComponentsHost.ts
|
|
105
|
-
var import_server2 = require("next/server");
|
|
106
|
-
|
|
107
|
-
// src/shared/constants.ts
|
|
108
|
-
var RC_PROTECTED_REMOTE_FETCH_PATHNAME = "/rc-fetch-protected-remote";
|
|
109
|
-
var CORS_DOCS_URL = "https://vercel.com/docs/remote-components/concepts/cors-external-urls#accessing-cross-site-protected-remote-components";
|
|
110
|
-
|
|
111
|
-
// src/shared/ssr/fetch-headers.ts
|
|
28
|
+
// src/host/server/fetch-headers.ts
|
|
112
29
|
function remoteFetchHeaders() {
|
|
113
30
|
return {
|
|
114
31
|
/**
|
|
@@ -124,7 +41,11 @@ function remoteFetchHeaders() {
|
|
|
124
41
|
};
|
|
125
42
|
}
|
|
126
43
|
|
|
127
|
-
// src/
|
|
44
|
+
// src/utils/constants.ts
|
|
45
|
+
var RC_PROTECTED_REMOTE_FETCH_PATHNAME = "/rc-fetch-protected-remote";
|
|
46
|
+
var CORS_DOCS_URL = "https://vercel.com/docs/remote-components/concepts/cors-external-urls#accessing-cross-site-protected-remote-components";
|
|
47
|
+
|
|
48
|
+
// src/host/proxy/protected-fetch.ts
|
|
128
49
|
async function handleProtectedRemoteFetchRequest(requestUrl, options) {
|
|
129
50
|
const url = new URL(requestUrl, "https://fallback.com");
|
|
130
51
|
if (url.pathname !== RC_PROTECTED_REMOTE_FETCH_PATHNAME) {
|
|
@@ -204,8 +125,8 @@ async function handleProtectedRemoteFetchRequest(requestUrl, options) {
|
|
|
204
125
|
});
|
|
205
126
|
}
|
|
206
127
|
|
|
207
|
-
// src/
|
|
208
|
-
function
|
|
128
|
+
// src/host/proxy/index.ts
|
|
129
|
+
function withConsumeRemoteComponentsProxy(proxy, options) {
|
|
209
130
|
return async (request) => {
|
|
210
131
|
const protectedFetchResponse = await handleProtectedRemoteFetchRequest(
|
|
211
132
|
request.url,
|
|
@@ -214,12 +135,11 @@ function withRemoteComponentsHost(proxy, options) {
|
|
|
214
135
|
if (protectedFetchResponse) {
|
|
215
136
|
return protectedFetchResponse;
|
|
216
137
|
}
|
|
217
|
-
return typeof proxy === "function" ? await proxy(request) :
|
|
138
|
+
return typeof proxy === "function" ? await proxy(request) : import_server.NextResponse.next();
|
|
218
139
|
};
|
|
219
140
|
}
|
|
220
141
|
// Annotate the CommonJS export names for ESM import in node:
|
|
221
142
|
0 && (module.exports = {
|
|
222
|
-
|
|
223
|
-
withRemoteComponentsHost
|
|
143
|
+
withConsumeRemoteComponentsProxy
|
|
224
144
|
});
|
|
225
145
|
//# sourceMappingURL=proxy.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/host/proxy/index.ts","../../src/host/server/fetch-headers.ts","../../src/utils/constants.ts","../../src/host/proxy/protected-fetch.ts"],"sourcesContent":["import { type NextRequest, NextResponse } from 'next/server';\nimport {\n type HostProxyOptions,\n handleProtectedRemoteFetchRequest,\n} from './protected-fetch';\n\n/**\n * Wraps a Next.js proxy handler to add remote component support:\n * handles cross-origin asset fetches via the `/rc-fetch-protected-remote` endpoint,\n * then falls through to your proxy handler (or `NextResponse.next()`) for all other requests.\n *\n * Add `/rc-fetch-protected-remote` to your proxy/middleware matchers to activate it.\n *\n * @param proxy - Optional Next.js proxy handler to run for non-remote-component requests\n * @param options - Configuration options for SSRF protection\n */\nexport function withConsumeRemoteComponentsProxy(\n proxy?: (request: NextRequest) => NextResponse | Promise<NextResponse>,\n options?: HostProxyOptions,\n) {\n return async (request: NextRequest) => {\n // Check if this is a protected remote fetch request\n const protectedFetchResponse = await handleProtectedRemoteFetchRequest(\n request.url,\n options,\n );\n\n if (protectedFetchResponse) {\n return protectedFetchResponse;\n }\n\n return typeof proxy === 'function'\n ? await proxy(request)\n : NextResponse.next();\n };\n}\n\nexport type { HostProxyOptions } from './protected-fetch';\n","/**\n * The headers to use when fetching the remote component.\n */\nexport function remoteFetchHeaders() {\n return {\n /**\n * Authenticates deployment protection for the remote. Needed for SSR and SSG clients.\n * If the remote component uses vercel deployment protection, ensure the host and remote vercel\n * projects share a common automation bypass secret, and the shared secret is used as the\n * VERCEL_AUTOMATION_BYPASS_SECRET env var in the host project.\n */\n ...(typeof process === 'object' &&\n typeof process.env === 'object' &&\n typeof process.env.VERCEL_AUTOMATION_BYPASS_SECRET === 'string'\n ? {\n 'x-vercel-protection-bypass':\n process.env.VERCEL_AUTOMATION_BYPASS_SECRET,\n }\n : {}),\n Accept: 'text/html',\n };\n}\n","export const RC_PROTECTED_REMOTE_FETCH_PATHNAME = '/rc-fetch-protected-remote';\n\nexport const MISSING_SHARED_MODULES_MESSAGE =\n 'Remote Components shared modules not found. Did you forget to wrap your config with `withRemoteComponentsConfig` on both host and remote?';\n\nexport const CORS_DOCS_URL =\n 'https://vercel.com/docs/remote-components/concepts/cors-external-urls#accessing-cross-site-protected-remote-components';\n","/**\n * Proxy utilities for host applications that consume remote components.\n *\n * Hosts do NOT handle CORS - that's the remote's responsibility.\n * Hosts only handle protected fetch proxying.\n */\n\nimport { remoteFetchHeaders } from '#internal/host/server/fetch-headers';\nimport {\n CORS_DOCS_URL,\n RC_PROTECTED_REMOTE_FETCH_PATHNAME,\n} from '#internal/utils/constants';\n\nexport interface HostProxyOptions {\n /**\n * List of allowed URL patterns (as regex strings) that can be proxied.\n * These patterns are combined with REMOTE_COMPONENTS_ALLOWED_PROXY_URLS env var if both are set.\n * If neither is set, all URLs are blocked.\n */\n allowedProxyUrls?: string[];\n}\n\n/**\n * Handles protected remote component fetch requests by proxying them with\n * authentication headers. This is needed for accessing Vercel-protected remote\n * component deployments from client-side code.\n *\n * @param requestUrl - The full request URL\n * @param options - Host proxy configuration options\n * @returns Response object if this is a protected fetch request, or null if not\n */\nexport async function handleProtectedRemoteFetchRequest(\n requestUrl: string,\n options?: HostProxyOptions,\n): Promise<Response | null> {\n const url = new URL(requestUrl, 'https://fallback.com');\n\n if (url.pathname !== RC_PROTECTED_REMOTE_FETCH_PATHNAME) {\n return null;\n }\n\n const targetUrl = url.searchParams.get('url');\n if (!targetUrl) {\n return new Response('Bad request, missing url query param', {\n status: 400,\n });\n }\n\n // Only allow http/https URLs to prevent SSRF via file://, data:, etc.\n let parsedTargetUrl: URL;\n try {\n parsedTargetUrl = new URL(targetUrl);\n } catch {\n return new Response('Bad request: invalid URL', { status: 400 });\n }\n\n if (\n parsedTargetUrl.protocol !== 'https:' &&\n parsedTargetUrl.protocol !== 'http:'\n ) {\n return new Response('Bad request: only http/https URLs are supported', {\n status: 400,\n });\n }\n\n const envPatterns = process.env.REMOTE_COMPONENTS_ALLOWED_PROXY_URLS?.split(\n ',',\n ).map((p) => p.trim());\n const optionPatterns = options?.allowedProxyUrls;\n\n // Combine both sources if both are specified\n const allowedPatterns = [...(optionPatterns || []), ...(envPatterns || [])];\n\n if (allowedPatterns.length === 0) {\n return new Response(\n `Forbidden: no allowedProxyUrls or REMOTE_COMPONENTS_ALLOWED_PROXY_URLS configured. ` +\n `See: ${CORS_DOCS_URL}`,\n {\n status: 403,\n },\n );\n }\n\n // Validate the target URL against allowed patterns to prevent SSRF.\n // matchTarget is origin + pathname (no query string or fragment).\n const matchTarget = parsedTargetUrl.origin + parsedTargetUrl.pathname;\n const isUrlAllowed = allowedPatterns.some((pattern) => {\n try {\n const anchored = pattern.startsWith('^') ? pattern : `^${pattern}`;\n const bounded = anchored.endsWith('$') ? anchored : `${anchored}(/|$)`;\n const regex = new RegExp(bounded);\n return regex.test(matchTarget);\n } catch (error) {\n console.error(\n `Invalid regex pattern in allowedProxyUrls: ${pattern}`,\n error,\n );\n return false;\n }\n });\n\n if (!isUrlAllowed) {\n return new Response(\n `Forbidden: origin \"${parsedTargetUrl.origin}\" does not match any allowedProxyUrls. ` +\n `Add a matching pattern to REMOTE_COMPONENTS_ALLOWED_PROXY_URLS or the allowedProxyUrls option. ` +\n `See: ${CORS_DOCS_URL}`,\n {\n status: 403,\n },\n );\n }\n\n // Fetch the remote resource\n const response = await fetch(targetUrl, { headers: remoteFetchHeaders() });\n\n // Only forward safe headers — no set-cookie, CORS, or encoding headers.\n // content-length is excluded because fetch() auto-decompresses the upstream\n // response, making the original content-length incorrect for the decoded body.\n const SAFE_HEADERS = [\n 'content-type',\n 'cache-control',\n 'etag',\n 'last-modified',\n ] as const;\n const headers = new Headers();\n for (const name of SAFE_HEADERS) {\n const value = response.headers.get(name);\n if (value) {\n headers.set(name, value);\n }\n }\n\n return new Response(response.body, {\n status: response.status,\n statusText: response.statusText,\n headers,\n });\n}\n"],"mappings":"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","names":[]}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { NextRequest, NextResponse } from 'next/server';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Proxy utilities for host applications that consume remote components.
|
|
5
|
+
*
|
|
6
|
+
* Hosts do NOT handle CORS - that's the remote's responsibility.
|
|
7
|
+
* Hosts only handle protected fetch proxying.
|
|
8
|
+
*/
|
|
9
|
+
interface HostProxyOptions {
|
|
10
|
+
/**
|
|
11
|
+
* List of allowed URL patterns (as regex strings) that can be proxied.
|
|
12
|
+
* These patterns are combined with REMOTE_COMPONENTS_ALLOWED_PROXY_URLS env var if both are set.
|
|
13
|
+
* If neither is set, all URLs are blocked.
|
|
14
|
+
*/
|
|
15
|
+
allowedProxyUrls?: string[];
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* Wraps a Next.js proxy handler to add remote component support:
|
|
20
|
+
* handles cross-origin asset fetches via the `/rc-fetch-protected-remote` endpoint,
|
|
21
|
+
* then falls through to your proxy handler (or `NextResponse.next()`) for all other requests.
|
|
22
|
+
*
|
|
23
|
+
* Add `/rc-fetch-protected-remote` to your proxy/middleware matchers to activate it.
|
|
24
|
+
*
|
|
25
|
+
* @param proxy - Optional Next.js proxy handler to run for non-remote-component requests
|
|
26
|
+
* @param options - Configuration options for SSRF protection
|
|
27
|
+
*/
|
|
28
|
+
declare function withConsumeRemoteComponentsProxy(proxy?: (request: NextRequest) => NextResponse | Promise<NextResponse>, options?: HostProxyOptions): (request: NextRequest) => Promise<Response>;
|
|
29
|
+
|
|
30
|
+
export { HostProxyOptions, withConsumeRemoteComponentsProxy };
|