DllPlugin 插件配置實踐node
DLLPlugin 和 DLLReferencePlugin 用某種方法實現了拆分 bundles,同時還大大提高了構建的速度。jquery
工程目錄webpack
### 目錄結構以下:
dll-plugin # 工程名
| |--- dist # 打包後生成的目錄文件
| |--- node_modules # 全部的依賴包
| |--- src # 存放全部js文件
| | |-- pageOne.js
| | |-- pageTwo.js # js入口文件
| |--- webpack.config.js # webpack配置文件
| |--- webpack.dll.config.js # 打包第三方依賴的庫文件
| |--- README.md
| |--- package.json
複製代碼
首先咱們須要在項目下建立一個單獨的打包dll文件的配置文件webpack.dll.config.jsweb
const path = require('path');
const webpack = require('webpack');
const library = '[name]_dll_lib';
module.exports = {
mode: 'development',
// 入口, 接收多個參數做爲多個入口
entry: {
// dll文件中包含的第三方庫列表
jquery: ['jquery'],
echarts: ['echarts']
},
output: {
// 文件名稱
filename: 'dll/[name].dll.js',
// 文件輸出目錄
path: path.resolve(__dirname, 'dist'),
// 存放dll文件的全局變量名稱,須要注意命名衝突
library: library
},
plugins: [
new webpack.DllPlugin({
// manifest文件中的name屬性值, 需與output.library保持一致
name: library,
// mainfest文件輸出路徑和文件名稱
path: path.join(__dirname, 'dist', 'dll/[name].manifest.json')
})
]
}
複製代碼
接下來須要在webpack.config中使用的manifestnpm
module.exports = {
/***** other options ******/
plugins: [
// 告訴webpack使用了哪些第三方庫代碼
new DllReferencePlugin({
// manifest文件中請求的上下文,
context: __dirname,
// jquery 映射到json文件上去
manifest: require('./dist/jquery.manifest.json')
}),
new DllReferencePlugin({
// echarts 映射到json文件上去
manifest: require('./dist/echarts.manifest.json')
})
]
}
複製代碼
package.json 中添加打包命令json
"scripts": {
"build:dll": "webpack --config webpack.dll.config.js",
},
複製代碼
運行npm run build:dll, 運行完成以後,會在dist/dll目錄下生成 echarts.dll.js, echarts.manifest.json,jquery.dll.js, jquery.manifest.json 文件echarts
在src/pageOne.js入口文件中引入jquery和echarts庫, src/pageTwo.js文件中不引入任何依賴ide
const jquery = require('jquery');
const echarts = require('echarts');
console.log("Hello World from pageOne main file!");
複製代碼
執行打包命令 npm run build 函數
發現打包的時間是668ms, pageOne和pageTwo打包出來的大小僅相差了3kb, 顯然第三方庫代碼沒有打包到項目文件裏。再來對比一下使用dll和不使用dll的狀況優化
打包時間變成了1781ms, 增長了近兩倍, 打包大小變爲3683KB, 將jquery和echarts第三方庫代碼打包進了pageOne中。
使用DllPlugin分離bundle,構建速度和工程文件大小優化明顯。
瞭解dll-plugin的做用和用法後,再來看看它是怎麼實現的。
先看一下打包生成的dll文件, echarts.dll.js:
var echarts_dll_lib = (function(modules) {
// ... 此處省略 webpackBootstrap 函數代碼
}({
"./node_modules/echarts/index.js": (function(module, exports, __webpack_require__) {
// ID爲./node_modules/echarts/index.js模塊對應的代碼
}),
"./node_modules/echarts/lib/CoordinateSystem.js": (function(module, exports, __webpack_require__) {
// ID爲./node_modules/echarts/lib/CoordinateSystem.js模塊對應的代碼
}),
// ......
}));
複製代碼
DllPlugin 將echarts依賴導出成了一個函數,並將echarts_dll_lib掛載到window全局對象中, 能夠看到dll爲echarts中的各個模塊都分配了一個Id。
再看echarts.manifest.json:
{
"name":"echarts_dll_lib",
"content": {
"./node_modules/echarts/lib/util/animation.js": {
"id": "./node_modules/echarts/lib/util/animation.js",
"buildMeta":{"providedExports":true}
},
// .....
"./node_modules/echarts/index.js": {
"id":"./node_modules/echarts/index.js",
"buildMeta": {"providedExports":true}
},
// ......
}
}
複製代碼
echarts.manifest.json 文件能夠清楚的看到與其對應的dll.js文件中包含了哪些模塊,以及每一個模塊的路徑和ID。
在webpackConfig中配置DllReferencePlugin引入manifest, 當項目中引入echarts模塊時,會經過路徑匹配到manifest中的對應模塊id, 再經過模塊id和name屬性, 找到掛載再window上的對應的模塊代碼。