视频地址:https://www.bilibili.com/video/BV1YU4y1g745
webpack文档:https://webpack.docschina.org/concepts/
扩展
包括webpack和webpack cli两个软件包。
npm install webpack webpack-cli --global //全局安装
npm -init -y //初始化包配置文件
npm install webpack webpack-cli --save-dev //当前工作目录安装
Build,运行 webpack(默认命令,可用输出文件)。
--watch,监控文件内容改变,实时编译
Init,用于初始化一个新的 webpack 项目。
Loader,初始化一个 loader。
Plugin,初始化一个插件。
Info,输出你的系统信息。
Configtest,校验 webpack 配置。
Serve,运行 webpack 开发服务器。
Watch,运行 webpack 并且监听文件变化。
Flags,配置项调整
const path = require('path');
module.exports = {
/*入口文件配置*/
entry: './path/to/my/entry/file.js',
/*输出文件配置*/
output: {
path: path.resolve(__dirname, 'dist'), /*输出的目录*/
filename: 'my-first-webpack.bundle.js', /*输出为文件名*/
clean:true,/*是否清理后输出*/
},
/*loader,也称模块*/
module: {
rules: [{ test: /\.txt$/, use: 'raw-loader' }],
},
/*plugin*/
plugins: [
/*自动生成html文件的插件*/
new HtmlWebpackPlugin({
template: './src/index.html',/*模板文件路径*/
filename:"app.html",/*输出文件名*/
inject:"body" /*脚本注入位置*/
})
],
/*开发模式*/
mode:'none',
/*开发环境服务器先按照webpack-dev-server*/
devServer: {
open: true,/*是否启用*/
host: "localhost",/*绑定的地址*/
},
};
path模块说明:https://www.runoob.com/nodejs/nodejs-path-module.html
完整配置说明文档:https://webpack.docschina.org/configuration/
script
标签引入你所有 webpack 生成的 bundle。模块的配置说明:https://webpack.docschina.org/configuration/module/
资源模块说明:https://webpack.docschina.org/guides/asset-modules/#root
Rules属性的配置:https://webpack.docschina.org/configuration/module/#modulerules
资源模块(asset module)是一种模块类型,它允许使用资源文件(字体,图标等)而无需配置额外 loader。
asset/resource
发送一个单独的文件并导出 URL。之前通过使用 file-loader 实现。asset/inline
导出一个资源的 data URI。之前通过使用 url-loader 实现。asset/source
导出资源的源代码。之前通过使用 raw-loader 实现。url-loader
,并且配置资源体积限制实现。匹配到的引入的文件都将被发送到输出目录,并且其路径将被注入到输出文件 bundle.js 中。
默认情况下,asset/resource
模块以 [hash][ext][query]
文件名发送到输出目录。可以通过在 webpack 配置中设置 output.assetModuleFilename
来修改此模板字符串:
output: {
filename: 'main.js',
path: path.resolve(__dirname, 'dist'),
/* 自定义资源输出的文件名*/
assetModuleFilename: 'images/[hash][ext][query]'
},
module: {
/*创建模块时,匹配请求的规则数组。这些规则能够修改模块的创建方式。
这些规则能够对模块(module)应用 loader,或者修改解析器(parser)。*/
rules: [
/*rule,每个规则可以分为三部分 - 条件(condition),
结果(result)和嵌套规则(nested rule)。*/
{
/* test 属性,识别出哪些文件会被转换。*/
test: /\.png/,
type: 'asset/resource'
}
]
},
输出时支持的变量名如下(同output.filename):https://webpack.docschina.org/configuration/output/#outputfilename
css-loader:将css识别为模块;style-loader:将css放到页面上,less-loader:解析less;sass-loader:解析sass
module.exports = {
module: {
rules: [
{
test: /\.css$/i,
/* loader的加载顺序是从后往前 */
use: ["style-loader", "css-loader"],
},
],
},
};
miniCssExtractplugin,引入该插件后可使用MiniCssExtractPlugin.loader代替style-loader;合并引入的多个css模块到css文件;
module.exports = {
plugins: [
new MiniCssExtractPlugin({
/*类似于 webpackOptions.output 中的选项*/
/*所有选项都是可选的*/
/* 输出的文件路径、文件名*/
filename: '[name].css',
chunkFilename: '[id].css',
}),
],
}
CssMinimizerWebpackPlugin,优化和压缩 CSS。不同于其他插件,该插件在optimization配置项中使用
const MiniCssExtractPlugin = require("mini-css-extract-plugin");
const CssMinimizerPlugin = require("css-minimizer-webpack-plugin");
module.exports = {
module: {
rules: [
{
test: /.s?css$/,
use: [MiniCssExtractPlugin.loader, "css-loader", "sass-loader"],
},
],
},
optimization: {
minimizer: [
new CssMinimizerPlugin(),
],
},
plugins: [new MiniCssExtractPlugin()],
};
安装:https://webpack.docschina.org/loaders/babel-loader#root
npm install -D babel-loader @babel/core @babel/preset-env webpack
配置
module: {
rules: [
{
test: /\.m?js$/,
/* 排除指定目录下的文件 */
exclude: /(node_modules|bower_components)/,
use: {
loader: 'babel-loader',
options: {
presets: ['@babel/preset-env']
}
}
}
]
}
regeneratorRuntime报错解决办法:https://www.cnblogs.com/raind/p/9017817.html 、 @babel/plugin-transform-runtime
entry的配置:https://webpack.docschina.org/concepts/entry-points/#root
output的配置:https://webpack.docschina.org/concepts/output/
相关文档:https://webpack.docschina.org/guides/code-splitting/
普通多入口(缺点:会打包重复的代码,如引入的同一个库)
entry下的dependOn:当前入口所依赖的入口。它们必须在该入口被加载前被加载。
SplitChunksPlugin,最初,chunks(以及内部导入的模块)是通过内部 webpack 图谱中的父子关系关联的。CommonsChunkPlugin 曾被用来避免他们之间的重复依赖,但是不可能再做进一步的优化。从 webpack v4 开始,移除了 CommonsChunkPlugin,取而代之的是 optimization.splitChunks。
splitChunks.chunks,这表明将选择哪些 chunk 进行优化。当提供一个字符串,有效值为 all,async 和 initial。设置为 all 可能特别强大,因为这意味着 chunk 可以在异步和非异步 chunk 之间共享。
module.exports = {
//...
optimization: {
splitChunks: {
// include all types of chunks
chunks: 'all',
},
},
};
Es6的import方法动态导入(运行到导入语句时才进行导入),后 webpack会自动进行代码分离。
import("/main.js").then(({main}=>{}));
多页应用:https://zhuanlan.zhihu.com/p/109527475,多页面打包的原理就是:配置多个entry和多个HtmlWebpackPlugin
module.exports = {
optimization: {
splitChunks: {
cacheGroups: {
defaultVendors: {
test: /[\\/]node_modules[\\/]|vendor[\\/]analytics_provider|vendor[\\/]other_lib/,
},
},
},
},
};
此选项指定在浏览器中所引用的「此输出目录对应的公开 URL」。相对 URL(relative URL) 会被相对于 HTML 页面(或 <base>
标签)解析。
const path = require('path');
module.exports = {
output: {
path: path.resolve(__dirname, 'public/assets'),
publicPath: 'https://cdn.example.com/assets/',
},
};
生成环境下插件会按自身的功能进行运转,开发环境下有些插件不会进行相关处理;可在命令行内传入相关变量,替换配置项:
npx webpack --env production //生成环境构建
npx webpack --env development //开发环境构建
--env global=123 ,也可以传递键值对,在webpack-config.js中使用函数形式的配置形式,函数参数为传入的命令参数(配置项中使用这些变量,实现动态参数构建)。函数参数为一个对象,所有传入的参数为该对象的属性。
TerserWebpackPlugin ,该插件使用 terser 来压缩 JavaScript。
npm install terser-webpack-plugin --save-dev
const TerserPlugin = require("terser-webpack-plugin");
module.exports = {
optimization: {
minimize: true,
minimizer: [new TerserPlugin()],
},
};
externals配置项用于将某些 import 的包(package)打包到 bundle 中,而是在运行时(runtime)再去从外部获取这些扩展依赖(external dependencies)。
module.exports = {
externals: {
jquery: 'jQuery',
},
};
前提:代码分离(代码拆分)一般是指抽离共同的代码,动态导入是使用时才会动态加载JS,
相关文档:https://webpack.docschina.org/guides/code-splitting/#dynamic-imports
当涉及到动态代码拆分时,webpack 提供了两个类似的技术。第一种,也是推荐选择的方式是,使用符合 ECMAScript 提案 的 import()
语法 来实现动态导入。
和静态导入的区别在于一个是运行前加载,一个是运行时加载。
相关文档:https://webpack.docschina.org/guides/lazy-loading/#root
延迟加载(懒加载)或“按需”加载是优化站点或应用程序的好方法。这种做法本质上涉及在逻辑断点处拆分代码,然后在用户完成需要或将需要新代码块的操作后加载它。这加快了应用程序的初始加载速度并减轻了其整体重量,因为某些块甚至可能永远不会被加载。
相关文档:https://webpack.docschina.org/guides/code-splitting/#prefetchingpreloading-modules
link标签:https://developer.mozilla.org/zh-CN/docs/Web/HTML/Element/link
link预获取:https://developer.mozilla.org/zh-CN/docs/Web/HTML/Link_types/prefetch
<link rel="preload" href="style1.css" as="style">
<link rel="preload" href="main1.js" as="script">
import(/* webpackPrefetch: true */ './path/to/LoginModal.js');