使用Node.js 20及actions/cache@v3时Pub Sub Emulator缓存文件损坏
解决GitHub Actions中Firebase Pub Sub模拟器缓存损坏问题
问题根源分析
- 路径解析错误:错误日志中路径包含
$GITHUB_WORKSPACE字符串,说明环境变量在子工作目录(functions)中未被正确展开,导致模拟器访问了无效路径。 - 缓存key逻辑失效:首次运行时
emulator-cache目录不存在,hashFiles('emulator-cache/*.{jar,zip}')生成空hash值,导致缓存key每次变动,无法复用有效缓存。 - 缓存时机颠倒:先尝试缓存空目录,再下载模拟器,导致缓存的是空内容,后续恢复自然找不到有效jar文件。
具体修复方案
1. 修正模拟器路径环境变量
将环境变量改为GitHub Actions表达式解析的绝对路径,避免shell环境变量在子目录中的解析问题:
env: CI: true FIREBASE_EMULATORS_PATH: ${{ github.workspace }}/emulator-cache
2. 调整缓存key生成规则
改用Firebase CLI版本作为缓存key的核心标识,确保版本不变时复用缓存:
- name: "Cache Emulators" uses: actions/cache@v3 id: cache-emulators with: path: ${{ env.FIREBASE_EMULATORS_PATH }} key: ${{ runner.os }}-firebase-emulators-12.4.0 # 与你安装的firebase-tools版本一致 restore-keys: | ${{ runner.os }}-firebase-emulators-
3. 调整流程顺序:先下载模拟器再缓存
先让Firebase CLI下载模拟器到指定路径,再执行缓存操作,确保缓存的是完整的模拟器文件:
- name: Setup Firebase CLI run: sudo npm install -g firebase-tools@12.4.0 - name: Download Firebase Pub Sub Emulator run: firebase setup:emulators:pubsub --emulators-path ${{ env.FIREBASE_EMULATORS_PATH }}
4. 修复Test步骤的路径引用
在functions/package.json的test脚本中,确保模拟器路径正确(因Test步骤工作目录为functions,需使用相对根目录的路径):
"scripts": { "test": "FIREBASE_EMULATORS_PATH=../emulator-cache jest" }
5. 可选:修复缓存文件权限
缓存恢复后可能出现权限问题,添加步骤修正:
- name: Fix Emulator Cache Permissions if: steps.cache-emulators.outputs.cache-hit == 'true' run: chmod -R 755 ${{ env.FIREBASE_EMULATORS_PATH }}
完整修正后的工作流片段
name: develop-pr on: pull_request: branches: - develop env: CI: true FIREBASE_EMULATORS_PATH: ${{ github.workspace }}/emulator-cache jobs: build: runs-on: ubuntu-latest timeout-minutes: 30 strategy: matrix: node-version: [20.x] steps: - uses: actions/checkout@v4 - name: Extract branch name shell: bash run: echo "branch=$(echo ${GITHUB_REF#refs/heads/})" >> $GITHUB_OUTPUT id: extract_branch - name: Setup Node uses: actions/setup-node@v4 with: node-version: ${{ matrix.node-version }} - name: "Cache npm" uses: actions/cache@v3 with: path: ~/.npm key: ${{ runner.os }}-node-${{ matrix.node-version }}-${{ hashFiles('**/package-lock.json') }} - name: Setup Firebase CLI run: sudo npm install -g firebase-tools@12.4.0 - name: Download Firebase Pub Sub Emulator run: firebase setup:emulators:pubsub --emulators-path ${{ env.FIREBASE_EMULATORS_PATH }} - name: "Cache Emulators" uses: actions/cache@v3 id: cache-emulators with: path: ${{ env.FIREBASE_EMULATORS_PATH }} key: ${{ runner.os }}-firebase-emulators-12.4.0 continue-on-error: true - name: Fix Emulator Cache Permissions if: steps.cache-emulators.outputs.cache-hit == 'true' run: chmod -R 755 ${{ env.FIREBASE_EMULATORS_PATH }} - name: Install working-directory: ./functions run: npm install - name: Lint working-directory: ./functions run: npm run lint - name: Test working-directory: ./functions run: npm run test - name: Print debug logs if: failure() run: find . -type f -name "*debug.log" | xargs cat
内容的提问来源于stack exchange,提问作者Kingsley Simon
相关产品推荐
相关产品推荐

