diff --git a/.github/workflows/targeted-feature-verification.yml b/.github/workflows/targeted-feature-verification.yml index 8264f4fbfd..74608eabde 100644 --- a/.github/workflows/targeted-feature-verification.yml +++ b/.github/workflows/targeted-feature-verification.yml @@ -84,14 +84,20 @@ jobs: --max-command-seconds 720 echo "matrix=$(jq -c '.matrix' .workflow-artifacts/targeted-pr/shards/matrix.json)" >> "$GITHUB_OUTPUT" + # Keyed by run_id only (no run_attempt): "Re-run failed jobs" does not + # re-run this job, so a re-attempted shard must find the selection the + # original attempt uploaded. Artifacts from earlier attempts stay visible + # to later attempts of the same run. overwrite lets "Re-run all jobs" + # replace it; the selection is a pure function of the same base/head SHAs. - name: Upload immutable selection uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4 with: - name: targeted-feature-selection-${{ github.run_id }}-${{ github.run_attempt }} + name: targeted-feature-selection-${{ github.run_id }} path: .workflow-artifacts/targeted-pr include-hidden-files: true if-no-files-found: error retention-days: 14 + overwrite: true targeted: if: github.event_name != 'pull_request' || github.event.pull_request.head.repo.full_name == github.repository @@ -153,7 +159,7 @@ jobs: - name: Download immutable selection uses: actions/download-artifact@d3f86a106a0bac45b974a628896c90dbdf5c8093 # v4 with: - name: targeted-feature-selection-${{ github.run_id }}-${{ github.run_attempt }} + name: targeted-feature-selection-${{ github.run_id }} path: .workflow-artifacts/targeted-pr - name: Generate and check Flows v2 spec diff --git a/tests/fixtures/targeted-feature-verification.test.ts b/tests/fixtures/targeted-feature-verification.test.ts index ceea3ce12e..b7cfff03aa 100644 --- a/tests/fixtures/targeted-feature-verification.test.ts +++ b/tests/fixtures/targeted-feature-verification.test.ts @@ -508,6 +508,20 @@ describe('targeted Flows v2 PR verification', () => { expect(workflow).toContain('matrix: ${{ fromJSON(needs.select.outputs.matrix) }}'); }); + it('keys the shard selection artifact by run so "Re-run failed jobs" can download it', async () => { + const workflow = parse(await readFile('.github/workflows/targeted-feature-verification.yml', 'utf8')); + const step = (job: string, name: string) => + workflow.jobs[job].steps.find((candidate: { name?: string }) => candidate.name === name); + const upload = step('select', 'Upload immutable selection'); + const download = step('targeted', 'Download immutable selection'); + + // No run_attempt: the select job is not re-run by "Re-run failed jobs". + expect(upload.with.name).toBe('targeted-feature-selection-${{ github.run_id }}'); + expect(download.with.name).toBe(upload.with.name); + // "Re-run all jobs" re-uploads the same name. + expect(upload.with.overwrite).toBe(true); + }); + it('expands the broker binary template in a full-smoke spec', async () => { const directory = await mkdtemp(path.join(os.tmpdir(), 'relay-targeted-pr-broker-')); temporaryDirectories.push(directory);