Skip to content

🧾 Vue CLI 打包文件名与 Hash 机制详解

一、为什么要给文件名加 Hash

在前端构建中,我们常常在打包后的文件名中看到类似:

app.7f8d2a31.js
chunk-vendors.5c4d8e90.js
style.13ad9f1b.css

这些 hash 值 用于浏览器缓存优化(Cache Busting):

  • 浏览器缓存资源文件;
  • 当内容改变时,hash 改变,浏览器自动加载新文件;
  • 内容不变时,hash 保持不变,命中缓存,提升性能。

二、Hash 的类型与区别

Webpack 提供了三种常见的哈希方案:

名称示例粒度说明
[hash]app.[hash].js构建级整个项目构建生成一个 hash,任何文件改动都会导致所有文件的 hash 改变
[chunkhash]app.[chunkhash].js入口级每个入口(chunk)单独计算 hash,仅改动的入口文件 hash 变化
[contenthash]style.[contenthash].css内容级根据文件内容生成 hash,只要内容不变,hash 不变(最常用)

在现代前端项目中,通常推荐使用 [contenthash],因为它最稳定、最适合缓存优化。


三、Vue CLI 的默认文件名规则

Vue CLI 内部基于 Webpack,它自动为我们设置了合适的文件命名规则:

源码(简化):

js
const outputFilename = getAssetPath(
  options,
  `js/[name]${isLegacyBundle ? '-legacy' : ''}${isProd && options.filenameHashing ? '.[contenthash:8]' : ''}.js`
)

webpackConfig.output
  .filename(outputFilename)
  .chunkFilename(outputFilename)

解析:

  • 开发模式 (isProd=false):js/[name].js
  • 生产模式:js/[name].[contenthash:8].js
  • Modern 模式(旧浏览器兼容):js/[name]-legacy.[contenthash:8].js
  • 如果在配置中关闭 filenameHashing,则不带 hash。

四、Vue CLI 的相关配置项

你可以在 vue.config.js 里控制这些行为:

1️⃣ 默认设置(带 contenthash)

js
module.exports = {
  productionSourceMap: false // 不生成 map 文件(可选)
}

输出示例:

js/app.5f4c123a.js
js/chunk-vendors.82af912b.js
css/app.13ad9f1b.css

2️⃣ 不带 hash(开发或调试)

js
module.exports = {
  filenameHashing: false
}

输出:

js/app.js
js/chunk-vendors.js
css/app.css

3️⃣ 自定义 hash 规则(例如改为 chunkhash)

js
module.exports = {
  configureWebpack: {
    output: {
      filename: 'static/js/[name].[chunkhash:6].js',
      chunkFilename: 'static/js/[name].[chunkhash:6].js'
    }
  }
}

4️⃣ 自定义资源路径结构

js
module.exports = {
  outputDir: 'dist',
  assetsDir: 'static',
  configureWebpack: {
    output: {
      filename: 'static/js/[name].[contenthash:8].js',
      chunkFilename: 'static/js/[name].[contenthash:8].js'
    }
  }
}

结果:

dist/
 ├── static/js/
 ├── static/css/
 ├── static/img/
 └── index.html

五、内部实现原理简析

Vue CLI 使用以下内部逻辑保证 hash 稳定性:

机制作用
HashedModuleIdsPlugin确保模块 ID 稳定,避免 hash 因引入顺序变化而改变
MiniCssExtractPlugin生成带 [contenthash] 的 CSS 文件
HtmlWebpackPlugin自动注入带 hash 的 JS/CSS 到 index.html
SplitChunksPlugin拆分 vendors 与业务代码,减少 hash 影响范围

六、常见命名策略推荐

场景JS 文件名CSS 文件名说明
开发环境[name].js[name].css简单直观,方便调试
生产环境(推荐)[name].[contenthash:8].js[name].[contenthash:8].css内容级 hash,缓存友好
测试或旧系统兼容[name].[chunkhash:8].js[name].[contenthash:8].css控制粒度稍粗,但兼容性好

七、总结

  • Vue CLI 默认已启用 [contenthash:8] 文件名;
  • 可以通过 filenameHashingconfigureWebpack.output 等方式自定义;
  • 推荐生产环境使用 contenthash
  • 若开启 --modern 模式,会自动生成 -legacy 文件;
  • 内部借助多种插件确保 hash 稳定性。