了解webpack基本配置,通过webpack配置Vue项目。

前言

webpack是一个模块打包工具(module bundler),它可以对Web前端和Node.js等应用进行打包。

了解webpack基本配置

安装webpack

首先 我们需要通过包管理工具(npm/pnpm/yarn等)来安装webpack所需要的包(webpackwebpack-cli), 这是最基本的文件。

shell 复制代码
npm install webpack webpack-cli -D 
// webpack为webpack的核心包,webpack-cli是webpack的命令行工具,运行webpack命令需要使用
//可以通过@来安装指定版本 如:webpack@5.21.2

webpack相关基本配置

介绍webpack的相关配置,详细可参考下文中的webpack.config.js示例。

context

基础目录,表示资源入口entry是以哪个目录为起点的。值为字符串,表示一个绝对路径。

entry

webpack打包的入口文件配置项。表示从哪个文件为入口开始打包。值可以为字符串,也可以为数组、对象、函数、描述符。

  • 字符串形式:最简单的形式,表示打包入口的js文件。
  • 数组形式:最后一个文件是资源的入口文件,数组的其余文件会被预先构建到入口文件中。(注:数组形式的entry本质上还是单一入口。)
  • 对象形式:对象形式的entry又被称为多入口配置,与前两项不同,多入口文件配置打包后生成多个JS文件。
  • 函数形式:函数形式取函数返回值作为入口配置,返回值为上述三项之一。可以做一些额外的逻辑处理,但搭脚手架时很少使用。
  • 描述符形式:描述符形式也是一个对象,米哦啊书夫语法可以用来给入口传入额外的选项,例如设置dependOn选项时,可以与另一个入口chunk共享模块。

output

webpack打包后的资源出口配置项,四个属性:"path"(输出路径)、"filename"(输出文件名),"publicPath","chunkFilename"。

  • filename:打包后生成的资源名称,可以是文件名称,也可以是相对地址('./js/bundle.js')。最终打包输出的文件地址时path绝对路径与filename拼接后的地址。支持生成动态文件名如:'hash-bundle.js'。
  • path:表示资源打包后输出的位置,需要一个绝对路径,默认为dist目录。
  • publicPath:资源访问路径,默认值为auto。
  • chunkFailename:表示打包过程中非入口文件的chunk名称,通常在使用异步模块的时候,会生成非入口文件的chunk。

动态值

补充 :关于动态值有hash、fullhash、chunkhash、contenthash,与浏览器缓存相关,对于一些长期不变更的文件资源,通常会存储在本地磁盘,当文件变动时再去请求新的文件,而这种动态值如hash、chunkhash、contenthash是根据文件内容计算出来的,通过动态值得变化来判断文件有无变更。通常通过结合name(名字)、id(唯一序列号)来使用。 目前fullhash已经替代hash,使用hash会出现警告。
区别:

  • 通常对于单文件我们使用hash(fullhash)即可。例如:[name]-[fillhash:8].js,hash是根据全部参与打包得文件计算出来的。
  • 对于多文件通常使用chunkhash。chunkhash是通过当前打包的chunk计算出来的。
  • 对于css文件,我们一般使用contenthash。主要用于计算css得hash值。

mode

webpack打包模式,有三种分别为"production"(默认值),"development","none",productiondevelopment这两种模式分别按照线上生产和本地测试做一些优化处理。其中production是给生产环境打包使用(压缩代码),none会保留原始的打包结果。

预处理器

Loader:预处理器本质上是一个函数,它接收一个资源模块,然后将其处理成webpack能使用的形式。(解析模板),配置项为module

常用的一些预处理器:style-loadercss-loadervue-loaderts-loaderfile-loaderurl-loaderbabel-loadersass-loader等。 预处理配置项:exclude/include,通过字符串或正则表达式匹配文件,排除或进行处理。exclude优先级高。

插件

插件与预处理器不同,预处理器主要用来解析模板的,而插件是扩展wbepack的能力的。配置项为plugins

常用插件有:clean-webpack-plugincopy-webpack-pluginhtml-webpack-pluginmini-css-extract-pluginterser-webpack-pluginwebpack-bundle-analyzer等。

webpack本地服务

webpack官方提供了一个webpack服务工具webpack-dev-server,在本地开启一个网络服务器,可以用来处理网络请求。通过npm安装,npx启动服务。

shell 复制代码
    npm install webpack-dev-server -D
    npx webpack-serve 

webpack-dev-server常见配置,通过在webpack配置文件的devServer里来进行配置。

js 复制代码
······
    devServer:{
        histroyApiFallback:true, //解决Html Histroy模式下 所有404重定向问题。
        publicPath:'/',  //服务器请求资源路径,默认值为'/'
        open:true, //启动服务后是否自动打开浏览器
        compress:true,  // 是否为静态资源开启Gzip压缩
        hot:false, //是否启动热替换功能
        port:8080, // 服务端口号设置
    }
······

环境变量

这里的环境指的是Node.js的环境变量,Node.js在执行JS代码是可以获取到环境变量,它们存放在process.env模块中。 在实际开发中我们可以通过cross-env来设置环境变量。

shell 复制代码
    npm install cross-env -D

通过在package.json中配置如:

json 复制代码
   "script":{
       "start":"cross-env NODE_ENV=development webpack serve --config webpack.config.js"
       "build":"cross-env NODE_ENV=production webpack --config webpack.config.js"
   }

这样我们就可以通过不同命令来配置环境变量的值,并在webpack配置文件中使用。 当然我们还可以通过webpack自带插件,DefinePlugin来将环境变量注入到业务逻辑代码中。

js 复制代码
   plugins:[
       new wbepack.DefinePlugin({
       MY_DEV:'dev'
       })
   ]

webpack.config.js 示例

通常我们使用webpack都会在项目根目录下配置webpack.config.js文件,当我们执行webpack命令时,webpack会自动寻找该文件并根据其配置信息进行打包。 示例:

javascript 复制代码
    //webpack.config.js文件配置
    const path = require('path');
    const { CleanWebpackPlugin } = require('clean-webpack-plugin');
    const CopyPlugin = require('copy-webpack-plugin');
    const HtmlWebpackPlugin = require('html-webpack-plugin');
    const MiniCssExtractPlugin = require('mini-css-extract-plugin')
    module.exports={
        entry:'./a.js', //webpack入口文件
        output:{ //输出文件
            path:path.resolve(_dirname,'dist'), //输出文件路径
            filename:'bundle.js' //输出文件名
        },
        mode:'none' //webpack打包模式,有三种分别为"production"(默认值),"development","none"
        //production和development这两种模式分别按照线上生产和本地测试做一些优化处理。
        //其中production是给生产环境打包使用(压缩代码),none会保留原始的打包结果。
        module:{
            rules:[{
                test:'/\.(scss|css)$/',
                use:['style-loader','css-loader','sass-loader']
                // use:[MiniCssExtractPlugin.loader,'css-loader','sass-loader'] 生产
            },  
            {
                test: /\.vue$/, //解析vue 模板
                use: "vue-loader"
            },
            {
                test:/\.js$/,
                use:{
                    loader:'babel-loader',
                    options:{
                        presets:['@babel/preset-env']
                    }
                }
            },
            {
                test:/\.(png|jpg)$/,
                use:{
                    loader:'url-loader',
                    options:{
                        limit:1024*8,
                    }
                }
            }
            ]
        },
        plugins:[
            new CleanWebpackPlugin(),
            new CopyPlugin({
                patterns:[
                    {
                       from:path.resolve(_dirname,'src/img/'),
                       to:path.resolve(_dirname,'dist/image/')
                    },
                ]
            }),
            new MiniCssExtractPlugin({
                filename:'[name]-[contenthash:8].css',
                chunkFilename:'[id].css',
            })
            new HtmlWebpackPlugin({
                title:'webpack入门',
                filename:'index.html',
                // template:'./public/index.html'
            }),
            
        ],
        devServer:{
            histroyApiFallback:true, //解决Html Histroy模式下 所有404重定向问题。
            publicPath:'/',  //服务器请求资源路径,默认值为'/'
            open:true, //启动服务后是否自动打开浏览器
            compress:true,  // 是否为静态资源开启Gzip压缩
            hot:false, //是否启动热替换功能
            port:8080, // 服务端口号设置
        }
    }
//npm install webpack@5.21.2 webpack-cli@4.9.0 webpack-dev-server@3.11.2 -D

合并配置(开发环境与生产环境)

在实际开发中,开发环境和生产环境的配置有很多是相同的,通常我们把这些相同配置提取出来,以供开发环境和生产环境来使用。

我们可以通过配置NODE环境变量 通过判断来实现不同配置信息,webpack也提供了webpack-merage 可以帮助我们更简单方便的合并webpack配置文件。

shell 复制代码
    npm install webpack-merage -D

创建三个配置文件

  • webpack.development.js 开发环境配置
  • webpack.production.js 生产环境配置
  • webpack.common.js 公共配置 webpack-merage语法:
js 复制代码
   //webpack.common.js
   const path = require('path')
   module.exports = {
        ······
        //配置信息
   }
   
   
   //webpack.development.js
   const { merge } = require('webpack-merage')
   const common = require('./webpack.common.js')
   module.exports = merge(common,{
           ····开发环境的配置信息
   });
   
   //webpack.production.js 与开发环境配置文件类似

通过配置packages.json文件来使用不同的配置文件 例:

json 复制代码
    "script":{
        "start":"cross-env NODE_ENV=development webpack serve --config webpack.development.js"
        "build":"cross-env NODE_ENV=production webpack --config webpack.production.js"
    }

性能优化

webpack-bundle-analyzer

webpack-bundle-analyzer是一个非常有用的webpack可视化优化分析工具,他可以帮我们分析打包后的资源体积大小,并可以分析该资源由哪些模块组成。

shell 复制代码
    npm install webpack-bundle-analyzer -D
js 复制代码
    //webpack.config.js
    const BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin;
    ······
        plugins:{
            new BundleAnalyzerPlugin();
        }
    ······

speed-measure-webpack-plugin

webpack优化需要关注得除资源组成与大小外,还需要关注打包花费的时间。speed-measure-webpack-plugin可以帮我们分析打包过程中预处理器与插件等花费得时间。

js 复制代码
    const SpeedMeasurePlugin = require("speed-measure-webpack-plugin");
    const smp = new SpeedMeasurePlugin();
    let config = {
     //配置项
    }
    module.exports = smp.wrap(config)

资源压缩

对于JS文件压缩,可以使用插件terser-webpack-plugin,可以通过plugins插件形式,也可以通过opotimization配置 对于CSS文件压缩可以使用插件css-minimizer-webpack-plugin,通过opotimization配置。

例:

js 复制代码
    const TerserPlugin = require("terser-webpack-plugin");
    const CssMinimizerPlugin = require("css-minimizer-webpack-plugin");
    module.exoprts = {
        module:{
            rules:[{
                test:'/\.(scss|css)$/',
                use:[MiniCssExtractPlugin.loader,'css-loader','sass-loader']
            }]  
        },
        plugins:[
            new MiniCssExtractPlugin({
                filename:'[name]-[contenthash:8].css',
                chunkFilename:'[id].css',
            })
        ],
        optimization : {
            minimize:true,
            minimizer:[new TerserPlugin(),new CssMinimizerPlugin()],  //压缩器
        }
    }

缩小查找范围

exclude与include 设置处理范围

通过对预处理器设置exclude和include字段,设置处理范围。例如使用babel-loader,node_modules中的第三方包一般都进行过转码处理,所以可以将此目录排除在babel-loader处理范围。

module.noParse 排除解析模块

通过module.noParse,有些模块不需要被任何预处理器解析,例如jQuery,Lodash这一类的库。

resolve.modules 快速搜寻第三方包

用于配置webpack如何搜索第三方模块的路径。

resolve.extensions 匹配文件后缀名

用于webpack匹配文件后缀名。 import {name} from './b'; //省去了.js 通过配置 extensions : '.js','.json'

splitChunks

用途:抽离公共代码。 参数:

  • chunks:表示什么类型的chunks里提取代码,有三个字符串值,分别为:'initial(只从入口chunks提取代码)'、'async(从动态加载的chunks提取)'、'all(all表示从上两者中都提取代码)'可以使用,还可以通过函数来匹配要提取的chunks。默认值为async。
  • miniSize:提取出来的chunk的最小体积,只有到达这个值才会被提取,默认20 000 (20Kb)
  • maxSize:表示提取出来的chunk的最大体积,其默认值是0,表示不限制最大体积。它是一个可违反的值,在被违反时起到提示作用。
  • minChunks:默认值是1,表示拆分前至少被多少个chunks引用的模块才会被提取。
  • maxAsyncRequests:按需(异步)加载时的最大并行请求数。
  • maxInitialRequests:入口点的最大并行请求数
  • cacheGroups:缓存组,可以继承或覆盖来自splitChunks.*的任何配置,几个重要参数
    • priority:缓存组优先级。一个模块可以有多个缓存组,其priorty的默认值是负数,自定义组priority的默认值是0。
    • reuseExistingChunk:是否重用chunk。若当前chunk中包含从主bundle中拆分出的模块,则它将被重用,而不是生成新的模块,其默认值为true。
    • test:匹配模块资源路径或chunk名称,其值可以是布尔值、正则表达式或字符串,若其值缺省则会选择所有模块。

优先级 minSize > maxSize > maxInitialRequests/maxAsyncRequests

使用TreeShaking

Tree Shaking可以检测模块中没有用到的代码块,在webpack打包时将它们移除从而减小打包后的资源体积。 开启Tree Shaking,对于webpack5 已经可以做到深层次Tree Shaking。

注:生产环境我们不会开启Tree Shaking 会影响构建速度,生产环境我们将mode改为production,即可自动打开Tree Shaking。

手动开启Tree Shaking

js 复制代码
    const TerserPlugin = require("terser-webpack-plugin");
    ······
    optimization:{
        usedExports:true,
        minimize:true,
        minimizer:[new TerserPlugin()],
    }

排除Tree Shaking文件 如polyfill

js 复制代码
    {
        "sideEffects":[
            "./polyfill.js"
        ]
    }

通过webpack构建Vue项目

项目结构:

  • src
  • -- main.ts
  • -- App.vue
  • webpack.config.js
  • index.html
  • package.json

基础构建

一、构建项目目录

生产package.json文件

shell 复制代码
    npm init -y 

新建webpack.config.js、index.html、src目录(下有mian.js、App.vue文件)。

二、安装相关依赖

安装webpack、webpack-cli(命令行)、webpack-dev-server(本地服务)、vue、vue-loader(解析vue文件)、html-webpack-plugin(使用html模板)。 也可以安装一些其他的插件 如:我们项目中需要使用sass,可以安装sass、sass-loader。 将css代码提取出来可以使用 mini-css-extract-plugin 。

shell 复制代码
    npm install webpack webpack-cli webpack-dev-server -D
    npm install vue 
    npm install vue-loader -D
    npm install sass sass-loader -D
    npm install html-webpack-plugin -D
    npm install mini-css-extract-plugin -D

三、配置webpack.config.js

注:参考示例,并不可直接使用。

js 复制代码
const path = require('path');

const HtmlWebpackPlugin = require('html-webpack-plugin');

const { VueLoaderPlugin }= require('vue-loader');

module.exports = {
  entry: './src/main.js',
  output: {
    path: path.resolve(__dirname, 'dist'),
    filename: '[name]-[chunkhash].js',
    clean:true;//清空上次打包的结果
  },
  
  module: {
    rules: [
      {
        test: /\.vue$/,
        loader: 'vue-loader',
      },
      {
       test:'/\.(scss|css)$/',
       use:['style-loader','css-loader','sass-loader']
       // use:[MiniCssExtractPlugin.loader,'css-loader','sass-loader'] 生产
      },  
    ]
  },
  plugins:[
    new HtmlWebpackPlugin({
      template: './index.html',
    }),
    new VueLoaderPlugin(),
  ],
   optimization: {
    splitChunks: {
      cacheGroups: {
        moment: {
          test: /[\\/]node_modules[\\/]/,
          priority:-10,
          chunks: "all",
          reuseExistingChunk:true,
        },
        common: {
          chunks: "all",
          priority:-20
          minChunks: 2,
          reuseExistingChunk:true,
        },
      },
    },
  },
  mode:'development',
}

可以通过npx webpack来打包 npx webpack serve 启动服务,也可以通过package.json文件配置脚本。

更多详细配置可以参考上文相关webpack基本配置介绍,比如说我们还可以通过插件压缩JS、CSS代码,压缩图片,通过splitChunks进行公共代码抽离。还可以通过安装ts和ts-loader来使用ts开发。

总结

本篇文章主要是对webpack基本配置的一些总结,其次通过webpack手动配置vue项目,可以帮助我们加深对webpack的了解,方便以后的灵活运用,对以后工作中的项目优化会提供一些帮助。
如果文章中有描述错误或不清晰的地方,希望可以帮忙指正。

相关推荐
weixin_382395238 小时前
为小工厂量身打造:本地部署的物料管理系统带缺料计算
前端·制造
__zRainy__8 小时前
解决pnpm v10+不自动构建
前端·pnpm·工程化
猫猫不是喵喵.9 小时前
Vue3 Props 属性
前端·javascript·vue.js
醉城夜风~10 小时前
CSS元素显示模式(display)
前端·css
AI大模型-小华10 小时前
Codex 三方充值快速入门指南
java·前端·数据库·chatgpt·ai编程·codex·chatgpt pro
做前端的娜娜子13 小时前
同一链接实现 PC Web 与移动 H5 自适应
前端·掘金·金石计划
小帅不太帅13 小时前
架构没变、规模没变,DeepSeek V4 Flash 正式版凭什么暴涨 47 分?
前端·aigc·deepseek
jarvisuni13 小时前
DeepSeekFlash前端依旧拉垮,而且变慢了很多!
前端·javascript·算法
卷福同学15 小时前
AI编程出海第二步:验证关键词能否做站
前端·人工智能·后端