configureWebpack、chainWebpack配置vue.config.js方式
作者:土豆Coder
引入问题
我们使用vue create waf-console-vue
创建一个Vue项目时,新生成的项目我们可以看到在public/index.html
中有这样的内容:
<title><%= htmlWebpackPlugin.options.title %></title>
在Vue CLI 关于HTML和静态资源中有说明:
public/index.html
文件是一个会被处理的模板html-webpack-plugin处理的模板。在构建过程中,资源链接会被自动注入。
所以我们会想到,这里使用变量的形式访问到的
htmlWebpackPlugin.options.title
也就是我们在创建项目的时候命名的项目名称,然后被脚手架Vue CLI
构建项目时自动被处理模板写入了webpack配置中,那我们要如何修改这个配置项呢?
这就引出了问题:
我们如何在@vue-cli4
的vue.config.js
文件中修改webpack中的这个配置项?
也就是如何修改这个值
htmlWebpackPlugin.options.title
修改htmlWebpackPlugin.options.title
因为新的脚手架vue不希望我们直接操作webpack配置文件,所以不再提供webpack.dev.js
这样的文件了,如果我们想要修改webpack配置需要手动创建文件vue.config.js
,那我们如何看默认项目已经配置好的webpack配置内容呢?
vue inspect > output.js
运行后项目中会自动生成一个文件output.js
,这个就是当前项目的webpack配置内容
红框中我们看到title
就是我们的项目名称,现在我们要修改这个值
// vue.config.js module.exports = { chainWebpack: config => { config .plugin('html') .tap(args => { args[0].title = 'title test' return args }) } }
此时,重新启动项目npm run serve
可以看到项目在浏览器中的title
变成了我们设置的值title test
,我们重新导出webpack的配置看看内容是不是改变了
vue inspect > output.js
到此为止我们就通过修改webpack配置改变了项目title
值。
chainWebpack
从上面的应用实例中通过chainWebpack
链式操作修改了webpack的配置,下面是几个利用链式操作修改的例子
修改Loader选项
这是修改之前的配置
// vue.config.js module.exports = { chainWebpack: config => { config .plugin('html') .tap(args => { args[0].title = 'title test' return args }) config.module .rule('vue') .use('vue-loader') .loader('vue-loader') .tap(options => { options.compilerOptions.whitespace = '' // 修改的地方 return options }) } }
修改后我们inspect
结果
总结:如果你想修改某个配置项的值我们都可以先使用inspect出webpack的配置内容,对应的每一项都有注释告诉我们应该如何书写
例如上面使用红框框出的
config.plugin('html')
以及
config.module.rule('vue').use('vue-loader')
添加Loader选项
module.exports = { chainWebpack: config => { config .plugin('html') .tap(args => { args[0].title = 'title test' return args }) config.module .rule('vue') .use('vue-loader') .loader('vue-loader') .tap(options => { options.compilerOptions.whitespace = '' return options }) // GraphQL Loader config.module .rule('graphql') .test(/\.graphql$/) .use('graphql-tag/loader') .loader('graphql-tag/loader') .end() // 你还可以再添加一个 loader .use('other-loader') .loader('other-loader') .end() } }
替换规则的Loader
如果你要替换某个规则的Loader,如果直接调用链式操作,只是在该规则下增加了一条Loader
所以正确的做法是先把这个规则已有的Loader都给删除,然后再加上自己的Loader,这里以svg
为例,修改之前的内容是
module.exports = { chainWebpack: config => { const svgRule = config.module.rule('svg') svgRule.uses.clear() // 清除已有的所有loader svgRule .use('vue-svg-loader') .loader('vue-svg-loader') config .plugin('html') .tap(args => { args[0].title = 'title test' return args }) config.module .rule('vue') .use('vue-loader') .loader('vue-loader') .tap(options => { options.compilerOptions.whitespace = '' return options }) // GraphQL Loader config.module .rule('graphql') .test(/\.graphql$/) .use('graphql-tag/loader') .loader('graphql-tag/loader') .end() // 你还可以再添加一个 loader .use('other-loader') .loader('other-loader') .end() } }
此时我们inspect
结果
添加plugin
const NodePolyfillPlugin = require('node-polyfill-webpack-plugin') module.exports = { chainWebpack: config => { config .plugin('node-polyfill-webpack-plugin') .use(NodePolyfillPlugin) } }
此时我们inspect
结果
configureWebpack
// vue.config.js module.exports = { configureWebpack: config => { console.log(config) }, chainWebpack: config => { console.log(config) } }
通过打印出来的值可以看到结果一样,都是webpack的配置内容。
configureWebpack
对象返回的值会被webpack-merge
合并到最终的webpack配置中,如果你需要基于环境有条件的配置行为,或者想要直接修改配置,可以使用这个。
该方法的第一个参数就是已经解析好的配置,你可以直接修改配置,或者返回一个将会被合并的对象。
像这样:
// vue.config.js module.exports = { configureWebpack: config => { if (process.env.NODE_ENV === 'production') { // 为生产环境修改配置 } else { // 为开发环境修改配置 } } }
总结
以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。