【Webpack】模块打包工具 Webpack 的各种使用方式

编程知识 更新时间:2023-05-03 01:17:56

1. Webpack 简介

  • Webpack 是一个现代 JavaScript 的静态模块打包器(module bundler);
  • 那为什么要用这种构建工具进行打包呢?答:解决模块依赖和兼容性;
  • 打包器(构建工具)会将所有依赖关系按照规则合并为单个 JS 文件,一次加载;
  • 最终,生成浏览器能够使用的静态资源,下图为官方宣传效果图:

2. 安装 Webpack

  • 既然 Webpack 是 JavaScript 打包工具,那自然学前基础必然是 HTML5 和 ES6+;
  • 安装需要使用 npm(或 cnpm),需要去安装 Node.js,开发工具使用 Webstorm;
  • 找到官网下载 node.js,任意版本均可,下载安装,在命令行测试版本号:
>> node -v
  • 创建一个 Webstorm 项目,准备使用 npm 安装,可以先测试版本好:
>> npm -v
>> npm config get registry 										// 查看镜像,不是国内,设置淘宝镜像即可
>> npm config set registry https://registry.npm.taobao
  • 有时 npm 命令不太稳定,报错的话,可以使用 cnpm,语法一模一样;
>> npm install -g cnpm --registry=https://registry.npm.taobao
  • 安装好 npm 或 cnpm 后,测试 webpack 命令是否有效,如下:
>> webpack -v
  • 首先,先全局安装,需要两个:webpack 核心模块、webpack-cli 命令行工具;
  • 其中:install 可以简写为 i,-g 表示全局;
>> npm i webpack webpack-cli -g
  • 或者:在本地的项目中安装 webpack,–save-dev 可以简写为-D;
>> npm i webpack webpack-cli -D
  • 官方推荐使用本地安装,这样如果有多版本的话,不会导致冲突;
  • 而本地安装,就只能在本项目中使用 webpack 命令,并且需要 npx 命令。

3. 模块打包

  • 我们创建 02 目录,在其创建约定俗成的两个子目录 src 和 dist;
  • 其中:src 表示源文件,dist 表示生成发布的文件;
  • 在 src 中建立两个 js 文件,用 node 环境支持的 CommonJS 规范的模块化;
// module.js
module.exports = {
	'Mr.Lee'
};

// index.js
const name = require('./module.js').name;
console.log(name);
  • 建立 02.html 文件,引入 src 中的 index.js 文件,但浏览器是无法运行的;
  • 此时,我们需要进行打包来解决两个问题:浏览器兼容和导入导出 js 文件的合并;
  • 使用打包命令,注意目录的问题,如果在根目录带上子目录路径;
>> webpack ./02/src/index.js -o ./02/dist/bundle.js --mode=development
  • 只要打包入口文件即可,依赖的文件会自动合并;
  • development 表示开发模式,production 表示生产模式,压缩成一行;

4. 配置文件

  • 打包一次的命令太过于冗长,且特别容易出错,所以要对这些路径参数进行存储;
  • 我们可以创建 package.json 文件,来配置 scripts 属性来部署生成路径;
>> npm init -y 					// 生成配置文件命令
  • 然后在 scripts 属性里添加子属性:build,属性值具体如下:
"build" : "webpack ./02/src/index.js -o ./02/dist/bundle.js --mode=development"
  • 然后使用 npm 命令自动执行这个属性值的路径;
>> npm run build
  • 如果是比较简单的打包,package.json 还行,当参数越发复杂维护将变得困难;
  • Webpack 还提供了一个 webpack.config.json 配置文件,解决这个问题;
  • 由于我们是子目录 01,02 这种,完全可以直接存放子目录中即可;
  • 也就是说,配置文件不一定非要存放在根目录,可以根据自己目录结构进行调整;
/*
* webpack 构建时,会自动读取此文件
*/

// 获取当前路径
const path = require('path');
module.exports = {
	// 入口文件
	entry: './src/index.js',
	// 出口文件
	output: {
		// 文件名
		filename : 'bundle.js',
		// 路径,要绝对路径
		path : path.resolve(__dirname, './dist')
	},
	// 生成模式
	mode : "development"
};
  • 在哪个目录,就进入哪个目录,直接执行命名:webpack,即执行打包;

5. DevServer

问题需求

  • 由于代码可能有 CommonJS 等非浏览器支持的语法,每次都必须打包才行运行;
  • 虽然借助 Webstorm 等工具可以构建服务器环境,但实际上不能时时监控刷新;
  • IDE 提供的服务器之间访问的是打包后的文件,是否监听时时刷新看个人习惯;
  • 以上:如果要方便的话,开发者需求的想法是,开发时方便调试,最后再打包;
  • 所以,官方提供了 Webpack-dev-Server 工具来解决这个问题,支持特性:
    (1) 支持 HTTP 服务访问:localhost,127.0.0.1 这种;
    (2) 监听变化时时刷新网页,时时预览;
    (3) 支持 Source Map;

安装部署

  • DevServer 只要安装到本地即可使用,命令如下:
>> npm i webpack-dev-server -D

在应用根目录安装,package.json 会自动添加 webpack-dev-server 版本号;

  • 由于课件是按照 01,02 这样目录构建的,你自己测试完全可以在根目录下;
  • 当然,根目录和子目录在部分操作上可能有路径问题,自行调试几次;
  • 运行 DevServer 时,由于我们在 03 这个子目录中,所以,我们要进入:
>> cd 03
  • 在 webpack.config.js 配置一些最基本的参数,方便运行;
// devServer 自动化
devServer: {
	publicPath : '/dist', 			// 访问路径
	port : 3000, 					// 独立端口
	stats: 'minimal', 				// 迷你型服务启动信息
},
  • 本地我们可以删除 dist 目录,还原打包之前再启动 devServer,测试效果;
  • 此时我们可以发现并不需要打包到本地,它是自动打包到内存让你时时预览调试的;
  • 也就是说:调试阶段,可以用 devServer,完成了,再最终打包到本地即可;
  • 我们可以在子目录生成一个 package.json 文件,在 scripts 设置 dev 属性;
"dev" : "webpack-dev-server"
>> npm run dev
  • 目前这个版本,火狐还是会有断开服务器的提醒,不过完全不影响我们调试;
  • 如果强迫症的同学,有两种解决方案:
    (1) 注释掉输出的错误信息,或者把错误提醒改成信息提醒;
    (2) 或者在 devServer 设置错误级别:
clientLogLevel : 'none'

还有火狐还会出现 sockjs.js.map 的警告,可以设置 devTool 解决;

devtool: 'source-map',

以上问题,谷歌浏览器均不存在!

6. Plugin 部署 Html

问题需求

  • 目前为止,我们只能打包 js 文件模块,事实上:Html 文件也需要打包到一起;
  • 也就是说,我们需要把.js 和.html 文件都要打包到 dist 目录中去;
  • 那么 src 目录也应该存放相应的.html 文件,之前放在外面是方便测试;
  • 如果我们设定.html 名称为 index.html,放入 src,那如何连接.js 文件呢?
  • 预想,如果会打包到 dist,那么直接路劲:src=“bundle.js”;
  • 可以这样,调试的时候,路径又会产生问题?那这些问题,都直接交给插件处理吧!

安装部署

  • 首先,安装 html-webpack-plugin 插件,本地安装即可;
>> npm i html-webpack-plugin -D
  • 安装好后,可以在 package.json 中看到版本号;
  • 我们删除掉 src 外面的.html 文件,在 src 建立 index.html 文件,用于打包;
  • 我们并不需要在.html 文件中使用
// html 插件
const HtmlWebpackPlugin = require('html-webpack-plugin');

// 插件
plugins: [
	new HtmlWebpackPlugin({
		template: "./src/index.html", 		// 值为默认值,源文件
		filename: "index.html" 				// 值为默认值,打包生成的文件名
	})
],

// devServer,publicPath 可以忽略
devServer: {
	// publicPath : '/dist',
	port : 3000,
	stats : "minimal",
},
  • 经过上述的一系列操作,解决了两个问题,打包后引入.js 文件,会自动引入;
  • 在使用 DevServer 时,localhost:3000 直接访问的就是 index.html;
  • 如果想要.html 和.js 打包后存在不同目录,可设置,并会自动链接;
filename : 'js/bundle.js',
filename: "html/index.html"
<script src="../js/bundle.js"></script>
  • 打包后,上节课的 source map 生成了一个.map,这个在火狐刷新会引起弹窗;
  • 只要使用 inline-source-map,不生成文件,在最后生成一行文本即可;

7. Loader 打包 CSS

问题需求

  • 通过之前的学习,我们知道如何打包 js 模块和 html 页面,并融合;
  • 还有一种东西需要处理,就是 css 样式以及 less、sass 等预处理样式;
  • 思路也是一样的,调试的时候可以试试监听,打包的时候也能融合;
  • 这里需要使用 module 这个属性,并需要安装使用以下三种插件:
    (1) css-loader:读取和编译 css 文件,转换为样式字符模块;
    (2) style-loader:将 css 插入到 JavaScript 中;
    (3) less-loader:读取和编译 less 预处理样式,转换为 css 文件;

安装部署

  • 首先,我们先创建两个基本的 css 文件,另一个引入其中一个;
/* font.css */
h1 {
	color: blue;
	font-size: 200px;
}

/* base.css */
@import "font.css";
body {
	background-color: gray;
}
  • 和打包 html 文件一样,css 文件并不需要你手动去 link 引入,让插件处理;
  • 然后在.js 文件中,把.css 文件通过 require 引入进来;
require('./base.css');
  • 安装所需的 css-loader 插件和 style-loader 插件;
>> npm i css-loader -D
>> npm i style-loader -D
  • 安装完成后,可以在 package.json 检查版本号,确认已安装;
  • 在 webpack.config.js 中,使用 module 进行 css 文件部署工作;
// 模块
module: {
	// 规则
	rules: [
		{
			// 规则获取需要部署的文件后缀
			test: /\.css$/,
			// style-loader 将 css 字符串插入到 javascript
			// 通过浏览器工具样式被动态插入到<style>标签内
			// css-loader 将 css 文件编译成字符串给 style-loader 处理
			// 所以,这里数组的执行顺序是从右到左执行,否则失败;
			use : ['style-loader','css-loader']
		},
	]
},
  • 还有一种 css 编码方式是:预处理样式,比如 Less,sass 等;
  • 首先创建一个 less.less 预处理样式文件,代码 css 一样即可,然后引入;
require('./less.less');
  • 我们这里简单使用一下 Less 先做一个基础了解,先安装 less-loader;
>> npm i less-loader -D
{
	test: /\.less$/,
	// less-loader 会先将.less 文件转换为.css 文件,然后再向左边处理
	use : ['style-loader', 'css-loader', 'less-loader']
}

8. Loader 打包图片文件

打包思路

  • 我们继续打包文件:图片文件,分为 css 引入图片和 html 插入图片;
  • 如果是 css 加载图片,都是背景图,总所周知小图片采用 base64 转换字符串;
  • 而大图片和 html 插图图片,则都需要单独的 loader 插件来完成;
  • 本节课用到的 loader 插件如下:
    (1) file-loader:解析 JavaScipt 和 css 插入的图片;
    (2) url-loader:将图片转换为 base64 编码字符串;
    (3) html-loader:将.html 进行打包,从而解析 img 插入问题;

安装部署

  • 首先,先研究第一个插件:file-loader,安装并配置;
>> npm i file-loader -D
{
	test: /\.(png|jpg|gif)/,
	use : ['file-loader']
}
#loading {
	width: 780px;
	height: 422px;
	background-image: url("./loading.gif");
}
#ts {
	width: 609px;
	height: 609px;
	background-image: url("./ts.png");
}
  • 也可以在.js 文件引入图片,会被自动解析;
const img = require('./ts.png');
console.log(img);
  • 现在,我们要扩展这个插件内容,要求自定义目录和名称:
{
	test: /\.(png|jpg|gif)/,
	loader: 'file-loader', 				// 加载一个 loader
	options: {
		name : './img/[name].[ext]', 	// 写入 img 目录,且按原名和后缀,
	}
},
  • 第二个插件,我们限定小于 10kb 的,直接用 base64 编码保存图片;
  • 具体为何要用这么做:扩展要探讨很多,直接搜索相关关键字了解;
  • 总结就是一句话:小图片用 base64 性比价收益最高,反之一样;
>> npm i url-loader -D
{
	test: /\.(png|jpg|gif)$/,
	// 这里使用 url-loader,它依赖 file-loader
	// 通过先判断图片大小,小的采用 base64,大的采用 file-loader
	loader: 'url-loader',
	options: {
		limit : 10240, 					// 限定 10kg 一下采用 base64 编码,
		name : './img/[name].[ext]'
	}
},
  • 第三种,就是插入到 html 的图片,需要使用 html-loader 进行解析;
>> npm i html-loader -D
{
	test: /\.html$/,
	use : ['html-loader'] 				//自动交给 url-loader 处理
},

9. 分离 CSS 分类打包

  • 虽然之前我们使用 style-loader 和 css-loader 进行打包;
  • 但这种打包是融入到.js 里面最终生成的,并不是独立的.css 文件;
  • 之前使用了 html 插件进行.html 打包,这次使用 css 打包的插件为:
>> npm i mini-css-extract-plugin -D
// 获取 css 插件
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
// 插件
plugins: [
	new MiniCssExtractPlugin({
		filename : './css/[name].css',
	})
],
use : [
	{
		loader : MiniCssExtractPlugin.loader,
		options: {
			publicPath : '../'
		}
	},
	'css-loader'
]
  • 这样配置,路径就全部正确了。如果有强迫症,可以去掉./js 和./css 中的./;
  • 还有一种方式,就是直接使用 publicPath,加上 域名/img、域名/js、域名/css;
http://127.0.0.1/img/xxx.jpg 			// 绝对路径,一劳永逸
  • 使用 域名/img 这种模式,方便把 img,js,css 等静态资源部署到 cdn 上;
  • 也可以设置开发 src 和 dist 目录结构保持相同,这样更加清晰;

10. PostCss 兼容性转换

兼容处理

  • CSS 尤其是很多 CSS3,在部分浏览器是有兼容处理的,需要进行设置;
  • 可以使用 postcss-loader 来实现 CSS 语法的兼容性处理;
>> npm i postcss-loader -D
// 放在最右边
use : [
	...
	'postcss-loader'
]
  • 单有 postcss-loader 还不行,需要搭配创建 autoprefixer 插件转换;
>> npm i autoprefixer -D
  • 单有 postcss-loader 还不行,需要搭配创建 autoprefixer 插件转换;
  • 这个插件会在需要兼容性的样式加上 CSS 前缀,比如:-ms、-webkit 等;
  • 我们在 base.css 和 font.css(被@import 导入),增加需要兼容的 css;
display: flex;
transform: rotateY(130deg);
  • 在当前目录创建 postcss.config.js,用来配置兼容的浏览器;
const AutoPreFixer = require('autoprefixer');
module.exports = {
	plugins: [
		new AutoPreFixer({
			overrideBrowserslist : [
				'> 0.15% in CN' //可以写多个列表
			]
		})
	]
}
{ 		//由于采用了@import,被导入的 css 无法解析,需要设置 importLoaders=1 即可
	loader : 'css-loader',
	options: {
		importLoaders: 1
	}
}
  • 下图就是配置浏览器的语法,可以自行添加;

CSS4 代码

  • 除了兼容浏览器之外,还可以通过 postcss-preset-env 实现 CSS4 代码兼容;
>> npm i postcss-preset-env -D
:root: {
	--green : green;
};

h1 {
	color : var(--green);
}
// 请注意:如果使用 postcss-preset-env,就删除 autoprefixer
// 因为 post-preset-env 集成了 autoprefixer,不需要再引入设置

const PostPresetEnv= require('postcss-preset-env);
module.exports = {
	plugins: [
		new PostPresetEnv({
			browsers : [
				'> 0.15% in CN'
			]
		}),
	]
}

11. Babel 转换 ES6 语法

  • 我们有时需要将 ES6+的语法转换成 ES5,让兼容性更好一些;
  • 这时需要有三个模块需要安装,具体如下:
    (1) babel-loader:与 Webpack 协同工作的模块,加载处理 js 文件;
    (2) @babel/core:Babel 编译器的核心模块,是 babel-loader 依赖;
    (3) @babel/preset-env:Babel 预置器,用于分析 ES6 语法;
  • 我们安装上述三个模块,然后进行配置,具体方法如下:
>> npm i babel-loader @babel/core @babel/preset-env -D
{
	test : /\.js$/,
	loader: 'babel-loader',
	options: {
		presets : [
			'@babel/preset-env'
		]
	}
}
  • 我们在 src 中的 js 文件,使用 ES6 的箭头函数来尝试一下;
let fn = (x, y) => x + y;
console.log(fn(10, 20));
  • 在没有使用 Babel 时,它打包会原封不动的使用 ES6 语法;
  • 在使用 Babel 之后,编译后的代码如下:
var fn = function fn(x, y) {
	return x + y;
};
console.log(fn(10, 20));
  • 如果你使用了未纳入标准(提案中)的代码,打包时,它会提醒你安装相关插件;
// 提案中,尚未纳入标准的语法
class Person {
	#name;
	constructor() {
		this.#name = 'Mr.Lee';
	}
}
>> npm i @babel/plugin-proposal-class-properties -D
options: {
	presets : [
		'@babel/preset-env'
	],
	plugins : [
		'@babel/plugin-proposal-class-properties'
	]
}

12. ESLint 校验 JS 代码

  • 基本的 ESLint 实现,需要一下安装以下模块:
    (1) eslint:JS 代码检查工具核心模块;
    (2) eslint-loader:webpack 协同模块;
  • 首先,先安装 eslint,然后安装配置信息;
>> npm i eslint -D 				// 安装 eslint
>> eslint --init 					// 安装配置信息
  • 期间会让你选择配置信息情况,根据你实际情况选择即可,生成:.eslintrc.json;
  • 网上也会别人生成的配置信息可以拿来用,也可以去官网 eslint/demo 生成信息;
  • 再次,我们安装 eslint-loader 模块;
>> npm i eslint-loader -D
  • 最后,我们来配置 webpack.config.js;
{
	test : /.js$/,
	loader: 'eslint-loader',
	// 编译前执行
	enforce: 'pre',
	// 不检查的目录
	exclude: /node_modules/
},
  • 防止错误飘红太多,干扰演示,我们注释掉大部分代码,写上示例;
var foo = bar;
  • 测试打包和预览提示校验;

13. 多页面配置打包

  • 如果我们想生成多个.html 文件,比如 index.html 和 main.html;
  • 此时,我们需要修改一下入口文件和出口文件;
// 入口文件
entry: {
	// 把需要加载的 js 以键值对方
	index : './src/js/index.js',
	main : './src/js/main.js'
},// 入口文件,也支持 ES6 的箭头函数
entry: () => ({
	index : './src/js/index.js',
	main : './src/js/main.js'
}),
  • 出口文件,需要按照入口文件的名称进行打包,否则只会打包一个;
// 出口文件
output: {
	// 文件名
	filename : 'js/[name].js',
}),
  • 最后,我们要使用 HtmlWebpackPlugin 插件来设置自己想要的打包方案;
// 插件
plugins: [
	new HtmlWebpackPlugin({
		template: "./src/index.html", 			// 默认值
		filename: "index.html", 				// 默认值
		chunks: ['index', 'main']
	}),
	new HtmlWebpackPlugin({
		template: "./src/main.html",
		filename: "main.html",
		chunks: ['main']
	}),
],

14. 压缩 Html 和 Css 代码

  • 为何要压缩代码?什么情况下要压缩?答:在生产环境下打包时节约资源;
  • 既然在生产环境,那首先要把打包的配置更改为生产环境;
// 生成模式
mode : "production",
  • 调节为生产环境打包,就会自动将 js 代码进行打包,不需要单独设置;
  • 对于 Html 文件打包,通过 HtmlWebpackPlugin 插件,生成环境会自动压缩;
  • 如果在开发环境中压缩,可以通过配置来设置要压缩的选项:
minify: {
	collapseWhitespace: true, 		// 是否去除空格,默认 false
	removeComments: true, 			// 是否移除注释 默认 false
},
  • 对于 CSS 文件,就算设置了生成环境,它也不会自动压缩,此时需要另外设置;
>> npm i optimize-css-assets-webpack-plugin -D
// 获取 css 压缩插件
const OptimizeCssAssetsWebpackPlugin = require('optimize-css-assets-webpack-plugin')
// 插件
plugins: [
	new OptimizeCssAssetsWebpackPlugin(), 			// 压缩 css
],

15. 打包 Ts 和 Scss

Scss

  • 和 Less 一样,Scss 也是 Sass 的一种使用较多的语法;
>> cnpm install sass sass-loader node-sass -D
  • 由于这次我备课时,npm 连不上,故改成 cnpm;
  • 具体配置基本和 Less 一样,先创建.scss 文件,并引入;
{
	test: /\.scss$/,
	// 从右向左执行
	use : [
		MiniCssExtractPlugin.loader,
		'css-loader',
		'sass-loader'
	]
},

TypeScript

  • 越来越流行的 TypeScript,JavaScript 的一个超集;
>> cnpm i typescript ts-loader -D
{
	test: /\.ts$/,
	use : 'ts-loader',
},
  • 编写一个.ts 文件,然后通过 import 导入到 index.js;
// type.ts
export const output = (content : string) => {
	return content
}

// import ts
import { output } from './type.ts'
console.log(output('Mr.Lee'))
  • 如果要省略掉 import 中文件后缀,需要配置;
module.exports = {
	resolve: {
		extensions: ['.ts', '.js']
	},
}
  • 需要创建 tsconfig.json 文件;

16. Resolve 模块解析

  • 上节我们使用了 typescript,在 import 不限定后缀会出现无法载入;
  • 所以,我们使用了 Resolve 模块解析的中 extensions 来进行配置;
// 模块解析
resolve: {
	// 导入文件查找的限定后缀,默认.js 和.json
	extensions: ['.ts', '.js', '.json' ]
},
  • 导入语句是如果检测不到指定的会报错;
  • alias 配置可以用别名的方式,将导入路径映射成一个新的路径;
// 设置一个别名路径(绝对路径)
alias: {
	css : path.resolve(__dirname, './src/css')
}
require('css/base.css');
  • modules 配置可以指定 webpack 的解析模块目录;
// 找到解析模块目录,如果当前找不到就不断往上一层找
modules: ['node_modules']

// 也可以设置指定目录直接查找,检查查找次数
modules: [path.resolve(__dirname, '../node_modules')]
  • 自然,也可以设置第二参数,防止第一参数找不到报错;

17. Source-Map 配置

  • Source-map 可以将编译、打包、压缩后的代码映射到源代码上;
  • 比如你打包或运行的代码是编译后的,报错后,它能指向你源代码的位置上;
// 会生成一个.map 文件
devtool: 'source-map',
  • 根据不同的方式,有下面几种类型:
source-map 				// 打包后会生成一个对应的.map 文件
inline-source-map 		// 打包后会在 js 文件的内部最后生成 map 内容
eval-source-map 		// 打包后会在每个模块都执行 eval
hidden-source-map 		// 打包后会生成.map 文件但不会追踪原始文件的错误代码
cheap-source-map 		// 打包后会生成.map 并只能精确到行
  • 以上打包还可以合并比如 eval-cheap-source-map
  • 在开发环境和生产环境,我们该如何选择?开发要求速度快,调试方便推荐:
eval-source-map 或 eval-cheap-source-map 		// 开发环境
source-map 										// 生产环境

18. watch 监听和 clean 清理

watch 监听

  • 每次打包,都比较烦,耗时耗力,有一种解决方案:watch 文件监听;
  • 这种解决方案,就是你打包时,就挂着监听你原始文件的变化,从而自动更新;
// 文件监听,默认 false
watch: true,

// 开启 watch,下面才有意义
watchOptions: {
	// 不监听解析模块目录
	ignored: /node_modules/,
	// 防止更新频率太快,默认 300 毫秒,意味监听到变化后 500 毫秒再编译
	aggregateTimeout: 500,
	// 轮询间隔时间,1 秒,询问系统指定文件是否变化了
	poll: 1000
},

clean 清理

  • 每次打包,都要手动删除,因为不删除的话,改了配置目录就会多出废目录或文件;
  • 所以,使用 clean-webpack-plugin 插件,来处理这个问题;
>> npm i clean-webpack-plugin -D
// 获取 clean 清理插件
const { CleanWebpackPlugin } = require('clean-webpack-plugin')
// 插件
plugins: [
	new CleanWebpackPlugin()
]

19. HMR 热替换

  • 首先,页面调试有一个问题,就是当我们编辑了 css 或 js,它会自动刷新;
  • 但如果有大量的 css 或 js,一个小修改,就要全部刷新,影响开发性能;
  • 而 HMR 热替换就是解决这个问题,当 css 或 js 修改时,只刷新修改的部分;
  • 对于 html 文件,不需要热替换,就一个文件;
  • 开启 HMR 热替换,可以在启动服务时加上–hot,或者在 devServer 配置;
devServer: {
	hot : true
},
  • 对于 css 的热替换,需要使用 style-loader ,而现在被抽离 css 插件替换了;
  • 所以,我们先要注释掉这个插件,改为 style-loader ;
test: /\.scss$/,

//从右向左执行
use : [
	// MiniCssExtractPlugin.loader,
	'style-loader',
	'css-loader',
	'sass-loader'
]
  • 当开启了 HMR 热替换之后,发现 html 文件修改后无法自动更新了;
  • 此时,我们需要在入口文件加入这个 html 文件,即可;
entry: [
	'./src/js/index.js',
	'./src/index.html'
],
  • 对于 js 的热替换,只要在入口文件,对加载的其它 js 文件进行设置即可;
import name from './module'
console.log(name)
if (module.hot) {
	module.hot.accept('./module', () => {
		console.log(name)
	})
}

20. Axios 跨域请求

  • 这里提供两个远程 json 文件,会返回一些数据用于测试跨域问题;
    https://cdn.liyanhui/data.json (可跨域,设置过)
    https://cdn.ycku/data.json (不可跨域,默认)
  • 安装 axios,用于 ajax 测试;
>> npm install axios
  • 编写代码,测试数据;
import axios from 'axios'
axios.get('https://cdn.liyanhui/data.json').then(res => {
	console.log(res.data)
})
  • 如果把地址中的 liyanhui 换成 ycku 的话,会出现跨域的问题;
  • 通过 devServer 设置代理模式,来解决跨域问题;
devServer: {
	// 设置代理
	proxy : {
		// 匹配前缀为/api
		'/api' : {
			// 目标域名 ip
			target : 'https://cdn.ycku',
			// 改变源
			changeOrigin : true,
			// 重写 url, 去掉 /api
			pathRewrite : {
				'^/api' : ''
			}
		}
	}
},
axios.get('/api/data.json').then(res => { ...

21. 环境分离设置

  • 当配置文件写的越发繁杂时,发现生产环境的配置和开发环境配置有冲突;
  • 此时,我们希望有两套配置文件,一套用于开发环境,一套用于生产环境;
  • 这里使用 js 合并插件 webpack-merge 来实现配置文件的分离保存;
  • 我们创建另外两个 dev.config.js(开发) 和 prod.config.js(生产) ;
  • 将原先的 webpack.config.js 改为 base.config.js ,然后分离代码;
>> npm i webpack-merge -D
// 合并 js 插件
const {merge} = require('webpack-merge')
// 基础配置
const base = require('./base.config')
// 开发环境配置
module.exports = merge(base, {
	....
}
  • 分离好了之后,我们需要修改 package.json,把默认的配置启动和打包更改了;
"dev": "webpack-dev-server --config dev.config.js",
"build" : "webpack --config prod.config.js"
  • 打包命名更改为 npm run build 即可;其它不变;

22. 打包优化和 dist 服务

打包优化

  • webpack 提供了一个选项:optimiztion 来帮助我们优化;
  • 只不过开启了生产环境,就自动开启了压缩,除了 css 需要我们自己弄;
  • 我们使用自带的 Terser-webpack-plugin 插件来设置自己的压缩选项;
// 打包优化插件
const TerserWebpackPlugin = require('terser-webpack-plugin')
// 优化
optimization : {
	// 如果是生成模式,自动为 true
	// minimize : true,
	// 配置 TW 插件
	minimizer : [new TerserWebpackPlugin({
		// 是否开启缓存,开启缓存加速
		cache : false,
		// 插件选项
		terserOptions : {
			// 压缩方式
			compress : {
				// 剔除无用代码
				unused : true,
				// 剔除死代码
				dead_code : true,
				// 剔除 console.log
				drop_console : true,
				// 剔除 debugger
				drop_debugger : true,
			}
		}
	})]
},

dist 服务

  • 打包后,我们想要在静态服务器上测试,先要安装静态服务器;
>> npm i serve -g 						// 安装
>> serve dist -s 						// 运行 dist 目录

更多推荐

【Webpack】模块打包工具 Webpack 的各种使用方式

本文发布于:2023-04-29 20:20:00,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/095108e6e08ce18cf7a80246d9af2a10.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:模块   方式   工具   Webpack

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!

  • 112073文章数
  • 28529阅读数
  • 0评论数