使用 Vue Web 组件访问 Webpack 外部库

Posted

技术标签:

【中文标题】使用 Vue Web 组件访问 Webpack 外部库【英文标题】:Webpack external library access with Vue web components 【发布时间】:2019-05-08 21:40:39 【问题描述】:

我使用 vue-cli.3 创建了一个 Web 组件,以便通过以下命令在其他项目中使用它:

vue-cli-service build --target lib --name helloworld ./src/components/HelloWorld.vue

该组件依赖于 lodash。我不想将 lodash 与组件捆绑在一起,因为 lodash 将由宿主应用程序提供,所以我在 vue.config.js 中配置 webpack,如下所示:

module.exports = 
    configureWebpack: 
        externals: 
            lodash: 'lodash',
            root: '_'
        
    

这样,我成功编译了没有lodash的组件。

在宿主应用程序(将使用该组件的应用程序)中,我将新创建和编译的组件的源路径添加到 index.html 中:

<script src="http://localhost:8080/helloworld.umd.js"></script>

在 App.vue 中注册组件:

<template>
    <div id="app">
        <demo msg="hello from my component"></demo>
    </div>
</template>

<script>
export default 
    name: "app",
    components: 
        demo: helloworld
    
;
</script>

helloworld 组件可以毫无问题地呈现。该组件的每个功能都可以正常工作,但只要我调用 lodash 的方法,我就会得到;

Uncaught TypeError: Cannot read property 'camelCase' of undefined

这意味着组件无法访问宿主应用程序使用的 lodash 库。

我需要找到一种方法来从组件中使用主机应用程序中已经捆绑的库。

有办法吗?

【问题讨论】:

查看 webpack 文档,您的 externals 设置似乎不正确。您需要像这样设置您的外部对象:externals: lodash: root: '_' 。我不认为您真的有一个名为 root 的依赖项,您希望将其公开为 _ :p 另一个提示,如果您要构建的库将安装在包含lodash 的另一个环境中,请确保lodashpackage.json 中的peerDependencies 下列出。 @chipit24 你是说环境的package.json?因为我不打包组件,所以它只是一个简单的脚本文件,我将其包含在一个 html 文件中,该文件将自身注册为 Vue 组件。 不,我的意思是你图书馆的package.json:docs.npmjs.com/files/package.json.html#peerdependencies,yarnpkg.com/lang/en/docs/dependency-types/#toc-peerdependencies。由于您不是通过 npm、yarn 等安装软件包。那么它在技术上不会有所作为。 我不发布包。正如我所解释的,这只是一个简单的 javascript 源代码。 【参考方案1】:

您使用的 Vue 配置应该可以工作(请参阅 GitHub demo),因此您的设置中可能缺少某些内容。我已经列出了到达演示的相关步骤:

    在 VueCLI 生成的项目的 public/index.html 中,从 CDN 导入 Lodash:

    <script src="https://cdn.jsdelivr.net/npm/lodash@4.17.11/lodash.min.js"></script>
    

    在库组件(src/components/HelloWorld.vue)中,可以使用_全局无需导入lodash。例如,显示一个计算属性,该属性将msg 属性格式化为_.camelCase

    为避免 lint 错误,请将 _ 指定为 ESLint global (/* global _ */)。

    vue.config.js中,配置Webpack将lodash外化:

    module.exports = 
      configureWebpack: 
        externals: 
          lodash: 
            commonjs: 'lodash',
            amd: 'lodash',
            root: '_' // indicates global variable
          
        
      
    
    

    package.json 中,将build 脚本编辑为:

    "build": "vue-cli-service build --target lib --name helloworld ./src/components/HelloWorld.vue",
    

    运行npm run build,然后编辑dist/demo.html,使其也包含上面的&lt;script&gt;标签。

    dist(例如python -m SimpleHTTPServer)中启动一个HTTP服务器,并打开dist/demo.html。观察_.camelCase(从第2步开始)的效果,没有控制台错误。

GitHub demo

【讨论】:

感谢@tony19 的回答。这是我尝试过的方法之一,它有效,但是有些库不会像 lodash 那样将自己注册到窗口中。因此,在主机应用程序中,我将所有这些手动注册到窗口中,并且它以这种方式工作。 好的。没有附加到window 的库的示例是什么?该库可能需要不同的配置。 我们自己的库来自我们自己的 npm 包:-)

以上是关于使用 Vue Web 组件访问 Webpack 外部库的主要内容,如果未能解决你的问题,请参考以下文章

运行时导入 Vue 组件的 webpack 块时如何添加授权标头

vue-router和webpack懒加载,页面性能优化篇

Vue.js中用webpack合并打包多个组件并实现按需加载

减少打包组件vue.config.js——Webpack的externals的使用

Web前端-Vue.js必备框架

vue+webpack2实现路由的懒加载