在从0开始搭建vue+webpack脚手架(二)中已经基本完成了开发环境的配置。当开发完成后,我们需要将完成的项目进行打包,接下来对打包做一些优化:
运行 $ npm run build 可生成dist目录
可以看到 01.jpg被存放在 images目录下, 并且后面生成一串不固定的字符串, 这是由之前的 rules配置的 name: 'images/[name]-[hash:8].[ext]' 产生的,
同样 bundle后面的字符串也是由 filename: "scripts/bundle.[hash:8].js"生成的
六、对CSS进行分离打包
在之前的开发环境下,我们都尽可能将图片和CSS都添加到bundle.js中,但是在完成开发后打包项目,我们需要将CSS文件单独分离出来。
1. 安装分离插件 ExtractTextWebpackPlugin, 使用webpack4.x的必须加 @next, 它会下载到extract-text-webpack-plugin@4.0.0-beta.0
, 否则打包时会有如图报错:
1 npm install --save-dev extract-text-webpack-plugin@next
当然,在最新的webpack版本中,也可以使用 mini-css-extract-plugin 功能和 extract-text-webpack-plugin相似
2. 修改之前配置中 css和style的rules
1 省略代码... 2 const ExtractTextPlugin = require('extract-text-webpack-plugin') 3 4 const config = { 5 # 省略代码... 6 module: { 7 rules: [ 8 { 9 test: /.vue$/, 10 use: [ 11 ... 12 ] 13 }, 14 { 15 test: /.jsx?$/, 16 loader: "babel-loader" 17 }, 18 ## 原来的css和stylus分为isDev环境和非isDev环境下配置 19 { 20 test: /.(jpg|jpeg|gif|png|svg)$/, 21 use: [ 22 ... 23 ] 24 } 25 ] 26 }, 27 plugins: [ 28 ... 29 ] 30 } 31 32 if (isDev) { 33 config.mode = 'development' 34 config.module.rules.push( // 开发环境的配置,不需要提取,与之前的相同 35 { 36 test: /.css$/, 37 use: ['style-loader', 'css-loader'] 38 }, 39 { 40 test: /.styl(us)?$/, 41 use: [ 42 'style-loader', 43 'css-loader', 44 { 45 loader: "postcss-loader", 46 options: { 47 sourceMap: true 48 } 49 }, 50 'stylus-loader', 51 ] 52 }, 53 ) 54 config.devServer = { 55 ... 56 } 57 config.plugins.push( 58 ... 59 ) 60 } else { 61 config.output.filename = 'scripts/bundle.[chunkhash:8].js' // 打包时使用chunkhash ,之前开发时使用hash或者使用文件名本身亦可 62 config.module.rules.push( 63 { 64 test: /.css$/, 65 use: ExtractTextPlugin.extract({ 66 fallback: 'style-loader', 67 use: ['css-loader'] 68 }) 69 }, 70 { 71 test: /.styl(us)?$/, 72 use: ExtractTextPlugin.extract({ 73 fallback: 'style-loader', 74 use: [ 75 'css-loader', 76 { 77 loader: "postcss-loader", 78 options: { 79 sourceMap: true 80 } 81 }, 82 'stylus-loader', 83 ] 84 }) 85 }, 86 ) 87 config.plugins.push( 88 new ExtractTextPlugin('style.[hash:8].css') 89 ) 90 } 91 92 module.exports = config
由以上修改的代码中看出:
(1)在开发环境中不用分离CSS代码, 打包时才使用 ExtractTextPlugin插件分离
(2)编译时使用ExtractTextPlugin的extract方法, 最后用style.[hash:8].css文件输出
(3)打包时使用chunkhash输出文件, 与hash的区别在于,hash是整个应用的文件一样,而chunkhash是每个文件都不一样
(4)运行打包结果如下 : 多出了style.[hash].css文件
七、单独打包类库文件(vue框架及第三方包)
原因:此类库的代码稳定性较高,而项目的业务代码经常需要更新迭代,为了让浏览器能更长时间缓存静态的类库文件,防止类库代码随着业务代码的更新而更新。类库的代码如果能长时间缓存在浏览器中,在项目运行时就不用每次都重新加载,达到减少服务器流量和用户加载更快。
在 else部分添加以下代码:
1 config.entry = { 2 app: path.join(__dirname, 'src/index.js'), 3 vendor: ['vue'] 4 } 5 config.plugins.push( 6 new ExtractTextPlugin('style.[hash:8].css'), 7 // new webpack.optimize.CommonsChunkPlugin() 在webpack4中已废弃, 使用SplitChunksPlugin 8 // new webpack.optimize.SplitChunksPlugin({ 9 // name: 'vendor' 10 // }), 11 ) 12 config.optimization = { 13 splitChunks: { 14 name: 'vendor' 15 }, 16 runtimeChunk: { 17 name: 'runtime' 18 } 19 }
打包后如下:
如上新增三个选项属性
vendor: ['vue'] ------ 表示 将vue, vue-router, vuex等第三方包单独打包
optimization.splitChunks ----- 表示对应vendor打包输出的文件
optimization.runtimeChunk ------ 表示 将app.js中webpack部分的代码分离打包出来
总结:
1. webpack在项目中使用需要分别配置两种环境,即开发环境和生产环境。在开发环境中使用webpack-dev-server和热更新模块HotModuleReplacementPlugin搭配,让数据在不刷新浏览器的情况下改变。在开发环境无需配置压缩代码, 而在生产环境可以使用UglifyJsPlugin对代码压缩。
2. 使用相关loader编译css,js和文件, 编译es6语法
3. devServer选项是在开发环境使用,可以配置热更新,本地域名端口等
4. 使用 ExtractTextPlugin插件对打包文件中的css代码分离出来,注意webpack4 和 webpack3 不用的安装方式。在最新版本的4.x中已经可以使用mini-css-extract-plugin来代替。
5. 使用 CommonsChunkPlugin将第三方类库如vue 等静态代码单独打包可以让浏览器长缓存,在webpack4.x中已经废弃,使用
optimize.SplitChunksPlugin, optimize.RuntimeChunkPlugin或者 optimization.splitChunks, optimization.runtimeChunk替代。