为什么

有没有发现,我们在每次更新代码的时候,都要重新打包然后重新刷新才能看到修改的内容。
这样做非常不方便,每次更新代码,都要重新打包。

所以webpack提供了几种方式。本文会讲三种方式。
我们先说第一种

watch

:::info webpack —watch: webpack 会帮我们监听它打包的文件,只要文件发生变化,他就会自动帮我们打包。 :::

“bundle”: “webpack —watch”

结构
image.png

  1. {
  2. "name": "webpack-demo",
  3. "version": "1.0.0",
  4. "description": "描述",
  5. "private": true,
  6. "scripts": {
  7. "bundle": "webpack --watch"
  8. },
  9. "author": "chenYongRen",
  10. "license": "ISC",
  11. "devDependencies": {
  12. "autoprefixer": "^10.4.7",
  13. "clean-webpack-plugin": "^4.0.0",
  14. "css-loader": "^6.7.1",
  15. "file-loader": "^6.2.0",
  16. "html-webpack-plugin": "^5.5.0",
  17. "node-sass": "^7.0.1",
  18. "postcss-loader": "^7.0.0",
  19. "sass-loader": "^13.0.0",
  20. "style-loader": "^3.3.1",
  21. "url-loader": "^4.1.1",
  22. "webpack": "^5.73.0",
  23. "webpack-cli": "^4.9.2"
  24. },
  25. "dependencies": {},
  26. "browserslist": [
  27. "> 1%",
  28. "last 2 versions"
  29. ]
  30. }

现在我们只要每次修改后刷新页面,就可以获取新的内容。
但是这里还有弊端:
1、每次都要自己刷新页面
2、无法进行http请求,我们可以看到当前访问的地址是我们文档的绝对地址,而不是一个服务器地址。
image.png

webpackDevServer

首先,我们需要安装webpackDevServer

npm install webpack-dev-server -D

使用”start”: “webpack-dev-server” 来启动一个本地服务器

  1. {
  2. "name": "webpack-demo",
  3. "version": "1.0.0",
  4. "description": "描述",
  5. "private": true,
  6. "scripts": {
  7. "bundle": "webpack --watch",
  8. "start": "webpack-dev-server"
  9. },
  10. "author": "chenYongRen",
  11. "license": "ISC",
  12. "devDependencies": {
  13. "autoprefixer": "^10.4.7",
  14. "clean-webpack-plugin": "^4.0.0",
  15. "css-loader": "^6.7.1",
  16. "file-loader": "^6.2.0",
  17. "html-webpack-plugin": "^5.5.0",
  18. "node-sass": "^7.0.1",
  19. "postcss-loader": "^7.0.0",
  20. "sass-loader": "^13.0.0",
  21. "style-loader": "^3.3.1",
  22. "url-loader": "^4.1.1",
  23. "webpack": "^5.73.0",
  24. "webpack-cli": "^4.9.2"
  25. },
  26. "dependencies": {},
  27. "browserslist": [
  28. "> 1%",
  29. "last 2 versions"
  30. ]
  31. }

需要注意,这是webpack5以下版本的写法,webpack5 的 devServer 不支持 ContentBase 的配置

  1. const path = require('path')
  2. const HtmlWebpackPlugin = require('html-webpack-plugin')
  3. const { CleanWebpackPlugin } = require("clean-webpack-plugin");
  4. module.exports = {
  5. mode: 'development',
  6. devtool: 'eval',
  7. entry: {
  8. main: './src/index.js'
  9. },
  10. devServer: {
  11. // 服务器启动在哪个文件夹下
  12. contentBase: './dist'
  13. },
  14. module: {
  15. rules:[
  16. {
  17. test: /\.(jpg|png|gif)$/,
  18. use:{
  19. loader: 'url-loader',
  20. options: {
  21. name:'[name]_[hash].[ext]',
  22. outputPath: 'images/',
  23. limit: 2048 // 2kb
  24. }
  25. }
  26. },
  27. {
  28. test: /\.scss$/,
  29. use:[
  30. 'style-loader',
  31. {
  32. loader:'css-loader',
  33. options: {
  34. importLoaders: 2
  35. }
  36. },
  37. 'sass-loader',
  38. 'postcss-loader'
  39. ]
  40. }
  41. ]
  42. },
  43. plugins:[new HtmlWebpackPlugin({
  44. template: 'src/index.html'
  45. }), new CleanWebpackPlugin()],
  46. output: {
  47. filename: '[name].js',
  48. path: path.resolve(__dirname, 'dist')
  49. }
  50. }

webpack5真正的配置方法

  1. const path = require('path')
  2. const HtmlWebpackPlugin = require('html-webpack-plugin')
  3. const { CleanWebpackPlugin } = require("clean-webpack-plugin");
  4. module.exports = {
  5. mode: 'development',
  6. devtool: 'eval',
  7. entry: {
  8. main: './src/index.js'
  9. },
  10. devServer: {
  11. // 服务器启动在哪个文件夹下
  12. static: {
  13. directory : path.join(__dirname, 'dist'),
  14. },
  15. },
  16. module: {
  17. rules:[
  18. {
  19. test: /\.(jpg|png|gif)$/,
  20. use:{
  21. loader: 'url-loader',
  22. options: {
  23. name:'[name]_[hash].[ext]',
  24. outputPath: 'images/',
  25. limit: 2048 // 2kb
  26. }
  27. }
  28. },
  29. {
  30. test: /\.scss$/,
  31. use:[
  32. 'style-loader',
  33. {
  34. loader:'css-loader',
  35. options: {
  36. importLoaders: 2
  37. }
  38. },
  39. 'sass-loader',
  40. 'postcss-loader'
  41. ]
  42. }
  43. ]
  44. },
  45. plugins:[new HtmlWebpackPlugin({
  46. template: 'src/index.html'
  47. }), new CleanWebpackPlugin()],
  48. output: {
  49. filename: '[name].js',
  50. path: path.resolve(__dirname, 'dist')
  51. }
  52. }

我们可以看到,现在他已经帮我们启动了一个服务器在 http://localhost:8080/
image.png
修改代码
image.png
它的好处就是
1、启用一个本地服务器,可以进行http请求
2、不用刷新也能获取最新的页面数据
3、有更多的配置项

  1. devServer: {
  2. // 服务器启动在哪个文件夹下
  3. static: {
  4. directory: path.join(__dirname, 'dist'),
  5. },
  6. // 自动打开浏览器
  7. open: true,
  8. // 默认端口号
  9. port: 8080
  10. },

自己创建一个服务器

如果要自己创建一个服务器,我们就需要用到node的知识,我们可以使用它的express框架搭建服务器

npm install express

当然这个文件还要监听webpack文件的变化,然后帮我们自动打包,所以还要使用一个webpack的开发中间件webpack-dev-middleware

npm install express webpack-dev-middleware -D

结构
image.png

  1. {
  2. "name": "webpack-demo",
  3. "version": "1.0.0",
  4. "description": "描述",
  5. "private": true,
  6. "scripts": {
  7. "bundle": "webpack",
  8. "watch": "webpack --watch",
  9. "start": "webpack-dev-server",
  10. "middleware": "node server.js"
  11. },
  12. "author": "chenYongRen",
  13. "license": "ISC",
  14. "devDependencies": {
  15. "autoprefixer": "^10.4.7",
  16. "clean-webpack-plugin": "^4.0.0",
  17. "css-loader": "^6.7.1",
  18. "file-loader": "^6.2.0",
  19. "html-webpack-plugin": "^5.5.0",
  20. "node-sass": "^7.0.1",
  21. "postcss-loader": "^7.0.0",
  22. "sass-loader": "^13.0.0",
  23. "style-loader": "^3.3.1",
  24. "url-loader": "^4.1.1",
  25. "webpack": "^5.73.0",
  26. "webpack-cli": "^4.9.2",
  27. "webpack-dev-server": "^4.9.3"
  28. },
  29. "dependencies": {},
  30. "browserslist": [
  31. "> 1%",
  32. "last 2 versions"
  33. ]
  34. }
  1. const path = require('path')
  2. const HtmlWebpackPlugin = require('html-webpack-plugin')
  3. const { CleanWebpackPlugin } = require("clean-webpack-plugin");
  4. module.exports = {
  5. mode: 'development',
  6. devtool: 'eval',
  7. entry: {
  8. main: './src/index.js'
  9. },
  10. devServer: {
  11. // 服务器启动在哪个文件夹下
  12. static: {
  13. directory: path.join(__dirname, 'dist'),
  14. },
  15. // 自动打开浏览器
  16. open: true,
  17. // 默认端口号
  18. port: 8080
  19. },
  20. module: {
  21. rules:[
  22. {
  23. test: /\.(jpg|png|gif)$/,
  24. use:{
  25. loader: 'url-loader',
  26. options: {
  27. name:'[name]_[hash].[ext]',
  28. outputPath: 'images/',
  29. limit: 2048 // 2kb
  30. }
  31. }
  32. },
  33. {
  34. test: /\.scss$/,
  35. use:[
  36. 'style-loader',
  37. {
  38. loader:'css-loader',
  39. options: {
  40. importLoaders: 2
  41. }
  42. },
  43. 'sass-loader',
  44. 'postcss-loader'
  45. ]
  46. }
  47. ]
  48. },
  49. plugins:[new HtmlWebpackPlugin({
  50. template: 'src/index.html'
  51. }), new CleanWebpackPlugin()],
  52. output: {
  53. // 我所有打包生成的文件之间的引用,前面都加根路径
  54. // 其实一般不加也可以
  55. publicPath:'/',
  56. filename: '[name].js',
  57. path: path.resolve(__dirname, 'dist')
  58. }
  59. }
  1. // 引用express
  2. const express = require('express')
  3. // 引用webpack
  4. const webpack = require('webpack');
  5. const webpackDevMiddleware = require('webpack-dev-middleware')
  6. // 引用webpack的配置
  7. const config = require('./webpack.config.js')
  8. // 引用webpack的编译器
  9. const complier = webpack(config);
  10. // 通过express创建一个http应用
  11. const app = express();
  12. // 再服务器上使用了webpack的中间件,它可以监听到webpack打包代码的变化、
  13. // 打包生成的publicPathwebpack配置文件中的一致
  14. publicPath: config.output.publicPath
  15. // 当然,这里的publicPath以及config.output.publicPath都不写也没问题
  16. app.use(webpackDevMiddleware(complier,{
  17. publicPath: config.output.publicPath
  18. }))
  19. // 它启动在3000的端口上
  20. app.listen(3000, ()=>{
  21. console.log("监听端口号3000")
  22. })

npm run middleware
image.png

image.png
这里手写的启动服务器的方法,肯定没有webpack自带的智能,通过这个方法我们可以知道,我们也是可以自己手写的,并且可以不断优化。

通过第三种方式,我们可以知道。
1、在node中我们也可以直接使用webpack
2、我们之前是在命令行中使用webpack

参考

开发
devtool
webpack-dev-server
命令行接口
Node.js API