一、Webpack主要作用:
- 代码转换:TypeScript 编译成 JavaScript、SCSS 编译成 CSS 等。
- 文件优化:压缩 JavaScript、CSS、HTML 代码,压缩合并图片等。
- 代码分割:提取多个页面的公共代码、提取首屏不需要执行部分的代码让其异步加载。
- 模块合并:在采用模块化的项目里会有很多个模块和文件,需要构建功能把模块分类合并成一个文件。
- 自动刷新:监听本地源代码的变化,自动重新构建、刷新浏览器。
- 代码校验:在代码被提交到仓库前需要校验代码是否符合规范,以及单元测试是否通过。
- 自动发布:更新完代码后,自动构建出线上发布代码并传输给发布系统。
二、Webpack 有以下几个核心概念:
- Entry:入口,Webpack 执行构建的第一步将从 Entry 开始,可抽象成输入。
- Module:模块,在 Webpack 里一切皆模块,一个模块对应着一个文件。Webpack 会从配置的 Entry 开始递归找出所有依赖的模块。
- Chunk:代码块,一个 Chunk 由多个模块组合而成,用于代码合并与分割。
- Loader:模块转换器,用于把模块原内容按照需求转换成新内容。
- Plugin:扩展插件,在 Webpack 构建流程中的特定时机会广播出对应的事件,插件可以监听这些事件的发生,在特定时机做对应的事情。
- Output:输出结果,在 Webpack 经过一系列处理并得出最终想要的代码后输出结果。
三、用Webpack打包WebStorm创建的React项目
1、安装Webpack和Webpack-cli
npm install webpack webpack-cli
2、修改package.json文件中的build为webpack
"scripts": {
"start": "react-scripts start",
"build": "webpack",
"test": "react-scripts test",
"eject": "react-scripts eject"
}
3、安装以下包
"babel-cli": "^6.26.0",
"babel-core": "^6.26.3",
"babel-loader": "^8.1.0",
"babel-preset-env": "^1.7.0",
"babel-preset-react": "^6.24.1",
"css-loader": "^5.2.7",
"file-loader": "^6.2.0",
"html-webpack-plugin": "^4.5.0",
"less-loader": "^5.0.0",
"node-sass": "^4.14.1",
"sass-loader": "^5.0.0",
"style-loader": "^2.0.0",
"url-loader": "^4.1.1"
指令如:
npm install babel-loader@8.1.0
注意:包的版本号(版本不匹配,打包会报错)
4、在项目根目录下创建webpack.config.js文件
const path = require('path');
const HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
mode: "development",
entry: './src/index.js', //入口配置
output: { //出口配置
path: path.resolve(__dirname,'build'), //打包文件的输出路径
filename: "bundle.js" //打包文件名
},
module: { //rules、loader
rules: [{
test: /\.js$/, //使用正则匹配所有需要使用babel-loader的文件
use: {
loader: "babel-loader", //指明要使用的loader
options: { //传入loader的参数
presets: ["@babel/env", "@babel/react"]
}
}
},
{
test: /\.css$/, //使用正则表达式匹配所有需要使用此loader的文件
use: [
'style-loader',
'css-loader',
]
},
{
test: /\.scss$/, //使用正则匹配所有需要使用此loader的文件
use: [
'style-loader',
'css-loader',
'sass-loader'
] //处理顺序依次是:sass-loader -> css-loader -> style-loader
},
{
test: /\.less$/,
use: [
'style-loader',
'css-loader',
'less-loader'
]
},
{
test:/\.(png|svg|jpg|gif)$/,
use: [{
loader: 'url-loader',
options: {
limit: 1024 * 30, //30KB以下的文件采用url-loader
fallback: 'file-loader', //否则采用file-loader,默认值是file-loader
outputPath: 'images' //图片输出路径,相当于output.path
}
}]
},
{
test: /\.(eot|ttf|woff|svg)$/,
use: [{
loader: "url-loader",
options: {
limit: 1024 * 30,
fallback: 'file-loader',
outputPath: 'fonts'
}
}]
}
]
},
plugins: [ //插件
new HtmlWebpackPlugin({
template: './public/index.html', //指定模板路径
filename: 'index.html' //指定文件名
})
]
}
5、配置详解:
5.1、配置Babel:目前浏览器对ES6的标准支持不全,所以我们需要把ES6转换成ES5
rules: [{
test: /\.js$/, //使用正则匹配所有需要使用babel-loader的文件
use: {
loader: "babel-loader", //指明要使用的loader
options: { //传入loader的参数
presets: ["@babel/env", "@babel/react"]
}
}
}
5.2、自动生成HTML:使用html-webpack-plugin 自动生成HTML,并引入相应文件。
const HtmlWebpackPlugin = require('html-webpack-plugin');
plugins: [ //插件
new HtmlWebpackPlugin({
template: './public/index.html', //指定模板路径
filename: 'index.html' //指定文件名
})
]
5.3、加载CSS:webpack本身只认得JS文件,其他非JS文件需要用loader进行转换。处理css文件,需要用到以下两个loader:
- css-loader 负责解析 CSS 代码,主要是为了处理 CSS 中的依赖,例如 @import 和 url() 等引用外部文件的声明。
- style-loader 会将 css-loader 解析的结果转变成 JS 代码,运行时动态插入 style 标签来让 CSS 代码生效。
{
test: /\.css$/, //使用正则表达式匹配所有需要使用此loader的文件
use: [
'style-loader',
'css-loader',
]
}
5.4、加载SCSS和less
{
test: /\.scss$/, //使用正则匹配所有需要使用此loader的文件
use: [
'style-loader',
'css-loader',
'sass-loader'
] //处理顺序依次是:sass-loader -> css-loader -> style-loader
},
{
test: /\.less$/,
use: [
'style-loader',
'css-loader',
'less-loader'
]
}
5.5、加载图片&字体:file-loader, url-loader可用于处理图片,字体等静态资源。
url-loader封装了file-loader:
- 文件大小小于limit参数时,url-loader将会把文件转为DataURL。
- 文件大小大于limit,url-loader会调用file-loader进行处理。
{
test:/\.(png|svg|jpg|gif)$/,
use: [{
loader: 'url-loader',
options: {
limit: 1024 * 30, //30KB以下的文件采用url-loader
fallback: 'file-loader', //默认值是file-loader
outputPath: 'images' //图片输出路径,相当于output.path
}
}]
},
{
test: /\.(eot|ttf|woff|svg)$/,
use: [{
loader: "url-loader",
options: {
limit: 1024 * 30,
fallback: 'file-loader',
outputPath: 'fonts'
}
}]
}
]
}
5.6、模式:在日常的前端开发工作中,一般都会有开发&生产两套构建环境。webpack 4.X新增用mode字段指定当前环境,并启用相应模式下的webpack内置的优化。
module.exports = {
mode: "development",
}
选项 | 描述 |
development (开发环境) | process.env.NODE_ENV =development |
production (生产环境) | process.env.NODE_ENV =production |