Skip to content

fix(ci): chain-release uses PAT so scrape-pack completion fires chain-image - #217

Merged
laradji merged 1 commit into
mainfrom
emdash/feat-anti-recursion-dispatch-scrape-pack-chain-image-workflow-010np
May 7, 2026
Merged

laradji merged 1 commit into
mainfrom
emdash/feat-anti-recursion-dispatch-scrape-pack-chain-image-workflow-010np

Conversation

@laradji

@laradji laradji commented May 7, 2026

Copy link
Copy Markdown
Owner

Summary

  • Replace GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} with secrets.CHAIN_DISPATCH_TOKEN on chain-release.yml's Dispatch scrape-pack.yml step. The default token's anti-recursion gate allows the dispatch itself but suppresses the downstream workflow_run trigger on scrape-pack's completion, so chain-image.yml never fires. A user-owned PAT re-enables the chain.
  • Rewrite the header comment block — the previous "the anti-recursion gate ... does NOT apply to workflow_dispatch" claim was wrong in the part that matters here (downstream workflow_run).
  • Add a Validate secrets fail-fast step mirroring release.yml's RELEASE_PUBLISH_TOKEN check (matches the fix(ci): use PAT in release.yml so release.published fires downstream #148 precedent).

Closes #216. Same anti-recursion class as #148 (which fixed release.yml -> update-package-channels.yml).

Operator action required before this is effective

Diagnostic recap (from #216)

scrape-pack run event triggering_actor chain-image fired?
25505373769 (v0.7.2 tag, dispatched by chain-release.yml) workflow_dispatch github-actions[bot] ❌ no
25507444431 (manual probe by operator) workflow_dispatch laradji ✅ yes (run 25507936913)

Same event, same branch, same successful completion — only the actor differs. PAT swap makes triggering_actor a real user.

Test plan

  • YAML lints — python3 -c "import yaml; yaml.safe_load(...)" passes.
  • No regression: existing gates (workflow_run.conclusion == 'success', tag-push event, ^v[0-9]+\\.[0-9]+\\.[0-9]+$ stable-tag regex) unchanged.
  • Pre-release tags still skip dispatch (and skip the PAT validation, so a missing PAT does NOT break pre-release tag pushes).
  • End-to-end validation on v0.7.3 tag push (operator) — full chain release.yml → chain-release → scrape-pack → chain-image → docker-publish runs without manual gh workflow run calls. PR cannot be marked done until this validates.

Out of scope

Per #216: no changes to scrape-pack.yml, chain-image.yml, docker-publish.yml, or release.yml. The break is on the chain-release dispatch hop only.

Note on AC: the issue mentions adding a bullet to CLAUDE.md "Release operator secrets". That file is gitignored in this repo (see .gitignore); the operator can update their private copy outside the PR.

…dispatch

The default GITHUB_TOKEN is allowed to call workflow_dispatch, but the
resulting run's completion does not spawn workflow_run downstreams
(anti-recursion gate). scrape-pack ran fine on the v0.7.2 tag push
but chain-image never fired; a manual probe with a real user PAT did
fire chain-image. Same failure mode #148 fixed for release.yml ->
update-package-channels.yml.

- Rewrite header comment to describe the gate accurately.
- Add Validate secrets step mirroring release.yml's PAT check.
- Switch GH_TOKEN on the dispatch step to CHAIN_DISPATCH_TOKEN.

Closes #216.
@laradji
laradji merged commit 764241c into main May 7, 2026
4 checks passed
@laradji
laradji deleted the emdash/feat-anti-recursion-dispatch-scrape-pack-chain-image-workflow-010np branch May 7, 2026 17:00
laradji pushed a commit that referenced this pull request May 7, 2026
The `gh api .../runs/<id> --jq '.inputs.tag'` read in chain-image's
Resolve-tag step always returns null — the runs REST endpoint does NOT
expose workflow_dispatch inputs. Latent since #209; surfaced once #217
made chain-image actually fire.

Embed inputs.tag in scrape-pack.yml's top-level run-name (`scrape-pack
(v<x.y.z>)` or `scrape-pack (cache-warm)`), then parse it out of
`github.event.workflow_run.display_title` on the chain-image side.
Stable-tag filter and cache-warm gate preserved exactly.

Closes #218.
laradji added a commit that referenced this pull request May 7, 2026
The `gh api .../runs/<id> --jq '.inputs.tag'` read in chain-image's
Resolve-tag step always returns null — the runs REST endpoint does NOT
expose workflow_dispatch inputs. Latent since #209; surfaced once #217
made chain-image actually fire.

Embed inputs.tag in scrape-pack.yml's top-level run-name (`scrape-pack
(v<x.y.z>)` or `scrape-pack (cache-warm)`), then parse it out of
`github.event.workflow_run.display_title` on the chain-image side.
Stable-tag filter and cache-warm gate preserved exactly.

Closes #218.

Co-authored-by: Nacer Laradji <nacer.laradji@gmail.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

fix(ci): chain-release anti-recursion — GITHUB_TOKEN dispatch of scrape-pack suppresses chain-image workflow_run

1 participant