一.webpack学习
- webpack核心概念
mode: 模式
entry:入口模块文件路径
output:输出bundle文件路径
module:模块,webpack构建对象
bundle:输出文件,webpac构建产物
chunk:中间文件,webpack构建的中间产物
loader:文件转换器(例如转换.vue文件)
plugin:插件,执行特定任务
2.quick start
1.npm init 初始化项目
2.创建src/index.js
3.创建publish/index.html
4.创建webpack.config.js,并填入配置
5.安装webpack webpack-cli
6.npm配置build命令
7.执行npm run build 完成打包构建
3.source-map分析
mode:development devtool:none 不会单独生存source-map 映射文件都会在bundle.js里面
浏览器会自动解析
# JavaScript Source Map 详解 4.loader
//config loader运行顺序从右到左 从下到上
module:{
rules: [
{
test: /\.css$/,
use:['style-loader','css-loader']
},
{
test: /\.test$/,
use;[path.resolve(__dirname,'./xxx/xxx-xxx.js')]
}
]
}
//my-loader.js
module.exports = (source) => {
let newSource = source
//do something
return newSource
}
5.plugins
//config 也有执行顺序,不过一般都会写在执行的生命周期触发
plugins: [new XXXXPlugins(options)]
// my-plugin.js
const pluginName = xxxx
class Myplugin {
constructor(options){}
apply(compiler) {
compiler.hooks.xxx.tap(pluginName,compilation => {
compilation.hooks.xxx.tap(pluginName,() => {
//do something
})
)
}
}
二.前端项目工程化改造
1.初始化webpack配置
// npm init -y
// cnpm i webpack webpack-cli style-loader css-loader -D
//配置webpack.config.js
2.配置多入口,多页面,处理图片,垫片,不同分别引入不通的js
//改造index 和login页面 需要配置多入口
entry: {
index: './src/index.js',
login: './src/login.js'
},
//处理图片
module: {
rules: [
{
test: /\.css$/,
use: ['style-loader', 'css-loader']
},
{
test: /\.(png|svg|jpg|jpeg|gif)$/i,
type: 'asset',
parser: {
dataUrlCondition: {
maxSize: 8 * 1024
}
},
generator: {
filename: 'images/[name].[hash:6][ext]'
}
}
]
},
//配置ProvidePlugin 垫片作用:自动加载,而不必模块import或require它们无处不在
new webpack.ProvidePlugin({
$: 'jquery',
jQuery: 'jquery'
})
//多页面多模版 引入不通的js需要用htmlWebpackPlugin的chunks
new htmlWebpackPlugin(
{
template: path.resolve(__dirname, './src/index.html'),
filename: 'index.html',
chunks: ['index']
}
),
new htmlWebpackPlugin(
{
template: path.resolve(__dirname, './src/login.html'),
filename: 'login.html',
chunks: ['login']
}
),
3.优化
//每次改动都要重新build 这里使用webpack-dev-server(只是在内存中储存打包好的文件,物理上dist目录不会生成,修改完然后还需要build)
//cnpm i webpack-dev-server -D
//由于html模版里的图片没有处理,直接把图片拷贝到dist目录
devServer: {
static: {
directory: path.join(__dirname, 'dist')
},
compress: true,
port: 9000,
hot: true
},
// cnpm i copy-webpack-plugin -D
new CopyWebpackPlugin({
patterns: [{
from: path.resolve(__dirname,'./src/img'),
to: path.resolve(__dirname,'./dist/img')
}]
})
//剥离css
//cnpm i min-css-extract-plugin -D
{
test: /\.css$/,
use: [MiniCssExtractPlugin.loader, 'css-loader']
},
new MiniCssExtractPlugin({
filename: 'css/[name].css',
chunkFilename: 'css/[name].chunk.css'
})
//压缩css js
//cnpm i css-minimizer-webpack-plugin uglifyjs-webpack-plugin
optimization: {
minimize: true,
minimizer: [
new UglifyJsPlugin({ sourceMap: true }),
new CssMinimizerPlugin()
]
},
//treeshaking
//1.解构引入
//2.只支持esmodule
//3.mode模式必须是production
//前提 splitChunks不处理业务代码里面的模块 不在node_modules下的同步包都打进index.js
//如果不配置splitChunks,会把所有同步包都打到index.js 异步包单独打成一个个单独的js
//配置splitChunks 只针对node_modules下
//先处理cacheGroups,然后再处理外面的chunks cacheGroups每个选项没设置都设置上面总的
- `chunks`选项,决定要提取那些模块。
- 默认是`async`:只提取异步加载的模块出来打包到一个文件中。
- 异步加载的模块:通过`import('xxx')`或`require(['xxx'],() =>{})`加载的模块。
- `initial`:提取同步加载和异步加载模块,如果xxx在项目中异步加载了,也同步加载了,那么xxx这个模块会被提取两次,分别打包到不同的文件中。
- 同步加载的模块:通过 `import xxx`或`require('xxx')`加载的模块。
- `all`:不管异步加载还是同步加载的模块都提取出来,打包到一个文件中。
- `minSize`选项:规定被提取的模块在压缩前的大小最小值,单位为字节,默认为30000,只有超过了30000字节才会被提取。
- `maxSize`选项:把提取出来的模块打包生成的文件大小不能超过maxSize值,如果超过了,要对其进行分割并打包生成新的文件。单位为字节,默认为0,表示不限制大小。
- `minChunks`选项:表示要被提取的模块最小被引用次数,引用次数超过或等于minChunks值,才能被提取。
- `maxAsyncRequests`选项:最大的按需(异步)加载次数,默认为 6。
- `maxInitialRequests`选项:打包后的入口文件加载时,还能同时加载js文件的数量(包括入口文件),默认为4。
- 先说一下优先级 `maxInitialRequests` / `maxAsyncRequests` <`maxSize` <`minSize`。
- `automaticNameDelimiter`选项:打包生成的js文件名的分割符,默认为`~`。
- `name`选项:打包生成js文件的名称。
- `cacheGroups`选项,核心重点,**配置提取模块的方案**。里面每一项代表一个提取模块的方案。下面是`cacheGroups`每项中特有的选项,其余选项和外面一致,若`cacheGroups`每项中有,就按配置的,没有就使用外面配置的。
- `test`选项:用来匹配要提取的模块的资源路径或名称。值是正则或函数。
- `priority`选项:方案的优先级,值越大表示提取模块时优先采用此方案。默认值为0。
- `reuseExistingChunk`选项:`true`/`false`。为`true`时,如果当前要提取的模块,在已经在打包生成的*js*文件中存在,则将重用该模块,而不是把当前要提取的模块打包生成新的*js*文件。
- `enforce`选项:`true`/`false`。为`true`时,忽略`minSize`,`minChunks`,`maxAsyncRequests`和`maxInitialRequests`外面配置选项。
splitChunks: {
minSize: 30 * 1024,
name: 'chunk',
chunks: 'all',
cacheGroups: {
jq: {
test: /jquery\.js/,
name: 'jq',
chunks: 'all'
},
flex: {
test: /flexslider\.js/,
name: 'flex',
chunks: 'all'
}
}
}
//使用ejs和clean
//cnpm i ejs-loader clean-webpack-plugin -D
三.前端项目工程化vue改造
1.移动webpack.config.js文件
//注意里面的配置的路径也要改变
//package.json里面加上 --config ./build/weback.config.js
2.初始化vue2改造
//1.创建main.js app.vue /public/index.html
//2.创建webpack.vue.config.js copy过来一份 修改
//3.安装vue@2.6.14 vue-loader@15.9.8 vue-template-compiler@2.6.14
//4.创建命令 start:vue build:vue
//注意启动webpack-dev-server UglifyJsPlugin不能用soureMap:true
3.首页和登录页移植
//1.安装vue-router^3.5.3
//2.按照vue修改组件
4.SPA改造成MPA
//1.创建webpack.vue.mpa.config.js copy过来一份 修改
//2.创建命令 start:vuempa build:vuempa
5.vue2升级成vue3
//1.安装最新的vue和vue-loader vuerouter
//2.按照vue3的语法修改项目