vue項目優化之按需加載組件-使用webpack require.ensure


 

require-ensurerequire-amd的區別:

  • require-amd
    • 說明: 同AMD規范的require函數,使用時傳遞一個模塊數組和回調函數,模塊都被下載下來且都被執行后才執行回調函數
    • 語法: require(dependencies: String[], [callback: function(...)])
    • 參數
      • dependencies: 模塊依賴數組
      • callback: 回調函數
  • require-ensure
    • 說明: require.ensure在需要的時候才下載依賴的模塊,當參數指定的模塊都下載下來了(下載下來的模塊還沒執行),便執行參數指定的回調函數。require.ensure會創建一個chunk,且可以指定該chunk的名稱,如果這個chunk名已經存在了,則將本次依賴的模塊合並到已經存在的chunk中,最后這個chunk在webpack構建的時候會單獨生成一個文件。
    • 語法: require.ensure(dependencies: String[], callback: function([require]), [chunkName: String])
      • dependencies: 依賴的模塊數組
      • callback: 回調函數,該函數調用時會傳一個require參數
      • chunkName: 模塊名,用於構建時生成文件時命名使用
    • 注意點:requi.ensure的模塊只會被下載下來,不會被執行,只有在回調函數使用require(模塊名)后,這個模塊才會被執行。

示例

require-amd

源代碼

  • webpack.config.amd.js

    var path = require("path"); module.exports = { entry: "./example.amd.js", output: { path: path.join(__dirname, "amd"), filename: "[name].bundle.js", chunkFilename: "[id].chunk.js" } };
  • example.amd.js

    require(["./module1"], function(module1) { console.log("aaa"); var module2 = require("./module2"); console.log("bbb"); });
    • 1
  • module1.js

    console.log("module1"); module.exports = 1;
  • module2.js

    console.log("module2"); module.exports = 2; 

構建結果

命令行中運行webpack --config webpack.config.amd.js
- main.bundle.js
- example.amd.js
- 1.chunk.js
- module1.js
- module2.js

運行結果

瀏覽器中運行amd/index.html,控制台輸出:

module1
aaa
module2
bbb

require-ensure

源代碼

  • webpack.config.ensure.js

    var path = require("path"); module.exports = { entry: "./example.ensure.js", output: { path: path.join(__dirname, "ensure"), filename: "[name].bundle.js", chunkFilename: "[name].chunk.js" } };
  • example.ensure.js

    require.ensure(["./module1"], function(require) { console.log("aaa"); var module2 = require("./module2"); console.log("bbb"); require("./module1"); }, 'test');
    • 1
    • 2
  • module1.js
    同上

  • module2.js
    同上

構建結果

命令行中運行webpack --config webpack.config.ensure.js
- main.bundle.js
- example.amd.js
- 1.chunk.js
- module1.js
- module2.js

運行結果

瀏覽器中運行ensure/index.html,控制台輸出:

aaa
module2
bbb
module1
  • 1

require-ensure-chunk

源代碼

  • webpack.config.ensure.chunk.js

    var path = require("path"); module.exports = { entry: "./example.ensur.chunk.js", output: { path: path.join(__dirname, "ensure-chunk"), filename: "[name].bundle.js", chunkFilename: "[name].chunk.js" } };
  • example.ensur.chunk.js

    require.ensure(["./module1"], function(require) { console.log("aaa"); require("./module1"); console.log("bbb"); }, 'common'); require.ensure(["./module2"], function(require) { console.log("ccc"); require("./module2"); console.log("ddd"); }, 'common')8
    • 9
    • 10
  • module1.js
    同上

  • module2.js
    同上

構建結果

命令行中運行webpack --config webpack.config.ensure.js
- main.bundle.js
- example.amd.js
- 1.chunk.js
- module1.js
- module2.js

運行結果

瀏覽器中運行ensure/index.html,控制台輸出:

aaa
module1
bbb
ccc
1module2 ddd

webpack-module-requir

使用 vue-cli構建的項目,在 默認情況下 ,執行 npm run build  會將所有的js代碼打包為一個整體,

打包位置是 dist/static/js/app.[contenthash].js   

類似下面的路由代碼 

router/index.js  路由相關信息,該路由文件引入了多個 .vue組件

  1. import Hello from '@/components/Hello'
  2. import Province from '@/components/Province'
  3. import Segment from '@/components/Segment'
  4. import User from '@/components/User'
  5. import Loading from '@/components/Loading'

執行 npm run build 會打包為一個整體 app.[contenthash].js ,這個文件是非常大,可能幾兆或者幾十兆,加載會很慢


所以我們需要分模塊打包,把我們想要組合在一起的組件打包到一個 chunk塊中去

分模塊打包需要下面這樣使用 webpack的 require.ensure,並且在最后加入一個 chunk名,

相同 chunk名字的模塊將會打包到一起

router/index.js 修改為懶加載組件

  1. const Province = r => require.ensure([], () => r(require('@/components/Province.vue')), 'chunkname1')
  2. const Segment = r => require.ensure([], () => r(require('@/components/Segment.vue')), 'chunkname1')
  3. const Loading = r => require.ensure([], () => r(require('@/components/Loading.vue')), 'chunkname3')
  4. const User = r => require.ensure([], () => r(require('@/components/User.vue')), 'chunkname3')

根據 chunkame的不同, 上面的四個組件, 將會被分成3個塊打包,最終打包之后與組件相關的js文件會分為3個 (除了app.js,manifest.js, vendor.js)

分模塊打包之后在 dist目錄下是這樣的, 這樣就把一個大的 js文件分為一個個小的js文件了,按需去下載,其他的使用方法和import的效果一樣

參考vue-router官方文檔: https://router.vuejs.org/zh-cn/advanced/lazy-loading.html



免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM