# webpack 简介
官方说,webpack is a static module bundler for modern JavaScript applications.
翻译过来:webpack 是一个静态的模块化打包工具,为现代的 JavaScript 应用程序;
- 我们来对上面的解释进行拆解: p 打包 bundler:webpack 可以将帮助我们进行打包,所以它是一个打包工具
- 静态的 static:这样表述的原因是我们最终可以将代码打包成最终的静态资源(部署到静态服务器);
- 模块化 module:webpack 默认支持各种模块化开发,ES Module、CommonJS、AMD 等;
- 现代的 modern:我们前端说过,正是因为现代前端开发面临各种各样的问题,才催生了 webpack 的出现和发展;
# 基础安装
# webpack 和 webpack-cli
webpack
是执行打包的本体,它原生只支持打包 Javascript
和 Json
文件,若需要打包如 html
、 css
、 image
等资源则要安装相应的 loader
。
webpack-cli
是调用 webpack
的一种手段。通常我们调用 webpack
都是直接在命令行里调用的,而这正是 webpack-cli
的功劳。如果没有安装 webpack-cli
那么我们将不能直接从命令行里读取参数。它起到的是一个传递命令行参数到 webpack
中的功能。实际上,当我们使用 Vue 或 React 的脚手架时,我们并没有安装 webpack-cli
这个东西。Vue 有 vue-cli
而 React 有 creat-react-app
,它们替代了 webpack-cli
传递命令行参数到 webpack
的功能。
# 安装
# 全局安装 webpack5 和 webpack-cli4
npm install -g webpack@5 webpack-cli@4
# 局部安装
npm install -D webpack@5 webpack-cli@4
# 基础使用
当我们直接使用 webpack
命令时,调用的是我们全局安装的 webpack
。
如果我们需要使用当前项目中的 webpack
版本打包项目,有三种方式分别是:
第一种直接找到本地安装路径,调用
# 直接找到node_modules/.bin下的webpack文件打包
node_modules\.bin\webpack
第二种使用 npx
# 使用npx,npx可以自动去node_modules文件夹下寻找文件
npx webpack
第三种在配置文件 package.json
中配置命令,该方法最常用
// 在配置文件 package.json 的 "script" 里的配置命令 | |
"scripts": { | |
"build": "webpack" //package.json 会优先在本地 node_modules 中寻找,若找不到则会往上查找全局环境下的 webpack | |
} |
# 调用scripts里的命令
npm run build
# 配置 package.json
当我们使用 webpack
打包文件时,它会默认从当前目录下找到 src
文件夹下的 index.js
。所有引入或关联到 index.js
里的资源都会被 webpack
打包,否则不会被打包。
默认打包的文件会生成在当前目录的 dist
文件夹下,名称为 main.js
。
在通常情况下,webpack 需要打包的项目是非常复杂的,并且我们需要一系列的配置来满足要求,默认配置必然是不可以的。
我们可以在根目录下创建一个 webpack.config.js
文件,来作为 webpack
的配置文件:
// 需求:将入口文件改为 main.js ,输出文件改为 bundle.js | |
// 方法一 常用方法 | |
// webpack.config.js | |
const path = require('path'); | |
// 导出配置信息 | |
module.exports = { | |
entry: "./scr/main.js", // 入口文件更改为 main.js | |
output: { | |
filename: "bundle.js", // 输出文件的名称更改为 bundle.js | |
path: path.resolve(__dirname,"./dist") | |
} | |
} |
# 方法二
npx webpack --entry ./src/main.js --output-path ./build
默认情况下 webpack
从 webpack.config.js
里读取配置,当我需要更改 webpack
读取配置的文件时,可以通过 --config
来指定配置文件
# 指定 wk.config.js 为 webpack 的配置文件
webpack --config wk.config.js
或者通过 package.json
指定
// package.json | |
"scripts": { | |
"build": "webpack --config wk.config.js" | |
} |
# 配置 Loader
开头我们说过, webpack
原生只支持打包 javascript
文件和 json
文件。当我们需要打包其它资源时,就要配置相应的 loader
来支持,否则会报错。
# css-loader
使用 loader
前我们需要安装好 loader
。安装 css-loader
:
npm install css-loader -D
使用 loader
通常有三种方式,分别是:
- 内联方式
- cli 方式
- 配置文件方式
# 内联方式
内联方式就是在引入的样式前加上使用的 loader,并且使用 !
分割每个 loader
。这种方式只能作用在当前文件下,若其它文件下也引入了 css 文件则需要再次配置。所以不常使用。
//index.js 中引入 css 文件并使用 css-loader 和 style-loader | |
import "style-loader!css-loader../css/index.css" // 在路径前面加上 loader 名称 |
# cli 方式
在 webpack5
的文档中已经没有了 --module-bind
命令,所以 webpack5
不支持该模式。具体配置方式可查找 webpack4 官方文档
# 配置文件方式
该方式是最常见的 loader
使用方式。其意思是在我们的 webpack.config.js
文件中写明配置信息。在该文件暴露的对象中,使用 module.rules
来配置 loader
// webpack.config.js | |
const path = require('path'); | |
// 导出配置信息 | |
module.exports = { | |
entry: "./scr/main.js", | |
output: { | |
filename: "bundle.js", | |
path: path.resolve(__dirname,"./dist") | |
} | |
module: { | |
rules: [ //rules 属性对应的值是一个数组:[Rule] 。数组中存放的是一个个的 Rule,Rule 是一个对象,对象中可以设置多个属性: | |
{ | |
test: /\.css$/, // 用于对 resource(资源)进行匹配的,通常会设置成正则表达式 | |
//loader:"css-loader" // 写法一 | |
//use: ["css-loader"] // 写法二 | |
// 写法三 | |
use: [ // 对应的值时一个数组:[UseEntry] 。UseEntry 是一个对象,可以通过对象的属性来设置一些其他属性: | |
{loader:"css-loader",options:'xxx'} // 完整写法,options 可以对 css-loader 传入参数 | |
// 若无需传参则可简写为写法二 | |
// 若处理该文件仅使用一个 loader,可简写为写法一 | |
] | |
//loader:'css-loader' 写法四。 loader 属性: Rule.use: [{loader} ] 的简写。 | |
} | |
] | |
} | |
} |
# style-loader
当我们把 css 文件打包好后,css 文件并不会生效。此时我们还需要使用 style-loader
将打包好的 css 插入页面。安装 style-loader
:
npm install style-loader -D
配置 style-loader
。这里需要注意的是,使用多个 loader
处理同一个资源时, loader
的调用顺序是从后往前的。所以 loader
的顺序需要将 style-loader
放在最后。配置书写如下:
// webpack.config.js | |
module: { | |
rules: [ | |
{ | |
test: /\.css$/, | |
use: [ | |
{loader: "style-loader"}, // 然后再插入页面 | |
{loader: "css-loader"} // 先将 css 文件解析打包 | |
] | |
} | |
] | |
} |
# less-loader
打包 less
文件的步骤也和上面的文件同理,但是 less-loader
本身并不能处理 less
文件,所以安装时还需要另外安装 less
处理工具, less-loader
仅仅只是调用了 less
处理工具而已。安装 less
处理工具和 less-loader
:
npm install less -D # 安装less处理工具
npm install less-loader -D # 安装less-loader
配置 less-loader
:
// webpack.config.js | |
module: { | |
rules: [ | |
{ | |
test: /\.css$/, | |
use: [ | |
{loader: "style-loader"}, | |
{loader: "css-loader"}, | |
{loader: "less-loader"} | |
] | |
} | |
] | |
} |
# browserslist
开发中我们经常需要去处理浏览器兼容性问题,我们不可能针对每个浏览器一个一个去配置兼容性。通常的做法是根据浏览器的市场占有率去选择性兼容。在开发中有专门的工具如 autoprofixer
、 PostCss
、 postcss-preset-env
去帮助我们自动生成兼容代码,而这里我们首先要解决的是关于浏览器的市场占有率等信息如何自动获取。 browserslist
就是帮助我们获取浏览器占有率,指定要配置哪些浏览器的工具。它可以让我们在不同的前端工具之间,共享目标浏览器和 Node.js 版本的配置。
安装 browserslist
:
npm install browserslist -D
配置 browserslist
。配置它有两种方式,一是通过 package.json
,二是单独编写 .browserslistrc
文件配置当有该文件时会默认读取该文件中的配置。
package.json
配置:
"browserslist": [ | |
"last 2 version", | |
"not dead", | |
"> 1%" | |
] |
我们还可以通过编辑 .browserslistrc
文件去配置:
last 2 version
not dead
> 1%
Browserslist 编写规则:
- defaults:Browserslist 的默认浏览器(> 0.5%, last 2 versions, Firefox ESR, not dead)
- 5%:通过全局使用情况统计信息选择的浏览器版本。 >=,< 和 <= 工作过
- 5% in US:使用美国使用情况统计信息。它接受两个字母的国家 / 地区代
- 5% in alt-AS:使用亚洲地区使用情况统计信息。有关所有区域代码的列表,请参见 caniuse-lite/data/regions
- 5% in my stats:使用自定义用法数据
- 5% in browserslist-config-mycompany stats:使用 来自的自定义使用情况数据 browserslist-config-mycompany/browserslist-stats.json
- cover 99.5%:提供覆盖率的最受欢迎的浏览器
- cover 99.5% in US:与上述相同,但国家 / 地区代码由两个字母组成
- cover 99.5% in my stats:使用自定义用法数据。
- dead:24 个月内没有官方支持或更新的浏览器
- last 2 versions:每个浏览器的最后 2 个大版本
- last 2 Chrome versions:最近 2 个版本的 Chrome 浏览器
- last 2 major versions 或 last 2 iOS major versions:最近 2 个主要版本的所有次要 / 补丁版本
- node 10 和 node 10.4:选择最新的 Node.js10.x.x 或 10.4.x 版本
- current node:Browserslist 现在使用的 Node.js 版本
- maintained node versions:所有 Node.js 版本,仍由 Node.js Foundation 维护
- iOS 7:直接使用 iOS 浏览器版本 7
- Firefox > 20:Firefox 的版本高于 20 >=,< 并且 <= 也可以使用。它也可以与 Node.js 一起使用
- ie 6-8:选择一个包含范围的版本
- Firefox ESR:最新的 [Firefox ESR] 版本
- PhantomJS 2.1 和 PhantomJS 1.9:选择类似于 PhantomJS 运行时的 Safari 版本
- extends browserslist-config-mycompany:从 browserslist-config-mycompanynpm 包中查询
- supports es6-module:支持特定功能的浏览器。 es6-module 这是 “我可以使用” 页面 feat 的 URL 上的参数。有关所有可用功能的列表,请参见 。caniuse- lite/data/features
- browserslist config:在 Browserslist 配置中定义的浏览器。在差异服务中很有用,可用于修改用户的配置,例如 browserslist config and supports es6-module
- since 2015 或 last 2 years:自 2015 年以来发布的所有版本(since 2015-03 以及 since 2015-03-10)
- unreleased versions 或 unreleased Chrome versions:Alpha 和 Beta 版本
- not ie <= 8:排除先前查询选择的浏览器
根据上述编写规则,我们编写了多个条件之后,多个条件之间是什么关系呢?
刚刚我们在 .browserslistrc
中书写的规则没有添加关键字,默认为 or
的关系