将CDN组件与CLI Build一起使用?

时间:2018-05-14 18:16:54

标签: javascript webpack vue.js vuejs2

所以,到目前为止,我们一直在构建我们的Vue应用程序,利用Vue的标准脚本标签(主要是因为我们可以慢慢从jQuery / Knockout重型应用程序转换),但是当我们开始转换我们更复杂的应用程序,如果我们不早点切换到CLI构建,我已经可以看到我们将继续推进的维护问题。

现在,对于我们的许多应用程序而言,这不是问题,但由于我们在Vue应用程序的早期采用了“内部CDN”方法,因此在Webpack中捆绑所有内容似乎在多功能性方面有点退步。现在我们提供4个文件,然后我们的MVC应用程序中的每个路由都有自己的关联Vue实例(即:about.js),它控制整个UI及其逻辑。我们的CDN服务:1。polyfills.js(用于浏览器兼容性),2。vendor.js(axios,moment.js和其他一些),3。vue.js(vue + vee-validate)和4. components.js (我们自己的自定义UI组件库)。

一般来说,我不关心1-3。这些都可以捆绑在webpack CLI构建中。我已经挂了4号,因为CDN上的服务让我们可以即时推送所有应用程序的更新,而无需运行新版本。目前,我们只有7个应用程序运行完整的Vue构建,但我们的目的是最终将所有80多个内部应用程序,以及几个现有和新的外部应用程序转换为Vue。如果我们的30个应用程序正在使用我们的共享组件之一,并且需要更新以解决任何功能,可访问性等问题,那意味着我们必须重建所有30个应用程序并推送它们,这根本不理想。

有没有办法继续为我们的组件使用CDN构建,并将其余部分捆绑为带Webpack的SPA?

请注意:这与引用外部JS库(如jQuery)不同。我正在尝试添加 Vue组件。如果从外部加载这样的库,然后尝试通过以下方式导入组件:

<ComponentName/>

Vue会给你一个控制台错误说:

[Vue warn]: Unknown custom element: <ComponentName> - did you register the component correctly? For recursive components, make sure to provide the "name" option.

found in

    ---> <App> at src\App.vue
           <Root>

只需添加如下:

export default {
    name: 'app',
    components: {
       ComponentName
    }
}

将返回:

Uncaught ReferenceError: ComponentName is not defined

因为没有导入。但是尝试导入它也行不通,因为它在应用程序中不存在,它是外部的。

3 个答案:

答案 0 :(得分:2)

嗯,从技术上讲,您可以使用http-vue-loader,它将通过HTTP加载.vue个组件。但是有一些限制,不建议用于生产。

答案 1 :(得分:1)

您希望使用Vue webpack CLI构建管理您的应用程序,但保持独立 Vue组件的灵活性,即作为多个应用程序/项目通用的单独文件。这是一个用&#34; 内部CDN &#34;描述的架构。

@RandyCasburn的pointed out,您可以通过简单地全局展示Vue(通常从CDN加载<script>)然后加载您的独立文件来实现上述目标使用Vue.component全局注册您的组件。

参考:How to 'import' Vuejs component into index.html?

但是,您希望能够将这些独立的Vue组件开发为单个文件组件(SFC)。

我基本上看到了两个有趣的解决方案,用于您描述的用法:

  1. 填补创建小型构建步骤工具的空白,将SFC转换为普通JS文件,可以通过<script>标记加载,并使用Vue.component全局注册组件。
  2. 不是构建通过Vue.component注册的JS文件,而是让它公开Vue组件配置/ options object,以便它可以是locally registeredloaded asynchronously。这需要更多的工作,因为您需要设置每个消费者应用程序webpack配置以异步加载非捆绑的块。
  3. 选项1:使用Vue.component

    将Vue SFC转换为单个JS文件

    实际上有一个最近提供此功能的模板项目:

    https://github.com/RonnieSan/vue-browser-sfc

      

    用于将单个文件组件(.vue)编译为独立JS文件以在浏览器中使用的构建设置模板

    另见Compile a ".vue" component in browser, with JS only?

    它使用webpack将您的.vue文件转换为已编译的JS文件,该文件使用Vue.component全局注册该组件。

    如果您感兴趣的是更精简的代码,您也可以使用Rollup而不是webpack执行非常类似的过程。使用rollup-plugin-vue

    这种方法的优点是它易于理解,您只需要重构HTML以加载Vue,然后是所有常见组件的JS文件。即使在开发过程中,这些组件也应该是全局可用的,因此Vue运行时不应该抱怨&#34; 未知的自定义元素&#34;,并且在您的消费者应用程序中,只是不要{{1} / /声明它们。

    缺点是您必须事先加载所有这些组件,无论您是否使用它们。

    选项2:将Vue SFC转换为单个JS文件为&#34; async&#34;选项对象

    这个更有趣,但设置得更复杂。

    与前面的解决方案一样,在组件方面,您使用构建步骤来转换SFC import文件,但您不需要额外的包含.vue声明的包装器。只需让webpack或Rollup将组件选项对象包装在IIFE或UMD中,即在全局上下文中注册对象。

    例如,您的Vue.component文件如下所示:

    rollup.config.js

    然后在您的消费者应用程序上,您仍然import VuePlugin from 'rollup-plugin-vue' export default { input: 'components/my-component.vue', output: { file: 'dist/my-component.js', name: 'MyComponent', // <= store the component on `window.MyComponent` format: 'umd', }, plugins: [VuePlugin()] } 并声明您的组件,但您需要设置webpack配置,以便它不会将文件捆绑在应用程序中,而是从网络异步加载它们。例如:

    import()

    为此,您可以使用dynamic-cdn-webpack-plugin,但是您必须提供自己的resolver功能,因为默认module-to-cdn使用不可配置的modules list。< / p>

    您在dynamic-cdn-webpack-plugin的only数组选项中列出您的组件,提供components: { 'my-component': () => import('my-component'), }, mimics resolver但使用您自己的列表。例如:

    module-to-cdn

    要使此方案有效,您还必须将组件列为const modules = { 'my-component': { var: 'MyComponent', // <= name under which the component will be stored. versions: { '*': { development: 'http://localhost:8080/my-cdn/my-component.js', production : 'http://localhost:8080/my-cdn/my-component.min.js', }, }, }, }; 依赖项中的模块,可能使用虚拟local path作为版本规范,以确保不尝试加载它们来自npm registry。

    优点是您不必触摸HTML文件,异步加载由您的应用直接管理。您可以捆绑Vue而不关心加载顺序/顺序。 CDN组件在实际需要时按需加载。

    缺点是它需要为所有消费者应用程序提供更复杂的webpack配置,但它完全可以管理。

答案 2 :(得分:0)

您是否尝试在webpack.config.js中配置多个入口点?然后,您可以使用一个入口点仅加载组件,而另一个入口点用于其他所有组件。我相信webpack website下面的示例行应该有效。

{
  entry: {
    app: './src/app.js', //Exports to /dist/app.js
    search: './src/components.js' //Exports to /dist/components.js
  },
  output: {
    filename: '[name].js',  //[name] is replaced with the 
                            //key names in the entry option(app & search) 
    path: __dirname + '/dist'
  }
}

然后您创建一个文件/src/app.js,用于导入项目1-3和导出/src/components.js文件的.vue