利用webpack-chain配置happypack和DllReferencePlugin

好久不发博文,最近主要是攻考试去了,积累的几篇文章都懒得写。

今天抽空写一下webpack的打包优化,由于我的框架是基于vue-admin-template做的,框架用的是webpack-chain命令做的,所以也导致了我做webpack优化走了不少弯路。

我的优化主要做了happypack多线程打包和DllReferencePlugin抽离依赖库。

1、先介绍happypack的步骤

(1)安装相关插件,os和happypack,安装的命令根据自己喜欢,我用的是yarn add osyarn add happypack

(2)开始引入依赖,在vue.config.js引入相关依赖,如图:

(3)引入之后开始在chainWebpack(config){}里面写相关代码,如图:

代码如下:

config.plugin('happypack')
      .use(HappyPack)
      .tap(options => {
        options[0] = {
          id: 'babel',
          // 如何处理  用法和loader 的配置一样
          loaders: ['babel-loader?cacheDirectory=true'],
          // 共享进程池
          threadPool: happyThreadPool
        }
        return options
      })
    const hRule = config.module.rule('js')
    hRule.test(/\.js$/)
      .include.add(resolve('src'))
      .end()
    hRule.uses.clear()
    hRule.use('happypack/loader?id=babel')
      .loader('happypack/loader?id=babel')
      .end()

这里需要注意的是一定要记得定义一下,const hRule = config.module.rule('js') 再进行过滤和匹配,如果直接在config.module.rule('js').test(/\.js$/).include.add(resolve('src')) .end()是不对的,有可能是不报错又不生效的,有的是打包正式环境会报错,我的会报错,具体错误如下:

这个错误是我百度了不少案例,然后结合自己的需要才找到正确的写法的,希望大家不要跟我一样犯这个错误。参考链接是这位小哥的:https://blog.csdn.net/weixin_44083712/article/details/106102706

以上就是多线程打包的代码优化,下面是DllReferencePlugin抽离依赖库的优化

2、下面是DllReferencePlugin的优化,这个优化一波三折,三次停工去做别的,最后是挤时间搞定的。我做这个主要参考https://www.geekjc.com/post/5d7f901fb4f5e60da8f3e628这个博客写的,他写得很全,但我按照写法是有bug的。下面是我的步骤。

(1)先将相关插件下载,用到是add-asset-html-webpack-plugin和clean-webpack-plugin,我用的是yarn add add-asset-html-webpack-plugin,yarn add clean-webpack-plugin喜欢用npm的可以用npm。

(2)引入依赖,如图:

然后安装完之后就可以写代码啦,

(3)首先写要分离的包,在vue.config.js同级目录下新建webpack.dll.config.js文件,目录图如下:

(4)文件内容如下(主要抽你经常不变的依赖库出来,我的库不变的主要有以下几个,所以就打包了以下几个):

const path = require('path')
// const CleanWebpackPlugin = require('clean-webpack-plugin')
const { CleanWebpackPlugin } = require('clean-webpack-plugin')
const webpack = require('webpack')

module.exports = {
  mode: 'production',
  entry: {
    vendor: ['vue/dist/vue.runtime.esm.js', 'vuex', 'vue-router', 'element-ui', 'echarts', 'vue-count-to', 'xlsx'],
    util: ['lodash']
  },
  output: {
    filename: '[name].dll.js',
    path: path.resolve(__dirname, 'dll'),
    library: 'dll_[name]'
  },
  plugins: [
    new CleanWebpackPlugin(), // clean-wepback-plugin目前已经更新到2.0.0,不需要传参数path
    new webpack.DllPlugin({
      name: 'dll_[name]',
      path: path.join(__dirname, 'dll', '[name].manifest.json'),
      context: __dirname
    })
  ]
}

(5)在package.json写一个命令 "build:dll": "webpack --config webpack.dll.config.js",如图:

(6)写好命令之后在终端运行以下这个命令生成dll文件夹,如图:

(7)运行完6的命令后生成一个dll文件夹,到这儿离成功就剩一半了,但恰恰是这一半耗了我很长的时间。下面是写代码合并进去的时候,在vue.config.js里面写相关代码。如图:

代码如下:

const dllReference = (config) => {
  config.plugin('vendorDll')
    .use(webpack.DllReferencePlugin, [{
      context: __dirname,
      manifest: require('./dll/vendor.manifest.json')
    }])

  config.plugin('utilDll')
    .use(webpack.DllReferencePlugin, [{
      context: __dirname,
      manifest: require('./dll/util.manifest.json')
    }])

  config.plugin('addAssetHtml')
    .use(AddAssetHtmlPlugin, [
      [
        {
          filepath: require.resolve(path.resolve(__dirname, 'dll/vendor.dll.js')),
          outputPath: 'dll',
          publicPath: 'dll'
        },
        {
          filepath: require.resolve(path.resolve(__dirname, 'dll/util.dll.js')),
          outputPath: 'dll',
          publicPath: 'dll'
        }
      ]
    ])
    .after('html')
}




 chainWebpack(config) {
    config.plugins.delete('preload') // TODO: need test
    config.plugins.delete('prefetch') // TODO: need test
    if (process.env.NODE_ENV === 'production') {
      dllReference(config)
    }
 }

(8)到这打包就完成了。我试着打包,发现报错了,报什么错呢,报Uncaught ReferenceError: _dll_vendor is not defined,我一百度,有个博主有遇到这个问题,说是未在webpack.dll.config.js中 new DllPlugin({})内未配置context。我看看我的代码我内配置了啊,我的问题不是这个,然后找了很久发现了问题

主要是在vue.config.js里面的config.plugin('addAssetHtml')的publicPath: 'dll'到底应该是怎么样的,因为原博客是publicPath: '/dll',我按照他的写法丢上服务器是报错的。然后看了一下是因为我们的module.exports = { publicPath: './'}是不一样的,我的是相对路径他的是绝对路径module.exports = { publicPath: '/'}所以它需要/dll而我不需要,我只需要写dll’。处理完之后打包,清除缓存运行,起来了,啊,一把辛酸泪啊!

注意:如果你路径写不对了,更新完之后,请先清缓存,清缓存很重要,并且后台丢包上去之后,你要等会。我就是因为不等或者是因为忘记清缓存,导致我很多次已经成功了,但是页面上还是报错。我又要不停试别的方法,导致多耗了几个小时的时间。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值