Skip to content

Commit bea4c6c

Browse files
authored
ci: use reusable auto-approve from Aswincloud/.github (#10)
Replace the duplicated ~113-line workflow with a thin caller. Logic now lives once in Aswincloud/.github/.github/workflows/auto-approve.yml and is invoked via workflow_call with secrets: inherit.
1 parent 5335230 commit bea4c6c

1 file changed

Lines changed: 4 additions & 101 deletions

File tree

.github/workflows/auto-approve.yml

Lines changed: 4 additions & 101 deletions
Original file line numberDiff line numberDiff line change
@@ -1,113 +1,16 @@
11
name: Auto-approve admin PRs
22

3-
# Automatically approve a pull request when its author is a member of the
4-
# Aswincloud/admins team. It ONLY approves — it never merges, so you stay in
5-
# control of when to merge and can push more changes first. This workflow
6-
# re-fires on each push; whether that dismisses a prior approval depends on the
7-
# repo's stale-review-dismissal setting (off on this repo).
8-
#
9-
# Two identities, split by a hard GitHub constraint:
10-
# - Membership read -> "Aswincloud Bot" GitHub App (short-lived token minted
11-
# per run; needs Members: Read). Replaces the old ORG_READ_TOKEN PAT.
12-
# - The approval -> WRITE_ACCESS_PAT, a real write-collaborator USER.
13-
# This is REQUIRED: GitHub does not count an app/bot review toward a
14-
# ruleset's required-approval count — only a user-with-write review does.
15-
# (We proved this: the app's approval left reviewDecision=REVIEW_REQUIRED.)
16-
# Secrets: APP_ID, APP_PRIVATE_KEY (app) and WRITE_ACCESS_PAT (approver).
17-
#
18-
# pull_request_target runs in the BASE repo context (so the secrets are
19-
# available even for fork PRs). Safe here: the job never checks out or runs the
20-
# PR's code — it only calls the GitHub API.
21-
3+
# Thin caller — the logic lives in the org-level reusable workflow so it's
4+
# defined once and reused everywhere. See Aswincloud/.github.
225
on:
236
pull_request_target:
247
types: [opened, reopened, ready_for_review, synchronize]
258

26-
permissions: {} # the App token carries the perms; the built-in token needs none
27-
28-
# One run per PR; a newer event supersedes an in-flight one.
299
concurrency:
3010
group: auto-approve-${{ github.event.pull_request.number }}
3111
cancel-in-progress: true
3212

3313
jobs:
3414
approve:
35-
runs-on: ubuntu-latest
36-
# Skip drafts — approve once it's a real review candidate.
37-
if: github.event.pull_request.draft == false
38-
steps:
39-
# Mint a short-lived installation token for the Aswincloud Bot app.
40-
# owner (no repositories:) => an org-level token that can read org teams
41-
# AND act on this org's repos.
42-
- name: Mint app token
43-
id: app
44-
uses: actions/create-github-app-token@bcd2ba49218906704ab6c1aa796996da409d3eb1 # v3.2.0
45-
with:
46-
app-id: ${{ secrets.APP_ID }}
47-
private-key: ${{ secrets.APP_PRIVATE_KEY }}
48-
owner: ${{ github.repository_owner }}
49-
50-
# 1) Is the PR author an ACTIVE member of the admins team?
51-
- name: Check admins-team membership
52-
id: member
53-
env:
54-
GH_TOKEN: ${{ steps.app.outputs.token }}
55-
AUTHOR: ${{ github.event.pull_request.user.login }}
56-
ORG: Aswincloud
57-
TEAM: admins
58-
run: |
59-
set -euo pipefail
60-
state="$(gh api "orgs/${ORG}/teams/${TEAM}/memberships/${AUTHOR}" \
61-
--jq '.state' 2>/dev/null || true)"
62-
if [ "${state}" = "active" ]; then
63-
echo "✓ @${AUTHOR} is an active member of @${ORG}/${TEAM}."
64-
echo "is_admin=true" >> "$GITHUB_OUTPUT"
65-
else
66-
echo "↷ @${AUTHOR} is not an active member of @${ORG}/${TEAM} — nothing to do."
67-
echo "is_admin=false" >> "$GITHUB_OUTPUT"
68-
fi
69-
70-
# 2) Approve the PR — only when the author is an admin.
71-
# This uses WRITE_ACCESS_PAT (a real write-collaborator USER), not the
72-
# app token, on purpose: GitHub does NOT count an app/bot review toward
73-
# a ruleset's required-approval count — only a review from a user with
74-
# write access satisfies it. The approval is all this step does; it
75-
# never merges, so you stay in control of WHEN it merges and can push
76-
# further changes first. This workflow re-fires on each push; whether a prior
77-
# approval is dismissed depends on the stale-review setting.
78-
- name: Approve the PR
79-
if: steps.member.outputs.is_admin == 'true'
80-
env:
81-
GH_TOKEN: ${{ secrets.WRITE_ACCESS_PAT }}
82-
REPO: ${{ github.repository }}
83-
PR: ${{ github.event.pull_request.number }}
84-
AUTHOR: ${{ github.event.pull_request.user.login }}
85-
HEAD_SHA: ${{ github.event.pull_request.head.sha }}
86-
ORG: Aswincloud
87-
TEAM: admins
88-
run: |
89-
set -euo pipefail
90-
91-
ME="$(gh api user --jq '.login')"
92-
93-
# Don't stack reviews: if this user already approved this exact commit,
94-
# stop. (Re-runs on `synchronize` then become no-ops.)
95-
already="$(gh api "repos/${REPO}/pulls/${PR}/reviews" --paginate \
96-
--jq "[.[] | select(.user.login==\"${ME}\" and .state==\"APPROVED\" and .commit_id==\"${HEAD_SHA}\")] | length")"
97-
if [ "${already}" -gt 0 ]; then
98-
echo "↷ Already approved ${HEAD_SHA} as @${ME} — skipping."
99-
exit 0
100-
fi
101-
102-
# GitHub forbids approving your OWN PR, so if the token's user is the
103-
# author, comment instead of failing.
104-
if [ "${ME}" = "${AUTHOR}" ]; then
105-
echo "↷ Token user (@${ME}) is the PR author — GitHub blocks self-approval; leaving a note."
106-
gh pr comment "${PR}" --repo "${REPO}" \
107-
--body "Auto-approve skipped: @${AUTHOR} is an admin, but the approver account is the author and GitHub doesn't allow approving your own PR." || true
108-
exit 0
109-
fi
110-
111-
gh pr review "${PR}" --repo "${REPO}" --approve \
112-
--body "Auto-approved: @${AUTHOR} is a member of @${ORG}/${TEAM}."
113-
echo "✓ Approved PR #${PR} as @${ME}."
15+
uses: Aswincloud/.github/.github/workflows/auto-approve.yml@main
16+
secrets: inherit

0 commit comments

Comments
 (0)