Webpack4兩種加載第三方模塊的方法:ProvidePlugin和 DllPlugin

第一種方法

這種方法比較簡單。就是用 webpack.ProvidePlugin 這個插件

plugins: [
         new webpack.ProvidePlugin({
             $:'fitflex',
             watchInDepth:'watch-in-depth'
         }),
        }),  
    ],

'fitflex''watch-in-depth 是我寫的兩個npm 包, 在node_modules 裏面, 這樣我們可以將其轉化爲兩個全局變量 $watchInDepth

這兩個全局變量可以直接在入口文件index.js 裏面使用,不需要import,也不需要require

第二種方法

就是用webpack.DllPluginwebpack.DllReferencePlugin
爲什麼我們要用一種比較麻煩的方法呢? 如果你用的框架比較大,代碼量比較多,那麼你不想在打包編譯的時候一直帶上它們,而只想打包一次。這裏借用了微軟的DLL概念,就是所謂的動態鏈接庫(dynamic link library)。
第一步:需要給第三方框架打包

webpack.dll.config.js

npm run build --config webpack.dll.config.js
const webpack = require('webpack');
const path = require('path');
module.exports ={
    resolve:{
        extensions: [".js", ".jsx"]
    },
    entry: {
       myDll:['fitflex', 'watch-in-depth']
    },
    output: {
        filename:'[name].dll.js',
        path: path.join(__dirname, "dist", "dll"),
        library:'[name]_dll_[hash]',
       
    },
    plugins:[
        new webpack.DllPlugin({
            name:'[name]_dll_[hash]',
            path:path.join(__dirname, 'dist','dll','[name].manifest.json')
        })
    ]
}

這裏我們看到,我們把這個myDll.dll.js 文件,以及它的myDll.manifest.json 放在了 dist 目錄下的子目錄 dll

到時候我們把打包後的文件放到dist目錄下,就可以用dll

接下來是 webpack.common.js 這裏我就不放 webpack.prod.jswepback.dev.js了,懂的人自然懂,因爲和它們無關。

const path = require('path');
const webpack = require('webpack');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const { CleanWebpackPlugin } = require('clean-webpack-plugin');
const ManifestPlugin = require('webpack-manifest-plugin');
const MiniCssExtractPlugin = require('mini-css-extract-plugin');

module.exports = {
    entry: {
        app: [
            // 'webpack-hot-middleware/client?path=/__webpack_hmr&timeout=20000', // only for webpack-hot-middleware
            path.resolve(__dirname, './src/index.js'),
        ],

    },
    output: {
        filename: '[name].[hash].js',
        path: path.resolve(__dirname, 'dist'),
        // publicPath: '/'// used for Node.js middleware  
    },
    plugins: [
        new ManifestPlugin(),
        new CleanWebpackPlugin({
            verbose:true,
            cleanOnceBeforeBuildPatterns: [ '!myDll']
        }),
        new webpack.HashedModuleIdsPlugin(),
        new webpack.NoEmitOnErrorsPlugin(),
        new webpack.NamedModulesPlugin(),
        new MiniCssExtractPlugin(),
        new HtmlWebpackPlugin({
            title: 'production',
            minify: {
                collapseWhitespace: true,
                minifyCSS: true,
            },
            filename: 'index.html',
            template: 'index.html',
            hash: true,
        }),
        // new webpack.ProvidePlugin({
        //     $:'fitflex',
        //     watchInDepth:'watch-in-depth'
        // }),
        new webpack.DllReferencePlugin({
            context:__dirname,
            manifest: path.join('dist', 'dll', `myDll.manifest.json`),
        }),
        
      
    ],
    optimization: {
        moduleIds: 'hashed',
        runtimeChunk: 'single',
        splitChunks: {
            cacheGroups: {
                vendor: {
                    test: /[\\/]node_modules[\\/]/,
                    name: 'vendors',
                    chunks: 'all',
                },
            },
        },

    },
    module: {
        rules: [
            {
                test: /\.css$/i,
                use: [
                    MiniCssExtractPlugin.loader,
                    'css-loader'
                ],
            },
            // {
            //     test: require.resolve('./src/index.js'),
            //     use: 'imports-loader?this=>window'
            // },

            {
                test: /\.(png|svg|jpg|gif)$/,
                use: [
                    'file-loader'
                ]
            }
        ]
    }
};

這裏我們需要關注四點。
第一個就是非常魔性的插件 clean-webpack-plugin ,老版挺直觀,新版在require的時候很魔性,特別是option裏面的屬性名,我無力吐槽,本來用要刪什麼文件,不刪什麼文件,用exclude, 或者include 搞定的玩意兒,非要搞個很長的名字,欺負我們不是以英語爲母語的國家嗎?
這裏我們把有myDll名字的文件排除出清除名單。因爲我們的目的就是希望dll文件編譯打包一次就不再重複編譯了。

第二
就是主角:webpack.DllReferencePlugin
這個插件的目的是讓編譯的文件可以識別myDll.manifesion.json 從而把index.js裏面的模塊正確的加載進來。

第三
我們需要在index.html裏面加上

 <script src="./dll/myDll.dll.js"></script>

保證正確引入dll文件。

第四
index.js裏面怎麼引入模塊呢?

const $ = require('fitflex');
const watchInDepth = require('watch-in-depth');

還是用require的老方法。

接下來展示下目錄
在這裏插入圖片描述
最後再吐槽一下官方的在github上的例子,好好的一個項目非要拆開寫分成 vendoruser,讓後讓我在如何把這兩者聯繫起來,這個問題上陷入了一天的沉思。

好了,最後再做個廣告,儘管恰不到飯,還是歡迎大家star我寫的這兩個包。
可以直接 npm install 哦。

watch-in-depth: 對嵌套對象,數組以及json文件的監控

fitflex: 一個巨好用的CSS動態佈局系統

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章