You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

Webpack 5不同文件结构下文件缓存无法复用问题求助(CI构建场景)

解决Webpack 5文件缓存在CI/目录复制场景下无法复用的问题

我之前优化CI构建速度时正好踩过这个坑!核心原因很明确:Webpack 5的文件系统缓存默认会基于文件的绝对路径生成缓存标识——当你把项目复制到同级的testBuild新目录后,所有源码文件的绝对路径都变了,Webpack会直接判定这是一个全新的项目,自然会放弃旧缓存、重新生成新的缓存文件。

要实现CI环境下的缓存复用,我们需要从两个方面入手:让缓存标识脱离绝对路径束缚,同时确保CI能持久化保存缓存目录,具体方案如下:

1. 自定义缓存键,基于相对路径生成

修改Webpack的cache配置,通过cacheKeys函数自定义缓存键的生成逻辑,把默认的绝对路径替换成相对于Webpack配置文件的相对路径。这样无论项目被复制到哪个目录,文件的相对路径都是一致的,缓存就能匹配上:

const path = require('path');

module.exports = {
  // ...其他Webpack配置
  cache: {
    type: 'filesystem',
    cacheDirectory: path.resolve(paths.cachePath, 'prod-cache'),
    // 自定义缓存键,替换绝对路径为相对路径
    cacheKeys: (defaultCacheKeys, { module }) => {
      if (module.resource) {
        // 计算文件相对于当前Webpack配置文件的相对路径
        const relativePath = path.relative(__dirname, module.resource);
        return {
          ...defaultCacheKeys,
          // 用相对路径覆盖默认的绝对路径缓存字段
          resource: relativePath,
        };
      }
      return defaultCacheKeys;
    },
    // 可选优化:添加package.json作为缓存依赖,确保依赖变动时缓存自动失效
    buildDependencies: {
      config: [path.resolve(__dirname, 'package.json')]
    }
  }
};

2. CI环境中配置缓存持久化

光改Webpack配置还不够,CI环境每次构建通常是全新的容器/虚拟机,所以必须把prod-cache目录配置为持久化缓存:

  • 举个GitHub Actions的例子,用actions/cache动作保存和恢复缓存:
    - name: 恢复Webpack缓存
      uses: actions/cache@v3
      with:
        path: ./path/to/prod-cache  # 替换成你的缓存目录实际路径
        key: webpack-cache-${{ hashFiles('package-lock.json', 'yarn.lock') }}
        restore-keys: |
          webpack-cache-
    
  • 如果是GitLab CI,直接配置cache字段即可:
    cache:
      paths:
        - ./path/to/prod-cache
      key:
        files:
          - package-lock.json
          - yarn.lock
        prefix: webpack-cache
    

这样每次CI构建时,都会先恢复之前保存的缓存目录,再执行构建,就能真正实现构建耗时的大幅缩短。

快速验证方法

修改配置后,先在原目录执行构建生成缓存,然后复制项目到新目录,执行构建时观察Webpack的控制台输出——如果看到类似Cache restored from disk: X modules的日志,就说明缓存已经成功复用了!

内容的提问来源于stack exchange,提问作者user14934764

火山引擎 最新活动