常用配置说明
-
entry
- 可以接受字符串,数组,对象等多种格式
- 项目打包入口文件,可以是绝对路径也可以是相对路径
- webpack 打包默认入口文件是 ./src/index.js 约定,默认输出是 项目根目录下 /dist/main.js
-
output 打包后的内容输出相关配置,path打包后文件路径, 只能使用绝对路径
-
常用loader相关理解
- 默认情况下,webpack 值支持.js,.json文件,通过 loader,可以让他解析其他类型的文件(.css, .less, .ts, .vue ....),充当翻译官的角色。理论上只要有响应的 loader,就可以处理任何文件。一个 loader 只干一件事,webpack 的约定
- 同一后缀文件使用多个 loader 时,loader 有执行顺序,从右向左依次执行
- css-loader只是把 css 代码打包进 js 文件而已,并不做任何操作
- style-loader 提取css-loader打包后的css代码,并自动生成标签,然后插入 html 中
- less-loader 只是把 less 语法编译为 css 语法,然后 css-loader 把编译好的 css 内容插入 js 文件中,最后 style-loader 把 css 添加到标签并动态插入到 html 文件标签中
- postcss-loader使用顺序,放在能够拿到 css 内容的地方就可以,拿到 css 内容,通过一些 js 插件处理 css 达到增强 css 的效果
-
loader 和 plugin 区别:loader 的主要职责是让 webpack 认识更多的文件类型,而 plugin 的职责是让其可以控制构建流程,从而执行一些特殊的任务。相当于 webpack 的功能补充。
hash,chunkhash,contenthash
如果不指定 hash 类型,webpack 默认是用 hash。
文件使用 hash 名的目的是为了利用浏览器的缓存,当我们做下次功能迭代的时候,只修改某一个文件的时候,hash 发生变化, 但是其他文件没有变化,hash 不变则会走缓存,变化的就会重新请求,这样可以减少请求
- hash 是随整个工程内容的变化而变化
- chunkhash 只影响一个 chunk 下的模块,一个文件所依赖的代码块会打包进一个 chunk
- contenthash 只根据自身的内容变化 而变化, 但是如果 contenthash 发生变化,他所属的 chunkhash 也会变化
项目目录结构
.
|-- src 项目源代码
|-- components 项目通用组件
|-- pages 项目功能模块
|-- index.js 项目入口文件
|-- static 项目静态资源,图片,字体文件
|-- webpack webpack 打包相关的配置
|-- config.js 通用配置变量抽离
|-- webpack.config.common.js webpack 公共配置
|-- webpack.config.dev.js 本地开发环境打包配置
|-- webpack.config.production.js 正式环境打包配置
|-- config.js
|-- index.html 打包模板
|-- .babelrc babel 相关配置文件
|-- postcss.config.js postcss 相关配置文件
|-- .npmrc npm 安装源设置
|-- package.json
完整的项目打包方案
webpack.config.common.js
const path = require('path');
const { CleanWebpackPlugin } = require("clean-webpack-plugin");
const HtmlWebpackPlugin = require("html-webpack-plugin");
const webpack = require("webpack");
module.exports = {
entry: {
index: './src/pages/index.js',
},
resolve: {
// 项目路径别名
alias: {
Utils: path.resolve(__dirname, "../src/utils"),
Components: path.resolve(__dirname, "../src/components"),
},
},
performance: {
// false | "error" | "warning" // 不显示性能提示 | 以错误形式提示 | 以警告...
hints: false,
// 开发环境设置较大防止警告
// 根据入口起点的最大体积,控制webpack何时生成性能提示,整数类型,以字节为单位
maxEntrypointSize: 5000000,
// 最大单个资源体积,默认250000 (bytes)
maxAssetSize: 3000000,
},
module: {
rules: [
{
test: /\.(js|jsx)$/,
use: 'babel-loader',
include: path.resolve(__dirname, "../src"),
exclude: /node_modules/,
},
]
},
plugins: [
new CleanWebpackPlugin(), // 每次打包前先清除之前的打包内容
new HtmlWebpackPlugin({
template: "./index.html", // 打包 html 模板
filename: "index.html", // 打包后生成的文件名
}),
new webpack.DefinePlugin({ // 自定义项目环境变量,此处用于二级目录部署
"process.env": {
SECONDARY_PATH: JSON.stringify(process.env.SECONDARY_PATH),
},
}),
]
}
webpack.config.dev.js
const path = require("path");
const config = require("./config");
const webpack = require("webpack");
const { merge } = require("webpack-merge");
const common = require("./webpack.config.common.js");
module.exports = merge(common, {
mode: "development",
output: {
path: path.resolve(__dirname, "dist"),
filename: "[name]-[hash:6].js",
publicPath: config.publicPath,
chunkFilename: "[name].[chunkhash:4].chunk.js",
},
devServer: {
port: 8089,
host: "0.0.0.0",
hot: true, // css 修改热更新,js 热更新需要配合 hotOnly和webpack.HotModuleReplacementPlugin()
compress: true,
// 当使用 HTML5 History API 时, 所有的 404 请求都会响应 index.html 的内容。 将 devServer.historyApiFallback 设为 true开启:
historyApiFallback: true,
hotOnly: true, // 即便HMR不⽣效,浏览器也不⾃动刷新,就开启hotOnly
/* proxy: { // 每个 key 都是需要转发的前缀
"/dataassets/api": {
target: "后端接口服务地址",
},
}, */
proxy: [
// 多个前缀代理到同一个后端服务写法
{
context: ["/dataassets/api", "/sso"],
target: "后端接口服务地址",
},
]
},
devtool: "inline-source-map", // 开发环境配置
module: {
rules: [
{
test: /\.(less|css)$/,
use: [
"style-loader",
"css-loader",
{
loader: "less-loader",
options: {
// less@3
javascriptEnabled: true,
// 覆盖antd样式的全局变量
modifyVars: config.modifyVars,
globalVars: {
imgUri: `~"${config.publicPath}"`,
},
},
},
],
},
{
test: /\.(jpe?g|png|gif|svg)$/i,
use: [
"file-loader?hash=sha512&digest=hex&name=[hash].[ext]",
],
},
{
test: /\.woff(2)?(\?v=[0-9]\.[0-9]\.[0-9])?$/,
use: "url-loader?limit=10000&mimetype=application/font-woff",
},
{
test: /\.(ttf|eot)(\?v=[0-9]\.[0-9]\.[0-9])?$/,
use: "file-loader",
},
],
},
plugins: [new webpack.HotModuleReplacementPlugin()],
});
webpack.config.production.js
const path = require("path");
const MiniCssExtractPlugin = require("mini-css-extract-plugin");
const CopyWebpackPlugin = require("copy-webpack-plugin");
const { merge } = require("webpack-merge");
const config = require("./config");
const common = require("./webpack.config.common.js");
module.exports = merge(common, {
mode: "production",
output: {
path: path.resolve(__dirname, "../dist"),
publicPath: config.publicPath, // 项目打包后的 css,js 都会添加统一访问路径前缀
filename: "js/[name].[hash:6].js",
chunkFilename: "js/[name].[hash:6].chunk.js",
},
module: {
rules: [
{
test: /\.(less|css)$/,
use: [
{
// MiniCssExtractPlugin 既有插件的配置也有 loader 的配置,具体配置项参考 github 文档
// https://github.com/webpack-contrib/mini-css-extract-plugin
loader: MiniCssExtractPlugin.loader,
options: {
publicPath: config.publicPath, // 配置打包后访问 css 文件的路径前缀。
},
},
"css-loader",
"postcss-loader",
{
loader: "less-loader",
options: {
// less@3
javascriptEnabled: true,
// 覆盖antd样式的全局变量
modifyVars: config.modifyVars,
globalVars: {
imgUri: `~"${config.publicPath}"`, // 用于设置样式文件里引入的 image 图片地址前缀
},
},
},
],
},
{
test: /\.(jpe?g|png|gif|svg)$/i,
use: [
{
loader: 'file-loader',
options: {
name: "[name]-[contenthash:6].[ext]",
limit: 2 * 1024, // 小于2k的图片,直接使用Base64编码进行处理
publicPath: config.publicPath
}
}
],
},
{
test: /\.woff(2)?(\?v=[0-9]\.[0-9]\.[0-9])?$/,
use: [
{
loader: 'url-loader',
options: {
publicPath: config.publicPath
}
}
]
},
{
test: /\.(ttf|eot)(\?v=[0-9]\.[0-9]\.[0-9])?$/,
use: [
{
loader: 'file-loader',
options: {
publicPath: config.publicPath
}
}
]
},
],
},
plugins: [
new MiniCssExtractPlugin({
filename: "css/[contenthash:6]-[name].css",
}),
new CopyWebpackPlugin([
{
from: path.resolve(__dirname, "../static"),
to: path.resolve(__dirname, "../dist/static"),
},
]),
],
});
常见问题FAQ
- 免费下载或者VIP会员专享资源能否直接商用?
- 本站所有资源版权均属于原作者所有,这里所提供资源均只能用于参考学习用,请勿直接商用。若由于商用引起版权纠纷,一切责任均由使用者承担。更多说明请参考 VIP介绍。
- 提示下载完但解压或打开不了?
- 找不到素材资源介绍文章里的示例图片?
- 模板不会安装或需要功能定制以及二次开发?
发表评论
还没有评论,快来抢沙发吧!