vue webpack壓縮程式碼_【原創】webpack如何優化vue專案
技術標籤:vue webpack壓縮程式碼
前言
日常開發中,Vue框架通常都會使用Webpack進行構建,隨著專案不斷迭代,專案逐漸變得龐大,然而專案的構建速度隨之變得緩慢,於是對Webpack構建進行優化變得刻不容緩。通過適當的方法優化後,專案的構建速度提高了50%。現將相關優化方法進行總結分享。
一.優化loader配置
由於Loader對檔案的轉換操作很耗時,所以需要讓儘可能少的檔案被Loader處理。我們可以通過以下3方面優化Loader配置:(1)優化正則匹配(2)通過cacheDirectory選項開啟快取(3)通過include、exclude來減少被處理的檔案。實踐如下:
專案原配置:
{
test: /\.js$/,
loader: 'babel-loader',
include: [resolve('src'), resolve('test')]
},
優化後配置:
{
// 1、如果專案原始碼中只有js檔案,就不要寫成/\.jsx?$/,以提升正則表示式的效能
test: /\.js$/,
// 2、babel-loader支援快取轉換出的結果,通過cacheDirectory選項開啟
loader: 'babel-loader?cacheDirectory',
// 3、只對專案根目錄下的src 目錄中的檔案採用 babel-loader
include: [resolve('src')]
},
二.優化UglifyJS外掛
webpack預設提供了UglifyJS外掛來壓縮JS程式碼,但是它使用的是單執行緒壓縮程式碼,也就是說多個js檔案需要被壓縮,它需要一個個檔案進行壓縮。所以說在正式環境打包壓縮程式碼速度非常慢(因為壓縮JS程式碼需要先把程式碼解析成用Object抽象表示的AST語法樹,再去應用各種規則分析和處理AST,導致這個過程耗時非常大)。
因此我們需要可以並行處理多個子任務,多個子任務完成後,再將結果發到主程序中,有了這個思想後,因此 ParallelUglifyPlugin 外掛就產生了,當webpack有多個JS檔案需要輸出和壓縮時候,原來會使用UglifyJS去一個個壓縮並且輸出,但是ParallelUglifyPlugin外掛則會開啟多個子程序,把對多個檔案壓縮的工作分別給多個子程序去完成,但是每個子程序還是通過UglifyJS去壓縮程式碼。無非就是變成了並行處理該壓縮了,並行處理多個子任務,效率會更加的提高。
安裝 webpack-parallel-uglify-plugin 外掛
然後在webpack.config.js 配置程式碼如下:
// 引入 ParallelUglifyPlugin 外掛const ParallelUglifyPlugin = require('webpack-parallel-uglify-plugin');module.exports = { plugins: [ // 使用 ParallelUglifyPlugin 並行壓縮輸出JS程式碼 new ParallelUglifyPlugin({ // 傳遞給 UglifyJS的引數如下: uglifyJS: { output: { /* 是否輸出可讀性較強的程式碼,即會保留空格和製表符,預設為輸出,為了達到更好的壓縮效果, 可以設定為false */ beautify: false, /* 是否保留程式碼中的註釋,預設為保留,為了達到更好的壓縮效果,可以設定為false */ comments: false }, compress: { /* 是否在UglifyJS刪除沒有用到的程式碼時輸出警告資訊,預設為輸出,可以設定為false關閉這些作用 不大的警告 */warnings:false, /* 是否刪除程式碼中所有的console語句,預設為不刪除,開啟後,會刪除所有的console語句 */drop_console:true, /* 是否內嵌雖然已經定義了,但是隻用到一次的變數,比如將 var x = 1; y = x, 轉換成 y = 5, 預設為不 轉換,為了達到更好的壓縮效果,可以設定為false */collapse_vars:true, /* 是否提取出現了多次但是沒有定義成變數去引用的靜態值,比如將 x = 'xxx'; y = 'xxx' 轉換成 var a = 'xxxx'; x = a; y = a; 預設為不轉換,為了達到更好的壓縮效果,可以設定為false */ reduce_vars: true } } }), ]}
打包對比基本上大小能相差30%!!!!
三.減少冗餘程式碼
babel-plugin-transform-runtime 是Babel官方提供的一個外掛,作用是減少冗餘的程式碼 。 Babel在將ES6程式碼轉換成ES5程式碼時,通常需要一些由ES5編寫的輔助函式來完成新語法的實現,例如在轉換 class extent 語法時會在轉換後的 ES5 程式碼裡注入 extent 輔助函式用於實現繼承。babel-plugin-transform-runtime會將相關輔助函式進行替換成匯入語句,從而減小babel編譯出來的程式碼的檔案大小
四.DllPlugin分包
通過DllPlugin
外掛分離出第三方包
新建
webpack.dll.conf.js
const path = require('path');
const webpack = require('webpack');
const CleanWebpackPlugin = require("clean-webpack-plugin");
module.exports = {
entry: {
vendor: [
'vue',
'vue-router',
'vuex',
'axios',
'element-ui',
'echarts'
]
},
output: {
filename: '[name]_dll_[hash:6].js', // 產生的檔名
path: path.resolve(__dirname, '../static/dll'),
library: '[name]_dll_[hash:6]'
},
plugins: [
new CleanWebpackPlugin({
root: path.resolve(__dirname, '../static/dll'),
dry: false // 啟用刪除檔案
}),
new webpack.DllPlugin({
name: '[name]_dll_[hash:6]',
path: path.resolve(__dirname, '../static/dll', '[name].dll.manifest.json')
})
]
};
修改
webpack.prod.conf.js
使用add-asset-html-webpack-plugin
動態新增dll.js
到html
。
需要注意
add-asset-html-webpack-plugin
要在HtmlWebpackPlugin
後引入;html-webpack-plugin
依賴包版本4.0.0-alpha
會出個問題,新增上去的路徑會變成undefined
需要是3.2.0版本
const AddAssetHtmlPlugin = require('add-asset-html-webpack-plugin');
...
plugins: [
// 插入dll json
new webpack.DllReferencePlugin({
context: path.join(__dirname),
manifest: require('../static/dll/vendor.dll.manifest.json')
}),
new HtmlWebpackPlugin(),
// 插入 dll js
new AddAssetHtmlPlugin([{
publicPath: config.build.assetsPublicPath + 'static/dll/', // 注入到html中的路徑
outputPath: 'static/dll/', // 輸出檔案目錄
filepath: resolve('static/dll/*.js'), // 檔案路徑
includeSourcemap: false,
typeOfAsset: "js"
}])
]
五.按需載入程式碼
通過vue寫的單頁應用時,可能會有很多的路由引入。當打包構建的時候,javascript包會變得非常大,影響載入。如果我們能把不同路由對應的元件分割成不同的程式碼塊,然後當路由被訪問的時候才載入對應的元件,這樣就更加高效了。這樣會大大提高首屏顯示的速度,但是可能其他的頁面的速度就會降下來。專案中路由按需載入(懶載入)的配置:
const Foo = () => import('./Foo.vue')
const router = new VueRouter({
routes: [
{ path: '/foo', component: Foo }
]
})
六.提取公共程式碼
如果每個頁面的程式碼都將這些公共的部分包含進去,則會造成以下問題 :• 相同的資源被重複載入,浪費使用者的流量和伺服器的成本。• 每個頁面需要載入的資源太大,導致網頁首屏載入緩慢,影響使用者體驗。 如果將多個頁面的公共程式碼抽離成單獨的檔案,就能優化以上問題 。Webpack內建了專門用於提取多個Chunk中的公共部分的外掛CommonsChunkPlugin。專案中CommonsChunkPlugin的配置:// 所有在 package.json 裡面依賴的包,都會被打包進 vendor.js 這個檔案中。
new webpack.optimize.CommonsChunkPlugin({
name: 'vendor',
minChunks: function(module, count) {
return (
module.resource &&
/\.js$/.test(module.resource) &&
module.resource.indexOf(
path.join(__dirname, '../node_modules')
) === 0
);
}
}),
// 抽取出程式碼模組的對映關係
new webpack.optimize.CommonsChunkPlugin({
name: 'manifest',
chunks: ['vendor']
}),
總結:
在現實專案中,專案上線後無疑就會要進行優化,特別是使用webpack打包後的專案,如果沒有進行優化,僅靠一般的腳手架搭建預設的配置,打包出來的專案效能堪憂,最直接體現的就是首屏載入速度,也是前端面試中經常考驗的哦,不慌,經過本文以上六種(包括但不限於)優化,打包從30分鐘,到2分鐘不到,整體還有優化空間,可以使用其他cdn
等再進行優化方式,快去試試吧!
覺得本文對你有幫助?請分享給更多人
關注「入坑網際網路」加星標,提升前端技能
The End
如果你喜歡,記得關注大坑
萬水千山總是情,點個 “在看” 行不行