-
Notifications
You must be signed in to change notification settings - Fork 0
ci(bump-callers): add the cursor-review-auto-label fleet + repair frozen caller pins (BE-4682) #81
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
mattmillerai
wants to merge
3
commits into
main
Choose a base branch
from
ci/auto-label-bump-fleet
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
+255
−11
Open
Changes from all commits
Commits
Show all changes
3 commits
Select commit
Hold shift + click to select a range
f9b0619
ci(bump-callers): add the cursor-review-auto-label fleet (BE-4682)
mattmillerai 7b360ed
fix(bump-auto-label): fail loudly when the main-tip lookup fails (BE-…
mattmillerai 91022c1
fix(bump-auto-label): precise staleness guard, scoped token, job time…
mattmillerai File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,200 @@ | ||
| name: Bump cursor-review-auto-label callers | ||
|
|
||
| # When the cursor-review-auto-label reusable workflow is updated on main, open a | ||
| # SHA-bump PR in every repo that pins a caller against it. PRs are opened by | ||
| # Cloud Code Bot so they are easy to filter and merge. | ||
| # | ||
| # WHY THIS FLEET EXISTS (BE-4682): auto-label had callers but no bumper. Its | ||
| # pins therefore never moved — every consumer stayed frozen on whatever SHA it | ||
| # was first wired to, drifting behind the reusable indefinitely. That is not a | ||
| # theoretical rot: the sibling groom fleet left its own caller | ||
| # (ci-groom.yml) off GROOM_CALLERS, the pin never bumped, and the caller | ||
| # eventually failed at startup against a reusable it was no longer compatible | ||
| # with. A reusable with callers and no bumper is the same trap with a longer | ||
| # fuse. | ||
| # | ||
| # This is a thin entrypoint over the shared bumper at | ||
| # .github/bump-callers/bump-callers.sh — the same script drives the | ||
| # cursor-review, agents-md-integrity, pr-size, assign-reviewers AND groom | ||
| # caller fleets. Keeping ONE implementation is deliberate: a forked copy is how | ||
| # other shared machinery in the org has drifted. The entrypoints differ only in | ||
| # their path-filter trigger and the parameters passed below. (They stay separate | ||
| # rather than a single matrix because their triggers differ — a | ||
| # cursor-review-auto-label.yml change must not spuriously bump the other fleets' | ||
| # callers, and vice versa.) | ||
| # | ||
| # NOTE ON THE PAIRING: auto-label is the companion to cursor-review.yml, but it | ||
| # is a SEPARATE fleet on purpose. The two reusables are pinned independently by | ||
| # consumers (many repos run cursor-review without auto-label), so folding them | ||
| # together would bump callers of one on a change to the other. | ||
| # | ||
| # The caller list is NOT hardcoded here. This repo is PUBLIC (workflow file and | ||
| # Actions run logs are both publicly viewable), and most callers are private, so | ||
| # their names must never appear in this file or its logs. The list lives in the | ||
| # repo-level Actions variable `AUTO_LABEL_CALLERS` (config, not a credential — a | ||
| # variable, not a secret, since secrets are write-only via the API) as a JSON | ||
| # array of {"repo","file","label"} objects, same shape as CURSOR_REVIEW_CALLERS. | ||
| # `bump-callers.sh` `::add-mask::`es every repo name before IT echoes anything. | ||
| # KNOWN GAP (shared by all six entrypoints, tracked separately): passing the | ||
| # roster through this step's `env:` means Actions prints the raw value in the | ||
| # step's env dump before the script — and its masking — ever runs. Closing it | ||
| # means reading the variable at run time (`gh variable get`) and masking it | ||
| # first, which needs a token permission this fleet does not mint today; it is a | ||
| # fleet-wide change, not one this entrypoint can make alone. Until then, treat | ||
| # the roster as visible in the public run log. | ||
| # Unlike the fleets seeded empty, this one is seeded NON-EMPTY (the | ||
| # callers already existed before the bumper did), so ALLOW_EMPTY is false below: | ||
| # an empty list here means the variable was clobbered, not that the fleet has no | ||
| # members, and failing loudly beats silently bumping nothing. | ||
| # | ||
| # Update flow — adding/removing a caller needs NO public commit: | ||
| # gh variable set AUTO_LABEL_CALLERS --repo Comfy-Org/github-workflows \ | ||
| # --body "$(jq -c . callers.json)" | ||
| # Keep the canonical callers.json in a PRIVATE infra/ops repo so variable edits | ||
| # have a reviewed source of truth; the org audit log records each edit. (The | ||
| # specific home repo is intentionally not named here — this file is public.) | ||
|
|
||
| on: | ||
| workflow_dispatch: {} # allow on-demand runs (e.g. to re-bump callers) | ||
| push: | ||
| branches: [main] | ||
| paths: | ||
| # cursor-review-auto-label.yml is entirely self-contained — it applies the | ||
| # review label inline via actions/github-script and loads no external | ||
| # prompt/script asset dir (unlike cursor-review/** or | ||
| # scripts/check-pr-size/**), and it exposes no `workflows_ref` input. So | ||
| # the workflow file itself is the only path that can change its behavior. | ||
| - .github/workflows/cursor-review-auto-label.yml | ||
|
|
||
| permissions: | ||
| contents: read | ||
|
|
||
| # Serialize runs of this fleet. The bumper pushes to a STABLE branch | ||
| # (ci/bump-auto-label) shared across runs, so two overlapping runs (a rapid | ||
| # second main push, or a push racing a manual re-run) would force-reset that | ||
| # branch and race the PR update — an older run finishing last could leave the | ||
| # committed diff pinned to a stale SHA. cancel-in-progress: false lets the | ||
| # running bump finish; GitHub keeps only the newest pending run, so the latest | ||
| # SHA always wins (BE-3882). | ||
| concurrency: | ||
| group: bump-auto-label-callers | ||
| cancel-in-progress: false | ||
|
|
||
| jobs: | ||
| bump: | ||
| # Guard against a workflow_dispatch run from a non-main ref: github.sha is | ||
| # the tip of whatever ref was selected, and the bumper force-resets a stable | ||
| # shared branch — a manual run from an older ref would pin every caller to a | ||
| # stale SHA (and run this job's script, with the App token minted below, | ||
| # from an unreviewed commit). The push trigger is already main-only, so this | ||
| # only ever skips stray manual runs. | ||
| if: github.ref == 'refs/heads/main' | ||
| runs-on: ubuntu-latest | ||
|
mattmillerai marked this conversation as resolved.
|
||
| # The job is a bounded loop of `git`/`gh` network calls; nothing here should | ||
| # take minutes. Without this a hung call would hold a runner for the default | ||
| # 6 hours (and, via the serializing concurrency group above, block every | ||
| # later bump behind it). | ||
| timeout-minutes: 20 | ||
| steps: | ||
| - name: Checkout | ||
| uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3 | ||
| with: | ||
| persist-credentials: false | ||
|
|
||
| - name: Generate Cloud Code Bot token | ||
| uses: actions/create-github-app-token@d72941d797fd3113feb6b93fd0dec494b13a2547 # v1.12.0 | ||
| id: token | ||
| with: | ||
| app-id: ${{ vars.APP_ID }} | ||
| private-key: ${{ secrets.CLOUD_CODE_BOT_PRIVATE_KEY }} | ||
| # `owner:` with no `repositories:` is deliberate and cannot be narrowed: | ||
| # the caller list is a runtime variable (see the header), so the repos | ||
| # this token must reach are not knowable at authoring time — and naming | ||
| # them here would leak private caller names into a public file. | ||
| # | ||
| # The PERMISSIONS can be narrowed without naming anything, so they are: | ||
| # unset, the minted token carries every permission the app holds on every | ||
| # repo it is installed on, far past what this bumper needs. It commits | ||
| # the rewritten caller file via the Git Data API (contents) and opens or | ||
| # updates the bump PR (pull-requests); `gh pr create --label` stamps the | ||
| # caller's label through the issues API (issues) — same trio, and the | ||
| # same reasoning, as the groom fleet's entrypoint. | ||
| owner: Comfy-Org | ||
|
mattmillerai marked this conversation as resolved.
|
||
| permission-contents: write | ||
| permission-pull-requests: write | ||
| permission-issues: write | ||
|
|
||
| - name: Bump SHA in caller repos | ||
| env: | ||
| GH_TOKEN: ${{ steps.token.outputs.token }} | ||
| NEW_SHA: ${{ github.sha }} | ||
| VAR_NAME: AUTO_LABEL_CALLERS | ||
| TAG: auto-label | ||
| WORKFLOW_FILE: cursor-review-auto-label.yml | ||
| # Seeded NON-EMPTY (the callers predate this fleet), so an empty list | ||
| # means the variable was clobbered — fail rather than no-op silently. | ||
| ALLOW_EMPTY: "false" | ||
| # JSON array of {"repo","file","label"} — see the header comment for the | ||
| # update flow. Kept in a variable (not the file) so private caller names | ||
| # never land in this public repo. NOTE: this env binding is itself the | ||
| # known log-exposure gap documented in the header — Actions dumps the | ||
| # step env before the script's `::add-mask::` runs. | ||
| CALLERS_JSON: ${{ vars.AUTO_LABEL_CALLERS }} | ||
|
mattmillerai marked this conversation as resolved.
|
||
| run: | | ||
| # The main-only ref guard above cannot catch a manual RE-RUN of an | ||
| # older main run: github.ref is refs/heads/main but github.sha is | ||
| # that run's original (now stale) commit, and the bumper would | ||
| # force-repin every caller to it. So establish the current main tip | ||
| # first; the guard below decides whether this run is genuinely stale. | ||
| # Don't pipe into `cut`: the pipeline would report cut's status, so a | ||
| # failed ls-remote (network blip, remote hiccup) yields an EMPTY | ||
| # main_tip that then compares unequal to github.sha and silently | ||
| # no-ops the whole fleet bump as if the run were stale. A lookup we | ||
| # couldn't perform is not evidence of staleness — fail loudly. | ||
| if ! ls_remote=$(git ls-remote origin refs/heads/main); then | ||
| echo "::error::Could not look up the current main tip (git ls-remote failed)" | ||
| exit 1 | ||
| fi | ||
| main_tip=${ls_remote%%$'\t'*} | ||
| if [[ -z "$main_tip" ]]; then | ||
| echo "::error::git ls-remote returned no SHA for refs/heads/main" | ||
| exit 1 | ||
| fi | ||
| WATCHED=.github/workflows/cursor-review-auto-label.yml | ||
| if [[ "$main_tip" != "$GITHUB_SHA" ]]; then | ||
|
mattmillerai marked this conversation as resolved.
|
||
| # main has moved on. That alone does NOT make this run stale: the | ||
| # push trigger is path-filtered to WATCHED, so an unrelated commit | ||
| # landing in the seconds between this run's trigger and this check | ||
| # starts NO run of its own. Skipping on a bare SHA mismatch would | ||
| # discard the only run for this change and leave every caller | ||
| # frozen — the exact pin-drift this fleet exists to prevent. | ||
| # What actually distinguishes a stale re-run is that WATCHED has | ||
| # CHANGED since: then a later commit did touch the path and does | ||
| # have its own run, which will pin the newer content. | ||
| if ! git fetch --depth=1 origin main; then | ||
| echo "::error::Could not fetch the current main tip to compare $WATCHED" | ||
| exit 1 | ||
| fi | ||
| main_tip=$(git rev-parse FETCH_HEAD) | ||
| tip_blob=$(git rev-parse --verify --quiet "FETCH_HEAD:$WATCHED" || true) | ||
| here_blob=$(git rev-parse --verify --quiet "HEAD:$WATCHED" || true) | ||
| if [[ -z "$tip_blob" ]]; then | ||
| echo "$WATCHED no longer exists on main ($main_tip) — decommissioned; nothing to bump" | ||
| exit 0 | ||
| fi | ||
| if [[ "$tip_blob" != "$here_blob" ]]; then | ||
| echo "github.sha $GITHUB_SHA is behind main ($main_tip) and $WATCHED changed since — stale run/re-run; the newer commit has its own run. Nothing to bump" | ||
| exit 0 | ||
| fi | ||
| echo "main moved to $main_tip since $GITHUB_SHA, but $WATCHED is unchanged — this run is still the only one for that change; proceeding" | ||
| fi | ||
| # The push path filter also matches a commit that DELETES the | ||
| # reusable workflow; bumping callers to a SHA where the file is gone | ||
| # would break every caller. Deletion means decommissioning — no-op. | ||
| # (This fleet has no run-time asset dir — the yml is self-contained — | ||
| # so unlike the sibling entrypoints only the workflow file is checked.) | ||
| if [[ ! -f .github/workflows/cursor-review-auto-label.yml ]]; then | ||
| echo "cursor-review-auto-label.yml absent at this SHA — decommissioned; nothing to bump" | ||
| exit 0 | ||
| fi | ||
| bash .github/bump-callers/bump-callers.sh | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.