ci: give each e2e.yml caller its own artifact namespace

pr.yml now calls the reusable e2e.yml twice in one workflow run: the advisory
`e2e` job and the blocking `orchestration_e2e` job. Both start e2e.yml's
`build` job, and both would upload `e2e-build-out`. upload-artifact v4+ fails
outright when two jobs in one run upload the same name, so a PR touching
orchestration source AND any other routed source would kill whichever build
finished second -- taking the new required check red for a reason that has
nothing to do with the PR. `playwright-traces-changed` had the same collision
on failure in both lanes.

Add an optional `artifact_suffix` workflow_call input, default '', and append
it to every artifact name e2e.yml uploads or downloads -- not just the two that
can collide today, because a bare name left behind would fail only when a spec
fails in both lanes, hiding the signal exactly when it matters. The advisory
caller passes nothing; schedule and dispatch runs pass no inputs at all, so
both keep the names they have always used. `orchestration_e2e` passes
`-orchestration`.

release-e2e-dispatch-contract's "hands the built relay artifact to every E2E
run command" pinned the literal `e2e-build-out` on the upload and both
downloads. It now compares the downloads against the upload's own name, which
is what the test was really guarding: upload and download must agree. A mutant
that renames one download still fails it.

Verified: actionlint resolves the caller/callee input contract (a deliberately
typo'd input name is reported), and both new assertions were mutation-checked.
This commit is contained in:
Jinwoo-H
2026-09-09 19:33:37 -04:00
parent 0c69c739c1
commit 0d5ab3f50e
4 changed files with 73 additions and 11 deletions
+17 -9
View File
@@ -21,6 +21,14 @@ on:
description: '"true" when the PR touches SSH execution source; gates the Docker-SSH lane'
required: false
type: string
artifact_suffix:
description: >-
Appended to every artifact name this workflow uploads or downloads. A caller that
invokes this workflow twice in one run must give the second call a distinct value:
upload-artifact fails outright when two jobs in the same run upload one name.
required: false
default: ''
type: string
workflow_dispatch:
inputs:
ref:
@@ -70,7 +78,7 @@ jobs:
- name: Upload E2E build output
uses: actions/upload-artifact@v7
with:
name: e2e-build-out
name: e2e-build-out${{ inputs.artifact_suffix }}
path: out/
# Why: build-relay.mjs writes each relay's marker as `out/relay/<platform>/.version`,
# and upload-artifact drops dotfiles by default — consumers then fail SSH specs with
@@ -159,7 +167,7 @@ jobs:
- name: Download E2E build output
uses: actions/download-artifact@v8
with:
name: e2e-build-out
name: e2e-build-out${{ inputs.artifact_suffix }}
path: out/
# Why: the Electron suite is wall-clock constrained on OSS runners, but
@@ -180,7 +188,7 @@ jobs:
if: failure()
uses: actions/upload-artifact@v7
with:
name: playwright-traces-${{ matrix.shard_name }}
name: playwright-traces-${{ matrix.shard_name }}${{ inputs.artifact_suffix }}
path: test-results/
retention-days: 7
if-no-files-found: ignore
@@ -214,7 +222,7 @@ jobs:
- name: Download E2E build output
uses: actions/download-artifact@v8
with:
name: e2e-build-out
name: e2e-build-out${{ inputs.artifact_suffix }}
path: out/
- name: Run changed E2E specs
@@ -258,7 +266,7 @@ jobs:
if: failure()
uses: actions/upload-artifact@v7
with:
name: playwright-traces-changed
name: playwright-traces-changed${{ inputs.artifact_suffix }}
path: test-results/
retention-days: 7
if-no-files-found: ignore
@@ -301,7 +309,7 @@ jobs:
- name: Download E2E build output
uses: actions/download-artifact@v8
with:
name: e2e-build-out
name: e2e-build-out${{ inputs.artifact_suffix }}
path: out/
# Why: this is the release-path proof that the deployed Linux relay keeps
@@ -354,7 +362,7 @@ jobs:
if: failure()
uses: actions/upload-artifact@v7
with:
name: playwright-traces-ssh-docker-watcher-isolation
name: playwright-traces-ssh-docker-watcher-isolation${{ inputs.artifact_suffix }}
path: e2e-traces/
retention-days: 7
if-no-files-found: ignore
@@ -396,7 +404,7 @@ jobs:
native-runtime: electron
- uses: actions/download-artifact@v8
with:
name: e2e-build-out
name: e2e-build-out${{ inputs.artifact_suffix }}
path: out/
- name: Start isolated localhost SSH server
shell: bash
@@ -438,7 +446,7 @@ jobs:
- uses: actions/upload-artifact@v7
if: failure()
with:
name: localhost-ssh-traces
name: localhost-ssh-traces${{ inputs.artifact_suffix }}
path: test-results/
retention-days: 7
if-no-files-found: ignore
+5
View File
@@ -962,6 +962,11 @@ jobs:
with:
ref: ${{ github.event.pull_request.head.sha }}
test_files: ${{ needs.code_paths.outputs.orchestration_test_files }}
# Why: a PR touching orchestration source AND another routed source runs both callers of
# e2e.yml in one workflow run, and upload-artifact fails when two jobs upload one name.
# Without this the second `build` to finish dies on e2e-build-out and takes a required
# check red for a reason unrelated to the PR.
artifact_suffix: -orchestration
# Why this is not in verify's needs: it is the first PR-gate run of a harness whose reliability
# is only known from nightly main runs (20/20 green, 2026-08-09..2026-08-29, p50 3m25s). It