webpack5打包vue项目

1,846 阅读5分钟

本人webpack打包项目gitee地址:gitee.com/Hello9307/z…

一、 起步

目标:搭建一个基本项目,执行npm run dev启动一个本地项目进行开法,执行npm run build打一个包

1-1. 准备工作

1.搭建项目基本框架,我的如下

webpack-demo
|-- public
    |-- index.html
|-- src
    |-- assets
    |-- views
    |-- main.js
|-- webpack.config.js

以上就是基本的目录结构,pulic用于存放一些不需要打包的文件(例如存放在前台的下载文件,流浪器标签哪个图标)、html模板

2.index.html模板文件

<!DOCTYPE html>
<html lang="">
  <head>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width,initial-scale=1.0">
    <link rel="icon" href="<%= htmlWebpackPlugin.options.favicon %>favicon.ico">
    <title><%= htmlWebpackPlugin.options.title %></title>
  </head>
  <body>
    <noscript>
      <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
    </noscript>
    <div id="app"></div>
    <!-- built files will be auto injected -->
  </body>
</html>

<%= htmlWebpackPlugin.options.title %>这个取值在 webpack.config.js里面设置,查看下面的html-webpack-plugin使用

1-2. 安装必要依赖

1.webpack

npm install --save-dev webpack webpack-cli

2.使用模板

npm install --save-dev html-webpack-plugin

3.样式插件

npm install --save-dev style-loader css-loader

4.本地服务

npm install --save-dev webpack-dev-server

1-3. webpack.config.js

const path = require("path")
const HtmlWebpackPlugin = require("html-webpack-plugin")

module.exports = {
    // 环境,生产:production
    mode: "development",
    // 还要加下面这个处理webpack5使用webpack-dev-server编辑文件没有刷新浏览器问题
    target: process.env.NODE_ENV = "production" ? "browserslist" : "web",
    // 入口文件
    entry: "./src/main.js",
    // 输出文件
    output: {
        // 输出文件名
        filename: "main.js",
        // 输出路径,path.resolve 获取一个绝对路径
        path: path.resolve(__dirname, "dist"),
        // 是否打包时候清空之前生成的(现在就是清空整个dist文件夹)
        clean: true
    },
    resolve: {
        // 起别名,项目中就可以使用 @ 表示 src 目录了
        alias: {
            '@': path.resolve(__dirname, 'src')
        }
    },
    // 开发环境使用,报错就知道是哪个原始文件出错了
    devtool: "inline-source-map",
    // loader 转换器,将除 js, json 这两webpack默认不识别的文件转为 js 文件
    module: {
        rules: [
            {
                test: /.css$/i,
                // 注意执行顺序是后往前
                use: ['style-loader', 'css-loader']
            },
            {
                test: /.(png|jpg|jpeg|svg|gif)$/i,
                type: 'asset/resource'
            },
            {
                test: /.(woff|woff2|eot|ttf|otf)$/i,
                type: 'asset/resource'
            }
        ]
    },
    // 插件
    plugins: [
        // 自动生成 index.html 文件
        new HtmlWebpackPlugin({
            // 标题,模板中使用 EJS 方式读取 <%= htmlWebpackPlugin.options.title %>
            title: "阿德雷的城堡",
            favicon: "./public/favicon.ico",
            // index.html 文件模板
            template: "./public/index.html"
        })
    ]
}

webpack5处理图片和字体文件不需要在安装loader了,直接配置就行

1-4. package.json

{
  "name": "zq-repository",
  "version": "1.0.0",
  "description": "## Project setup ``` yarn install ```",
  "private": true,
  "scripts": {
    "test": "echo "Error: no test specified" && exit 1",
    "dev": "webpack serve --open",
    "build": "webpack"
  },
  "keywords": [],
  "author": "",
  "license": "ISC",
  "dependencies": {
    "lodash": "^4.17.21",
    "vue": "^2.6.14",
    "vue-router": "^3.5.2"
  },
  "devDependencies": {
    "css-loader": "^6.2.0",
    "html-webpack-plugin": "^5.3.2",
    "style-loader": "^3.2.1",
    "webpack": "^5.46.0",
    "webpack-cli": "^4.7.2",
    "webpack-dev-server": "^3.11.2"
  }
}

起步配置搭建完成,现在执行npm run build在根目录下会生成dist文件夹,执行npm run dev在浏览器打开当前项目

二、 完善基本配置

目标:1. 需要使用 .vue 文件编写前端代码;2.样式文件的处理;3.代码分离;4.缓存;5.压缩优化;

1. 编辑 .vue文件

安装必要依赖
npm install --save-dev vue-loader vue-loader-plugin vue-template-compiler
使用方式(调整webpack.config.js文件)
// const VueLoaderPlugin = require("vue-loader/lib/plugin");
// 之前是用上一种, 由于webpack5重写了ruleset模块,VueLoaderPlugin现在应该使用RuleSetCompiler
const VueLoaderPlugin = require("vue-loader-plugin");

module.exports = {
    plugins: [
        // VueLoaderPlugin 用于处理 rule
        // 例如将.vue 文件中 <script lang="ts"> 处理成 xx.vue.ts,这样ts-loader就能够识别了
        // 看到的一篇文章说明:https://www.cnblogs.com/eret9616/p/11802889.html
        new VueLoaderPlugin()
    ]
}

这样就可以使用.vue文件了,就是这么简单。

2. 样式文件的处理

目标:1.使用less;2.自动添加样式前缀;3.样式文件单独引入(以link方式,便于添加hash)

2-1. 使用less

安装必要依赖
npm install --save-dev less less-loader
使用方式
module: {
    rules: [
        {
            test: /\.less$/i,
            use: ['style-loader','css-loader', 'less-loader']
        }
    ]
}

2-2.自动添加样式前缀

安装必要依赖
npm i -D postcss postcss-loader autoprefixer

如果你使用了postcss-preset-env就不需要在安装autoprefixer了。

使用方式

这里有两种使用方式。一种是直接所有配置都在webpack.config.js里面;一种是部分在webpack.config.js部分在根目录新建的postcss.config.js文件;这里使用第二种; postcss.config.js

module.exports = {
    plugins: [
        [
            require('autoprefixer')
        ]
    ]
}

webpack.config.js
就是在css-loader前面使用postcss-loader

module: {
    rules: [
        {
            test: /\.less$/i,
            use: ['style-loader','css-loader', 'postcss-loader', 'less-loader']
        }
    ]
}

2-3. 样式文件单独引入

目前开发环境查看项目,会发现样式都是以<style>形式嵌入到html中使用的。如果需要将样式以<link>方式引入,需要使用到mini-css-extract-plugin

安装必要依赖
npm i -D mini-css-extract-plugin
使用方式
const MiniCssExtractPlugin = require("mini-css-extract-plugin");

module: {
    rules: [
        {
            test: /\.less$/i,
            use: [MiniCssExtractPlugin.loader, 'css-loader', 'postcss-loader', 'less-loader']
        }
    ]
},
plugins: [
    new MiniCssExtractPlugin({
        filename: "[name].[hash].css"
    })
]

注意这里不再使用style-loader了,它是将样式表以内联的方式引入。

3. 代码分离

代码分离是 webpack 中最引人注目的特性之一。此特性能够把代码分离到不同的 bundle 中,然后可以按需加载或并行加载这些文件。代码分离可以用于获取更小的 bundle,以及控制资源加载优先级,如果使用合理,会极大影响加载时间。

官网地址:webpack.docschina.org/guides/code…
目标:1.将第三方依赖拆分出来(便于后面的缓存优化处理);

3-1. 基本代码分离

这个只需要简单的配置就行

optimization: {
    moduleIds: 'deterministic',
    // 将 runtime 代码拆分为一个单独的 chunk
    runtimeChunk: "single",
    splitChunks: {
        chunks: 'all'
    },
}

4. 缓存

这个主要为了浏览加载速度。本质就是浏览器加载文件,如果文件在本地有缓存,就使用本地的,没有就加载之后进行缓存。那么开发要做的就是当改变了某个文件,就要改变这个文件名,让流浪器加载这个新的文件。
官网:webpack.docschina.org/guides/cach…

4-1. webpack.config.js简单配置就可以实现了

output: {
    filename: '[name][hash].bundle.js',
},
optimization: {
    runtimeChunk: 'single',
}

只要给输出文件名添加[hash]或者[hash:n]给文件添加hash值就可以了,hash:n是添加几位。

4-2.提取第三方库到vendor中

optimization: {
    moduleIds: 'deterministic',
    // 将 runtime 代码拆分为一个单独的 chunk
    runtimeChunk: "single",
    splitChunks: {
        cacheGroups: {
            vendor: {
                test: /[\\/]node_modules[\\/]/,
                name: 'vendors',
                chunks: 'all',
            },
        },
    },
}

这里遇到一个问题,改变了其他文件,所有的hash值都变了,请教一下有遇到的大佬吗?希望是改变了本地文件,第三方库这个vendors包的名称应该不变。

5. 压缩

将css,js,图片等进行压缩处理,减少包体积。

5-1. js压缩

默认打生产包就会执行压缩(没有压缩,看看mode是不是被自定义了)

5-2. 图片无损压缩

直接使用压缩处理过的图片

这里可以直接将图片放到压缩图片的网站上压缩后使用。

  1. tinypng png 压缩率 66%;网站;一次可提供20张图片压缩,提供开发API需要申请免费key,每月可压缩500张图片。
  2. 图好快 png 压缩率 79%;网站;提供免费API,但是限速,有点慢,vip充值可提高并发数,唯一好的是不限制压缩数量,但是价格也不便宜;界面丑,可能没前端
  3. Optimizilla png 压缩率 68%;网站;支持中文,没有提供API,压缩速度很快体验和tinypng一样,卖广告,一次可提供20张图片压缩
  4. 腾讯智图 png 压缩率35%; 网站;智图是腾讯ISUX前端团队开发的一个专门用于图片压缩和图片格式转换的平台,其功能包括针对png,jpeg,gif等各类格式图片的压缩,以及为上传图片自动选择最优的图片格式。同时,智图平台还会为用户转换一份webp格式的图片,网站不收费无广告不提供对外API但提供各种安装客户端,其实使用感觉一般。

建议使用:Optimizilla 或 tinypng 压缩几乎无损

imagemin-webpack-plugin

官网:www.npmjs.com/package/ima…

var ImageminPlugin = require('imagemin-webpack-plugin').default

plugins: [
    new ImageminPlugin({
      disable: process.env.NODE_ENV !== 'production', // Disable during development
      pngquant: {
        quality: '95-100'
      }
    })
  ]
imagemin-webpack-loader

官网:www.npmjs.com/package/ima…

rules: [{
  test: /\.(gif|png|jpe?g|svg)$/i,
  use: [
    'file-loader',
    {
      loader: 'image-webpack-loader',
      options: {
        bypassOnDebug: true, // webpack@1.x
        disable: true, // webpack@2.x and newer
      },
    },
  ],
}]

5-3. 样式文件压缩

安装依赖
npm i -D css-minimizer-webpack-plugin
使用方式
const CssMinimizerPlugin = require("css-minimizer-webpack-plugin");

optimization: {
    // 省略其它配置
    minimizer: [
        // `...`webpack5可以使用这种方式集成默认的minimizer的配置
        `...`,
        new CssMinimizerPlugin()
    ]
}

注意:压缩要配合mini-css-extract-plugin一起使用才有效。

6. 配置文件拆分

官网:webpack.docschina.org/guides/prod…

6-1. 安装依赖

// 用于和合并通用配置和开发或生产的配置
npm i -D webpack-merge

6. 添加通用、生产、开发配置文件

添加webpack.common.jswebpack.dev.jswebpack.prod.js

配置文件合并通用配置文件
const { merge } = require('webpack-merge');
const common = require('./webpack.common.js');

module.exports = merge(common, {
    
});
修改package.json文件
"scripts": {
  "dev": "webpack serve --open --config webpack.dev.js",
  "build": "webpack --env prod --config webpack.prod.js"
},

菜鸟上路,有错误的地方希望大佬批评指正,多谢多谢。