从URL动态加载React组件库?

发布于 2025-01-18 22:54:23 字数 1179 浏览 5 评论 0 原文

我正在为打字稿库的文档工具。这个想法是利用包裹的手表模式连续构建库,并在预先构建的文档应用程序中使用相同的图书馆。

对于同样,我需要通过URL动态加载模块库(内置另一个项目)。

<script type="module">
    const libraryModule = "http://localhost:8080/lib.module.js";
    const promise = import(libraryModule);

    promise.then(library => {
        // do something with library
        window.ComponentLibrary = library;
    });
</script>

但是,包裹将上述 import require 替换,并且负载失败。使用 System.Import thrws 系统未定义错误

我尝试使用 dynamic-import-polyfill ,然后以下文和下文的使用初始化它:

dynamicImportPolyfill.initialize({
    modulePath: 'http://localhost:13090', // Defaults to '.'
    importFunctionName: '$$import' // Defaults to '__import__'

    const promise = $$import(libPath);
});

这引发了以下错误:

TypeError: Failed to resolve module specifier "react/jsx-dev-runtime". Relative references must start with either "/", "./", or "../"

我还尝试使用 script> script 代码>文本/JavaScript ,但也不起作用。

在这里寻找有关加载组件库的最佳方式的指导?

I am working on documentation tool for Typescript library. The idea is to leverage parcel's watch mode to continuously build the library, and use the same in a pre-built documentation app.

For the same I need to load a module library (built in another project) dynamically via URL.

<script type="module">
    const libraryModule = "http://localhost:8080/lib.module.js";
    const promise = import(libraryModule);

    promise.then(library => {
        // do something with library
        window.ComponentLibrary = library;
    });
</script>

However, parcel replaces the above import with require and the load fails. Using System.import throws System is not defined error.

I tried to use dynamic-import-polyfill and then initialize it as under and the use as below:

dynamicImportPolyfill.initialize({
    modulePath: 'http://localhost:13090', // Defaults to '.'
    importFunctionName: '$import' // Defaults to '__import__'

    const promise = $import(libPath);
});

This throws the following error:

TypeError: Failed to resolve module specifier "react/jsx-dev-runtime". Relative references must start with either "/", "./", or "../"

I have also tried using script type as text/javascript but doesn't work either.

Looking for guidance on the best way here to get the component library loaded?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

空‖城人不在 2025-01-25 22:54:23

弄清楚了:是的,我们可以动态地加载组件库作为模块。

问题是React UMD模块不是纯ES/JavaScript模块。另外,使用React 17,JSX组件是从 React/JSX-Runtime 中选择的。因此,首先,我必须将React UMD模块转换为ES模块 - 它只是一个薄包装器。同样,添加了 jsx-runtime 的包装器。要使事情工作必须使用 importMaps ,这些当前在所有浏览器中不支持 - 请参见检查最新支持。

这完成了您的设置,现在您的库编译为ES模块可以正常工作。以下是我用来工作的方法:

<script type="importmap">
        {
            "imports": {
                "react/jsx-runtime": "/react-jsx-runtime.js",
                "react": "/react-as-es-module.js"
            }
        }
    </script>
    <script type="module" src="/component-library.js"></script>
    <script type="module">
        import * as MyComponentLib from "/component-library.js";
        window.ComponentLibrary = { ...MyComponentLib };
    </script>

react-jsx-runtime.js 的代码如下:

import * as React from 'react';

export const jsx = React.createElement;
export const jsxs = React.createElement;

react-as-as-es-module.js 的代码为:

import 'https://unpkg.com/[email protected]/umd/react.production.min.js';

const {
    Children,
    Component,
    Fragment,
    // and all other exports
} = React || {};

export {
    Children,
    Component,
    Fragment,
    // and all other exports
}

export default React;

我编译了 component-library.js 使用 parceljs 使用类型:”模块“ package.json 文件中。我会在博客文章和Demo Github回购中详细介绍。

希望这会有所帮助。

Figured it out: yes, we can load a component library as a module dynamically.

The issue was that React UMD module is not a pure ES/Javascript module. Also, with React 17, JSX components are picked from react/jsx-runtime. So, first I had to convert the React UMD module into an ES module - it's just a thin wrapper. Similarly, added a wrapper for jsx-runtime. To make things work had to use importmaps which are currently not supported in all browsers - see caniuse.com to check latest support.

This completes your setup and now your library compiled as ES module will work just fine. Below is what I used to get working:

<script type="importmap">
        {
            "imports": {
                "react/jsx-runtime": "/react-jsx-runtime.js",
                "react": "/react-as-es-module.js"
            }
        }
    </script>
    <script type="module" src="/component-library.js"></script>
    <script type="module">
        import * as MyComponentLib from "/component-library.js";
        window.ComponentLibrary = { ...MyComponentLib };
    </script>

Code for react-jsx-runtime.js looks as under:

import * as React from 'react';

export const jsx = React.createElement;
export const jsxs = React.createElement;

Code for react-as-es-module.js goes as:

import 'https://unpkg.com/[email protected]/umd/react.production.min.js';

const {
    Children,
    Component,
    Fragment,
    // and all other exports
} = React || {};

export {
    Children,
    Component,
    Fragment,
    // and all other exports
}

export default React;

I compiled component-library.js using ParcelJS using the type: "module" in package.json file. I would detail this in blog post and demo Github repo soon.

Hope this helps.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文