Webpack 配置记录

安装

npm install webpack webpack -D

然后通过 npx webpack -v 查看版本号,这个时候查看的就是当前目录下面的webpack

loader

webpack不能识别非js结尾的文件,这个时候就需要loader来做处理

plugin

可以在webpack运行到某个时刻的时候,帮忙做一些事情

html-webpack-plugin 会在打包结束后,自动生成一个html文件,并把打包生成的js文件自动引入到这个html文件中

然后还可以自己制定模板

image

clean-webpack-plugin 自动清除制定目录

[图片上传失败...(image-50a50a-1560925259310)]

Entry和Output配置

打包多个文件,在output的filename配置成自动获取entry里面的键名

image
image

当我们的静态资源需要部署到cdn上或者另外的服务器上,可以在output里面配置publicPath,打包完之后,模板里面就会自动带上指定的域名了

image
image

SourceMap 配置 开发环境

当 webpack 打包源代码时,可能会很难追踪到 error(错误) 和 warning(警告) 在源代码中的原始位置

为了更容易地追踪 error 和 warning,JavaScript 提供了 source map 功能,可以将编译后的代码映射回原始源代码

image

cheap-module-eval-source-map 推荐开发环境使用,所有的错误(包括依赖包)都会被显示出来,同时速度比较快

cheap-module-source-map 推荐线上环境使用,

webpack-dev-server 自动更新,提升效率

image
image

命令开启的时候,dist目录会放到内存中,项目中暂时看不到dist

模块热更替 HMR

因为HRM是webpack内置的功能,所以在配置文件里先引入webpack


const webpack = require('webpack')
image
image

当我们在某个模块里面引入了其它模块,然后被引入的模块更改后,页面不要刷新,而只是更新被引入模块,就需要在模块里面进行一些配置

if(module.hot){
  module.hot.accept('./count', () => {
    count()
  })
}

这里的意思是,如果count模块更改,就执行后面的回调函数

通过babel转换JS代码

https://www.babeljs.cn/setup#installation 里面查找打包工具

首先在rules里面加入

image

然后在根目录加入.babelrc配置文件

image

上面使用了babel的polyfill功能,把低版本浏览器未实现的方法,通过腻子脚本来实现,这里只会打包使用到的polyfill

在代码里面引入polyfill就可以使用了,这种方式适用于业务代码,如果想打包包文件,可以使用transform-runtime

image
"presets": [["@babel/preset-env",{ // 业务
    "useBuiltIns": "usage"
  }]],
"plugins": [  // 包打包
    [
      "@babel/plugin-transform-runtime",
      {
        "corejs": 2,
        "helpers": true,
        "regenerator": true,
        "useESModules": false
      }
    ]
  ]

Tree shaking

只打包我们我们使用文件中的内容

optimization: {
    usedExports: true
  }
image

上图配置的sideEffects的意思是,对所有文件都执行tree shaking,如果我们想忽略某些文件,可以这么使用

sideEffects: [".css",".less"] 这样即使css或者less没有导出模块,treeshaking也不会忽略掉

但是在开发模式中,我们打包完的文件里面还是能看到全部的代码,这是因为如果开发的时候,treeshaking帮我们删除了一些代码,在代码出错提示的时候,行数就可能会出错。但是在生产环境就没有这个问题,只会打包引用的内容

开发模式和生产模式

通常开发和生产环境的打包配置文件有区别,这个时候我们可以把公共部分抽取出来,然后在我们打包的时候,通过merge把公共的配置加载进去,然后执行不同的配置文件

Code Splitting

默认方式

optimization: {
    splitChunks: {
      chunks: 'all'
    }
  }

异步方式需要先通过babel转码

Lazy loading 懒加载 Chunk

打包生成的每个文件都算一个chunk,懒加载就是延迟加载chunk

打包分析 Preloading Prefetching

webpack 官方打包工具分析 通过这个里面提供的命令,可以生成一份json文件,然后把json文件传到这个地址就可以进行分析了

或者使用命令工具,自动生成完整的的信息 webpack-bundle-analyzer

查看代码利用率 使用ctrl+shift+p 然后查找coverage

prefetch 等待核心代码加载完成后,然后再加载异步代码

CSS 文件的代码分割

minicssextractplugin 目前还不支持HMR 所以最好是用在线上的环境

这里需要注意treeshsaking的问题,因为treeshaking会把引入而没有使用的文件忽略掉,所以,我们要现在package里面把指定的文件进行配置

image
image

如果一个文件在模本里面被直接引用,打包的文件名就是filename,而不再模板里面的就走chunkfilename

image

如果在需要css代码压缩和合并,还需要另外一个插件

Webpack 与浏览器缓存

image

当我们配置contenthash后,文件内容不改动,重新打包的文件名是不会发生改变的

shimming 垫片

当我们使用的第三方库依赖某些包的时候

image

这个文件没有引入jquery,但是又使用了jquery提供的方法,所以需要在webpack配置文件中加一个插件

image

当页面中所有地方使用到$这个变量的时候,webpack会自动帮我们引入jquery

PWA 配置

workbox-webpack-plugin 因为这个插件只在线上使用,所以只用在线上的配置文件里面引入就可以了

image

然后还需要在业务代码里面使用生成好的service-worker文件

if('serviceWorker' in navigator){
  window.addEventListener('load', () => {
    navigator.serviceWorker.register('/service-worker.js').
    then(registration => {
      console.log('registed')
    }).catch(error => {
      console.log(error)
    })
  })
}

使用webpackDevServer 实现请求转发

proxy

image

会把所有的请求代理到dell-lee的域名下面

如果接口地址不变,而又想拿另外一个接口的数据,例如请求的还是header.json 但因为这个接口还在开发中,只能提供一个假接口demo.json 这个时候就可以使用下面的配置

image
image

当被代理网站有防爬虫的时候开启

dev-server 使用了非常强大的 http-proxy-middleware 包。更多高级用法,请查阅其 文档 在这个文档里面,就可以配置更多的东西了,例如header,auth

webpack-dev-server 单页路由

当我们在配置单页路由的时候,需要把不存在的路径全部指向到index,就可以这么配置 这个是在开发环境

image

historyapifallback 会把所有404都指向到默认页面

Eslint 安装

npm install eslint --save-dev

npx eslint --init // 初始化

Webpack 优化

  • 跟上技术的迭代(Node,Npm,Yarn)

  • 在尽可能少的模块上引用loader

  • Plugin尽可能精简并确保可靠

  • resolve 参数合理配置

这个配置会自动帮我们查找当前路径下面以这些为后缀的文件,可以省去我们手写后缀的麻烦
image
  • 使用DllPlugin 提高打包速度 应为第三方模块基本不会改变,所以可以针对第三方模块单独打包,这样每次webpack打包的时候,就不用再去分析第三方模块了。然后通过映射关系,使用第三方插件的时候,就不读取node_modules里面的文件了,而是读取我们打包完成的文件
    1. 首先单独配置一份dll的配置文件 这样指定的第三方模块就打包在一起了
const path = require('path');

module.exports = {
    mode: 'production',
    entry: {
        vendors: ['react','react-dom','lodash'] // 把这三个包打包在一起
    },
    output: {
        filename: '[name].dll.js',
        path: path.resolve(__dirname, '../dll')
    }
}

// 命令 "build:dll": "webpack --config ./build/webpack.dll.js"

​ 2. 然后把打包的文件,通过一个全局变量暴露出去

image

​ 3. 然后再增加一个插件add-asset-html-webpack-plugin 把我们打包好的文件添加到模板里面

image

​ 4.但是到这里,我们代码里面还是使用的是第三方的包,并没有使用我们打包好的文件,下面我们需要生成一个映射文件,在webpack打包的时候,如果发现第三方包在映射文件内,就直接取我们打包好的文件,下面是配置 还是webpack.dll.js

image

​ 5.然后再common配置文件里面,再增加一个插件,把我们刚生成的manifest映射文件引入进来,然后自动帮我们处理映射关系

new AddAssetHtmlWebpackPlugin({
            filepath: path.resolve(__dirname, '../dll/vendors.dll.js')
        }),
        new webpack.DllReferencePlugin({ // 就是这个
            manifest: path.resolve(__dirname, '../dll/vendors.manifest.json')
})

​ 6.最后,当我们要打包的文件分为多个,那怎么办呢 首先配置webpack.dll.js

[图片上传失败...(image-e9dc73-1560925259310)]

https://github.com/tinyzh/tinyzh.github.io/tree/master/webpack-dllplugn)

  • 缩小包的大小
  • 多进程打包
  • 合理使用sourceMap
  • 结合stats分析打包结果
  • 开发过程中,剔除无用插件,例如开发过程中不需要代码压缩,配置文件的mode就选择development就行

源码地址

地址

推荐阅读更多精彩内容

  • 版权声明:本文为博主原创文章,未经博主允许不得转载。 webpack介绍和使用 一、webpack介绍 1、由来 ...
    it筱竹阅读 8,898评论 0 21
  • 2017年12月7日更新,添加了clean-webpack-plugin,babel-env-preset,添加本...
    ZombieBrandg阅读 967评论 0 19
  • 全局安装webpack 全局安装webpack会有个问题,就是当你有两个项目依赖于不同版本的webpack,就会有...
    説好的妹紙呢阅读 1,386评论 0 10
  • 作者:小 boy (沪江前端开发工程师)本文原创,转载请注明作者及出处。原文地址:https://www.smas...
    iKcamp阅读 2,362评论 0 18
  • 写在开头 先说说为什么要写这篇文章, 最初的原因是组里的小朋友们看了webpack文档后, 表情都是这样的: (摘...
    Lefter阅读 4,738评论 3 31
  • 钟毅 文/图 今晚4岁多的儿子在A4纸上画了几副简笔画,邀请我帮他记录他创作的绘本故事。今晚的睡前亲子阅读时光...
    吉祥四宝妈妈阅读 283评论 0 7
  • 我在收麦子 笼子里只有一点麦粒 在偌大的麦场里没有找到自己的地方 看到大家的麦粒堆很高 而自己只有笼底那么多 场里...
    田萍阅读 136评论 2 8
  • 我从未像今天这样害怕过,那份孤独声淹没我面前的所有,电视机还播放着广告吗?外面还有路过的车辆吗?我的仓鼠还在噜...
    Fan_af26阅读 21评论 0 1
  • 悄悄地蒙上双眼,将自己置于盲途中。刚开始还试着欣喜,期待着奇迹发生。后来,玩着玩着就剩下自己了。又开始莫名的恐慌。...
    虚度老太婆阅读 52评论 0 0
  • 两个月前,橘子先生选择了辞职,当时并不存在什么已经找好了下家这种说法。用一个词来形容的话,应该叫"裸辞"。其实身边...
    Des李白阅读 89评论 0 0