webpack5-plugin
一、意识 plugin
loader: 转换 特定类型 读取文件时
plugin: 可做更多的事件,在打包的流程中,交叉一些操作(清理原有打包后果、css 压缩、创立 html 模板、定义我的项目全局变量等)
应用一个常见的 plugin(分内置与第三方),清理原有打包后果:
clean-webpack-plugin 下载:
yarn -D add clean-webpack-plugin
在 webpack.config.js 中配置 plugins:
const {CleanWebpackPlugin} = require('clean-webpack-plugin');
module.exports = {
...
plugins: [new CleanWebpackPlugin()
]
}
/**
* 插件就是一个类,相似于:* class HelloPlugin {* contructor(){}
* apply(compiler) {}
* }
* 须要应用模块化的形式引入,而后应用 new 关键字创建对象,再放入 plugins 数组中
*/
二、罕用插件应用
1.html-webpack-plugin 应用
性能:
用于生成 html 模板文件
装置:
yarn -D add html-webpack-plugin
配置插件:
const HtmlWebpackPlugin = require('html-webpack-plugin');
const {DefinePlugin} = require('webpack'); // 用于定义我的项目全局常量
plugins: [
...
new HtmlWebpackPlugin({
title: 'html-webpack-plugin',
template: './public/index.html',
}),
new DefinePlugin({BASE_URL: '"./"'})
]
// 未来 webpack 定义常量时,会间接 const BASE_URL = ./ , 会有语法错误,须要写成 const BASE_URL = '"./"'
2.Babel 应用
a. 命令行中应用 babel
为什么须要 Babel?
JSX TS ES6+ ---> 浏览器平台间接应用(配合.browserslistrc 条件)
转换
Babel 相似于 postcss,本身没有性能,只是为了转换提供平台
解决 JS 兼容
罕用工具包:
转换箭头函数:@babel/plugin-transform-arrow-functions
转换变量申明:@babel/plugin-transform-block-scoping
蕴含多种转换:@babel/preset-env
装置 babel 相干包:
yarn -D add @babel/core // 转换 js 的外围包(微内核),如果须要在转换过程中批改代码,该须要配合其它插件
yarn -D add @babel/cli // 为了能在命令行中间接应用 babel
命令行中应用 babel:
npx babel src --out-dir build
// 文件或目录(编译该目录下所有 js)输入门路
转换箭头函数:
// 装置依赖包 yarn -D add @babel/plugin-transform-arrow-functions
// 命令行中应用 npx babel src --out-dir build --plugins=@babel/plugin-transform-arrow-functions
转换变量申明形式(let、const ==> var):
// 装置依赖包 yarn -D add @babel/plugin-transform-block-scoping
// 命令行中应用 npx babel src --out-dir build --plugins=@babel/plugin-transform-arrow-functions,@babel/plugin-transform-block-scoping
应用预设依赖包(蕴含了较多新语法的转换形式):
// 装置依赖包 yarn -D add @babel/preset-env
// 命令行中应用 npx babel src --out-dir build --presets=@babel/preset-env
b. 在 webpack 中配置 babel
能够在 webpack 配置文件中,或.browserslistrc 文件配置浏览器筛选条件
装置 babel-loader
yarn -D add babel-loader
配置解决 js 文件:
{
test: /\.js$/,
use: [
{
loader: 'babel-loader',
options: {
// 应用单个工具包聚合
// plugins:[
// '@babel/plugin-transform-arrow-functions',
// '@babel/plugin-transform-block-scoping'
// ]
// 应用 babel 预设工具包
presets: ['@babel/preset-env']
// presets: [
// [
// '@babel/preset-env',
// {targets: 'chrome 91'}
// ]
// ]
}
}
],
}
应用 babel.config.js 配置文件:
module.exports = {presets: ['@babel/preset-env']
}
/**
* babel-loader 相干配置文件
* babel.config.js(json cjs mjs) 当初是多包格调,倡议应用
* bebelrc.json(js) babel 7.x 之前应用的较多
*
*/
应用配置文件后配置 babel-loader 时:
{
test: /\.js$/,
use: ['babel-loader'],
}
3.polyfill 的应用
性能:
polyfill 是什么?履行打补丁的操作
旧浏览器提供它没有原生反对的较新的性能。用原生 js 实现的新的语法、新的接口、新的性能的代码块。
简述:
装置依赖:
yarn add core-js regenerator-runtime
在 main.js 中引入依赖:
import 'core-js/stable';
import 'regenerator-runtime/runtime';
应用 polyfill 后的 babel-loader 的配置:
{
test: /\.js$/,
exclude: /node_modules/, // 排除掉 node_modules 目录下的 js 文件,防止反复填充解决
use: ['babel-loader'],
}
应用 polyfill 后的 babel.config.js 的配置:
module.exports = {
// 并不能实现所有性能的转换
presets: [
[
'@babel/preset-env',
{
// false: 不对以后的的 JS 解决做 polyfill 的填充
// 'useage': 根据用户源代码中所应用到的新语法进行填充
// 'entry': 依据须要兼容的浏览器进行填充
useBuiltIns:'entry',
corejs:3 // 指定应用的外围 js 版本
}
],
]
}
4.copy-webpack-plugin 应用
性能:
局部资源文件不须要打包,只须要复制到指定目录之下
装置:
yarn -D add copy-webpack-plugin
应用 copy-webpack-plugin 插件时的配置:
const CopyWebpackPlugin = require('copy-webpack-plugin');
new CopyWebpackPlugin({
patterns: [
// {// from: path.resolve(__dirname, 'public/favicon.ico'),
// // to: path.resolve(__dirname, 'dist/favicon.ico'), // 拷贝到 dist 目录下,默认会主动拷贝到 output 目录下
// }
{
from:'public',
// to:'dist', 默认到 output 目录下
globOptions: {ignore: ['**/index.html'] // 疏忽掉该目录下的 index.html 文件
}
}
]
})
4.webpack-dev-server 应用
检测源代码变动,并从新打包:
// 打包时 增加 --watch 参数
"scripts": {"build": "webpack --watch"},
配置到 webpack.config.js 中检测变动:
module.exports = {
watch:true,
...
}
毛病:
/**
* 开发模式
* - watch: true 或者 webpack -- watch
* - live server
*
* 有余:
* 1. 批改后,所有源代码都会从新编译
* 2. 每次编译胜利之后都须要进行文件读写
* 3.live server 是 vscode 的插件
* 4. 不能实现部分更新
*
*
* 应用 webpack-dev-server
*/
应用 webpack-dev-server:
装置:
yarn add webpack-dev-server
应用打包并开启服务:js webpack serve
webpack-dev-middleware 应用,其外部应用了 webpack-dev-server:
流程:
装置
yarn -D add express wabpack-dev-middleware
express 开启本地服务器
middleware 将打包之后的后果,交给本地服务器
应用 middle, 配合 express:
const express = require('express');
const webpackDevMiddleware = require('webpack-dev-middleware');
const webpack = require('webpack');
const app = express();
// 获取配置文件
const config = require('./webpack.config.js');
const compiler = webpack(config);
app.use(webpackDevMiddleware(compiler,{publicPath: config.output.publicPath}));
// 开启端口上的服务
app.listen(3000, () => {console.log('Server is running on http://localhost:3000');
})
5.HMR 性能应用
模块热替换(hot module replacement),须要配合 webpack-dev-server 应用
开发阶段屏蔽掉.browerslistrc 的影响:
module.exports = {
mode: 'development',
devtool: false,
entry: './src/main.js',
output: {path: path.resolve(__dirname, 'dist'),
filename: 'bundle.js',
// publicPath: '/dist/',
},
target: 'web', // 开发阶段屏蔽.browserslistrc
devServer: {hot: true, // 开启 HMR 性能的}
}
开启 HMR 性能后,默认状况下,还是刷新整个页面,须要再代码中,手动设置:
import 'core-js/stable';
import 'regenerator-runtime/runtime';
import './title'
console.log('--main.js is running'); // 这里不会更新
if(module.hot){
// 判断是否开启热更新
module.hot.accept(['./title.js'],()=>{ // 填写须要热更新的文件
console.log('title.js 更新了');
});
}
6. 框架热更新实现
a.React_HMR
应用 @babel/preset-react 解析 jsx 文件
装置:
yarn add -D @babel/preset-react
// babel-loader 配置:{
test: /\.jsx?$/,
exclude: /node_modules/, // 排除掉 node_modules 目录下的 js 文件,防止反复填充解决
use: ['babel-loader'],
}
// babel.config.js 配置
module.exports = {
presets: [['@babel/preset-env'],
['@babel/preset-react'],
]
}
应用 @pmmmwh/react-refresh-webpack-plugin 与 react-refresh 实现 React 的 HMR:
装置:
yarn add -D @pmmmwh/react-refresh-webpack-plugin react-refresh
@pmmmwh/react-refresh-webpack-plugin // 该插件的性能是让 webpack 与 react-refresh 插件联合
react-refresh 实现 react 的部分组件更新
配置:
// webpack.config.js
const ReactRefreshWebpackPlugin = require('@pmmmwh/react-refresh-webpack-plugin')
module.exports = {
mode: 'development',
...
target: 'web', // 开发阶段屏蔽.browserslistrc
devServer: {hot: true,},
...
plugins: [
...
new ReactRefreshWebpackPlugin(),]
}
// 在 babel.config.js 中配置实现 react 的 HMR 的插件
module.exports = {
presets: [['@babel/preset-env'],
['@babel/preset-react'],
],
plugins: [['react-refresh/babel'],
]
}
b.Vue_HMR
装置 vue-template-compiler(2.6)、vue-loader(15)让起能编译 .vue (vue2)文件:
yarn add -D vue-template-compiler@2.6 vue@2.6 vue-loader@15
配置 vue-loader:
const VueLoderPlugin = require('vue-loader/lib/plugin'); // 在 15 版本之前则不须要引入 vue-loader 插件
module.exports = {
mode: 'development',
...
target: 'web', // 开发阶段屏蔽.browserslistrc
devServer: {hot: true,},
module: {
rules: [
...
{
test: /\.vue$/,
use: ['vue-loader']
}
]
},
plugins: [
...
new VueLoderPlugin()]
}
应用 vue-loader 后,vue 默认反对 hmr