Skip to content

Commit 6840eb7

Browse files
authored
ci: add auto-ready-for-review workflow (#9179)
1 parent 99cd4e7 commit 6840eb7

File tree

3 files changed

+133
-2
lines changed

3 files changed

+133
-2
lines changed
Lines changed: 118 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,118 @@
1+
name: Auto Ready for Review
2+
3+
on:
4+
workflow_run:
5+
workflows: ["Test", "Validate PR Title"]
6+
types: [completed]
7+
8+
jobs:
9+
auto-ready-for-review:
10+
runs-on: ubuntu-24.04
11+
if: github.event.workflow_run.event == 'pull_request'
12+
steps:
13+
- name: Check PR and all workflows status
14+
uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1
15+
with:
16+
script: |
17+
const prNumber = context.payload.workflow_run.pull_requests[0].number;
18+
console.log(`[INFO] Processing PR #${prNumber}`);
19+
20+
// Get PR info
21+
const { data: pr } = await github.rest.pulls.get({
22+
owner: context.repo.owner,
23+
repo: context.repo.repo,
24+
pull_number: prNumber
25+
});
26+
27+
console.log(`[INFO] PR #${prNumber} - Draft: ${pr.draft}, Labels: ${pr.labels.map(l => l.name).join(', ')}`);
28+
29+
// Check if PR has autoready label and is draft
30+
const hasAutoreadyLabel = pr.labels.some(label => label.name === 'autoready');
31+
32+
if (!pr.draft) {
33+
console.log(`[INFO] PR #${prNumber} is not draft, skipping`);
34+
return;
35+
}
36+
37+
if (!hasAutoreadyLabel) {
38+
console.log(`[INFO] PR #${prNumber} doesn't have autoready label, skipping`);
39+
return;
40+
}
41+
42+
// Get all workflow runs for this PR's head commit (head_sha)
43+
const { data: workflowRuns } = await github.rest.actions.listWorkflowRunsForRepo({
44+
owner: context.repo.owner,
45+
repo: context.repo.repo,
46+
head_sha: pr.head.sha,
47+
per_page: 100
48+
});
49+
50+
console.log(`[INFO] Found ${workflowRuns.workflow_runs.length} workflow runs for PR #${prNumber}`);
51+
52+
// Check workflow status
53+
const runningWorkflows = workflowRuns.workflow_runs.filter(run =>
54+
run.status === 'in_progress' || run.status === 'queued'
55+
);
56+
57+
const failedWorkflows = workflowRuns.workflow_runs.filter(run =>
58+
run.conclusion === 'failure' || run.conclusion === 'cancelled'
59+
);
60+
61+
const successfulWorkflows = workflowRuns.workflow_runs.filter(run =>
62+
run.conclusion === 'success'
63+
);
64+
65+
console.log(`[INFO] Workflow status - Running: ${runningWorkflows.length}, Failed: ${failedWorkflows.length}, Success: ${successfulWorkflows.length}`);
66+
67+
if (runningWorkflows.length > 0) {
68+
console.log(`[INFO] Some workflows are still running: ${runningWorkflows.map(w => w.name).join(', ')}`);
69+
return;
70+
}
71+
72+
if (failedWorkflows.length > 0) {
73+
console.log(`[INFO] Some workflows failed: ${failedWorkflows.map(w => w.name).join(', ')}`);
74+
return;
75+
}
76+
77+
console.log(`[INFO] All workflows passed! Marking PR #${prNumber} as ready for review...`);
78+
79+
// Mark PR as ready for review using GraphQL API
80+
// Reference: https://github.com/orgs/community/discussions/70061
81+
try {
82+
const mutation = `
83+
mutation MarkPullRequestReadyForReview($pullRequestId: ID!) {
84+
markPullRequestReadyForReview(input: { pullRequestId: $pullRequestId }) {
85+
pullRequest {
86+
id
87+
isDraft
88+
number
89+
}
90+
}
91+
}
92+
`;
93+
94+
const updateResult = await github.graphql(mutation, {
95+
pullRequestId: pr.node_id
96+
});
97+
98+
const isDraft = updateResult.markPullRequestReadyForReview.pullRequest.isDraft;
99+
console.log(`[SUCCESS] PR #${prNumber} marked as ready for review. Draft status: ${isDraft}`);
100+
} catch (error) {
101+
console.log(`[ERROR] Failed to mark PR #${prNumber} as ready for review: ${error.message}`);
102+
console.log(`[ERROR] Error details: ${JSON.stringify(error.response?.data || error, null, 2)}`);
103+
return;
104+
}
105+
106+
// Remove autoready label
107+
try {
108+
const labelResult = await github.rest.issues.removeLabel({
109+
owner: context.repo.owner,
110+
repo: context.repo.repo,
111+
issue_number: prNumber,
112+
name: 'autoready'
113+
});
114+
console.log(`[SUCCESS] autoready label removed from PR #${prNumber}. Status: ${labelResult.status}`);
115+
} catch (error) {
116+
console.log(`[WARNING] Could not remove autoready label from PR #${prNumber}: ${error.message}`);
117+
console.log(`[WARNING] Error details: ${JSON.stringify(error.response?.data || error, null, 2)}`);
118+
}

magefiles/magefile.go

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -436,7 +436,15 @@ func Clean() error {
436436
// Label updates labels
437437
func Label() error {
438438
mg.Deps(Tool{}.Install) // Install labeler
439-
return sh.RunV("labeler", "apply", "misc/triage/labels.yaml", "-l", "5")
439+
440+
args := []string{"apply", "misc/triage/labels.yaml", "-l", "5"}
441+
442+
// Add --repo flag if GITHUB_REPOSITORY environment variable is set
443+
if repo := os.Getenv("GITHUB_REPOSITORY"); repo != "" {
444+
args = append(args, "-r", repo)
445+
}
446+
447+
return sh.RunV("labeler", args...)
440448
}
441449

442450
type Docs mg.Namespace

misc/triage/labels.yaml

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -138,4 +138,9 @@ labels:
138138
# release
139139
- name: backport
140140
color: A8F7BC
141-
description: Backport PRs
141+
description: Backport PRs
142+
143+
# automation
144+
- name: autoready
145+
color: 1d76db
146+
description: Automatically mark PR as ready for review when all checks pass

0 commit comments

Comments
 (0)