初始化webpack项目
1. 在当前位置创建一个空目录 $ mkdir webpack-demo(目录名)
2. cd webpack-demo 目录,初始化一个package.json $ npm init
3. 安装'webpack'与'webpack-cli' $ npm install webpack webpack-cli -D
4. 创建入口js文件与html文件,$ npm touch index.html src/index.js
5. 创建webpack.config.js文件 $ touch webpack.config.js
npx 执行依赖包里的二进制文件, 在 npm version >= 5.2.0 开始,默认安装了npx
如:可以直接通过npx webpack命令执行编译打包,
不需要用到./node_modules/.bin/webpack -v
// webpack.config.js 是webpack自身定义的默认配置文件名,会覆盖webpack的默认配置项
// webpack默认只能识别JS模块,其他模块是不识别的, loader就是帮助webpack来识别并解析除了JS的其他模块的, loader的配置主要在module.rules中进行
//loader的主要作用 1.识别文件类型,确定具体处理该模块的loader (rule.test) 2.使用对应的loader, 对文件进行相关操作转换 (rule.use)
const path = require('path')
const HtmlWebpackPlugin = require('html-webpack-plugin')
/**1.为html文件中引入的外部资源每次更新后的hash,防止引用缓存的外部文件问题
* 2.可以生成创建html入口文件,比如单页面会生成一个html文件入口,如果配置多个html-webpack-plugin即可生成多个页面入口**/
const { CleanWebpackPlugin } = require('clean-webpack-plugin') // 清理dist文件夹
const MiniCssExtractPlugin = require('mini-css-extract-plugin') // 将分离css插件,用于生产环境, 若开发环境用的话,就无法样式模块热更新
module.exports = {
entry: {
main: './src/index.js' //入口文件
},
output: { // 输出文件配置
filename: 'bundle.js', // 输出文件名
path: path.resolve(__dirname, 'dist') // output的path需要绝对路径,使用node.js的path模块来解析为绝对路径
},
mode: "development",
devServer: {
contentBase: './dist', // 启动的目录
open: false, // 自动打开浏览器
proxy: { // 设置代理,解决跨域请求问题
"/api": {
target: "http://127.0.0.1:5500"
}
},
port: 8088, // 指定端口号
hot: true, // 开启HMR(Hot Module Replacement) 热模块替换,由于是webpack自带的,所以要引入webpack, 监控并更新js模块的工作vue等框架自己做了,否则需要自己拖动监控
// hotOnly: true 在某些模块不支持热更新的情况下,不会刷新页面,只在控制台输出热更新失败
before(app, server, compiler) { // 当html发生改变时,重新加载页面
const watchFiles = ['.html'];
compiler.hooks.done.tap('done', () => {
const changedFiles = Object.keys(compiler.watchFileSystem.watcher.mtimes);
if (
this.hot &&
changedFiles.some(filePath => watchFiles.includes(path.parse(filePath).ext))
) {
server.sockWrite(server.sockets, 'content-changed');
}
})
}
},
// 非js模块的配置
module: {
rules: [
{
test: /\.(jpe?g|png|git)$/,
use: {
loader: "url-loader",
options: {
name: "[name]-[hash:7].[ext]", // []表示占位符(placeholder),name表示源文件的名字,ext是源文件的后缀,还可以连接hash: [name]-[hash].[ext]
outputPath: "images", // 输出的图片文件夹
limit: 10000 // 限制当图片小于10000以下,将图片转化为base64
}
}
},
{
test: /\.css$/,
use: [
// 执行顺序:由下至上,由右至左
'style-loader', // 把合并后的css直接放在页面的style样式上
// {
// loader: MiniCssExtractPlugin.loader
// }, // 将css分离出来
'css-loader' // 合并css
]
},
{
test: /\.scss$/,
use: [
'style-loader',
// {
// loader: MiniCssExtractPlugin.loader
// }, // 将css分离出来
'css-loader',
'sass-loader', // 将sass转化为css,依赖node-sass模块(npm i sass-loader node-sass -D)
'postcss-loader' // 自动添加需要前缀的样式, 还需安装autoprefixer依赖包
]
}
]
},
// plugins,是用于扩展webpack的功能,本身是一个类,通过在构造函数中传入不同参数实现不同功能, 数组里面的项即是插件的实例
plugins: [
// 执行顺序由上至下
new CleanWebpackPlugin({
cleanOnceBeforeBuildPatterns: [path.join(__dirname, "dist")]
}),
new HtmlWebpackPlugin({ // 自动生成html并打包至输出的目录中
title: 'html模板',
filename: 'index.html',
template: "./index.html"
}),
new MiniCssExtractPlugin({ // 将css分离出来
filename: '[name].css', // 输出文件名
chunkFilename: '[id].css', // 模块名
})
],
devtool: 'cheap-module-eval-source-map' // 用于开发环境,打包后的文件与源码的映射文件,打包后在dist文件夹中会多出后缀为map的映射文件,方便定位到具体错误所在,解决问题,
}
// 使用postcss-loader需要在根目录添加一个文件 $mkdir postcss.config.js
module.exports = {
plugins: [
require('autoprefixer')
]
}