在日常的Vue專案開發中,隨著業務的日漸複雜,程式碼量的日益增加,隨之帶來的問題就是打包後的vendor.js體積過大,導致載入時空白頁時間過長,給使用者的體驗太差。為此我們需要減少vendor.js的體積,從本質上來解決這種問題。
這裡大概例舉幾個在專案中實際用到過的方法,優化後的js大概縮小了50%左右,效果還是挺明顯的。
1,webpack externals
為什麼要配置externals
官方解釋:webpack 中的 externals 配置提供了不從 bundle 中引用依賴的方式。解決的是,所建立的 bundle 依賴於那些存在於使用者環境(consumer environment)中的依賴。
比如我們會在專案中引用各種第三方的js檔案,如 jquery,vue,axios 等,如果我們在打包時排除這些依賴,則可以大大減小檔案的大小,提高頁面載入速度,配置方法如下:
// 在 index.js 中引入資源
<script src="jquery.js"></script>
<script src="vuex.js"></script>
module.exports = {
...
output: {
...
},
externals : {
jquery: 'jQuery'
'vue': 'Vue',
}
...
}
這樣就剝離了那些不需要改動的依賴模組,換句話,下面展示的程式碼還可以正常執行:
import $ from 'jquery';
import Vue from 'vue'
這樣不僅之前對第三方庫的用法方式不變,還把第三方庫剝離出webpack的打包中,從而加速webpack的打包速度。
2,元件按需載入
這也是可以優化的點。如果頻繁使用了第三方元件/UI庫,如我的專案中經常使用了 element-ui 元件庫,如果全部引入,專案體積非常大,這時可以按需引入元件。
首先,我們需要安裝 babel-plugin-component
npm install babel-plugin-component -D
然後,將.babelrc 修改為:
{
"presets": [["es2015", { "modules": false }]],
"plugins": [
[
"component",
{
"libraryName": "element-ui",
"styleLibraryName": "theme-chalk"
}
]
]
}
然後引入部分元件,這樣一來,就不需要引入樣式了,外掛會幫我們處理。
// main.js
import Vue from 'vue'
import { Dialog, Loading } from 'element-ui'
[Dialog, Loading].forEach((comp) => {
Vue.use(comp);
})
3,路由懶載入
當打包構建應用時,JavaScript 包會變得非常大,影響頁面載入。如果我們能把不同路由對應的元件分割成不同的程式碼塊,然後當路由被訪問的時候才載入對應元件,這樣就更加高效了。
方法一
const login = () => import('@/components/login')
const router = new VueRouter({
routes: [
{ path: '/login', component: login }
]
})
注意:這個時候我們需要安裝 babel-plugin-syntax-dynamic-import 外掛,這樣打包時才會識別該語法
方法二
有時候我們想把某個路由下的所有元件都打包在同個非同步塊 (chunk) 中。只需要使用 命名 chunk,一個特殊的註釋語法來提供 chunk name (需要 Webpack > 2.4)。
const Foo = () => import(/* webpackChunkName: "group-foo" */ './Foo.vue')
const Bar = () => import(/* webpackChunkName: "group-foo" */ './Bar.vue')
const Baz = () => import(/* webpackChunkName: "group-foo" */ './Baz.vue')
4,資料快取——keep-alive
VUE2.0中提供了一個keep-alive方法,可以用來快取元件,避免多次載入相應的元件,減少效能的消耗。
舉例:使用者瀏覽A頁面,待A頁面的資源都載入完畢了,使用者通過路由跳轉到了B頁面,之後又退回到了A頁面,如果沒有特殊處理的話,A頁面的資源會重新載入一遍,造成資源浪費;若我們做了快取,則可以減少請求的次數,極高使用者體驗。
1,快取部分頁面
<keep-alive>
<router-view v-if="$route.meta.keepAlive"></router-view>
</keep-alive>
<router-view v-if="!$route.meta.keepAlive"></router-view>
// router 設定如下
routers:[
{ path: '/home',
name: home,
meta: {keepAlive: true} // 設定為true表示需要快取,不設定或者false表示不需要快取
}
]
2,快取元件
<!-- 基本 -->
<keep-alive>
<component :is="view"></component>
</keep-alive>
// include 和 exclude 屬性允許元件有條件地快取。二者都可以用逗號分隔字串、正規表示式或一個陣列來表示
<!-- 逗號分隔字串 -->
<keep-alive include="a,b">
<component :is="view"></component>
</keep-alive>
<!-- 正規表示式 (使用 `v-bind`) -->
<keep-alive :include="/a|b/">
<component :is="view"></component>
</keep-alive>
<!-- 陣列 (使用 `v-bind`) -->
<keep-alive :include="['a', 'b']">
<component :is="view"></component>
</keep-alive>
除了以上的優化方法外,還有常規的 圖片的壓縮合並、CDN加速、壓縮程式碼等方法,大家應該都很熟悉了,這裡就不在一一闡述了。如果大家還有好的優化方案,歡迎大家留言交流~