-
Notifications
You must be signed in to change notification settings - Fork 0
151 lines (133 loc) · 5.64 KB
/
combine-prs.yaml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
name: ci-combineprs
run-name: combine-prs [ ${{ inputs.branchPrefix }} ]
on:
workflow_dispatch:
inputs:
branchPrefix:
description: 'Branch prefix to find combinable PRs based on (ie, dependabot/ compose/ feat/ fix/ other)'
required: true
type: string
default: 'dependabot/'
mustBeGreen:
description: 'Combine PRs that are green? (dependabot context.status is unreachable so set to false)'
required: true
type: boolean
default: false
combineBranchName:
description: 'Name of the branch to combine PRs into'
required: true
default: 'combined-pr'
ignoreLabel:
description: 'Exclude PRs with this label'
required: true
default: 'nocombine'
jobs:
combine-prs:
runs-on: ubuntu-22.04
permissions:
contents: write
pull-requests: write
steps:
- uses: actions/github-script@v6 # v7 needs testing
id: fetch-branch-names
name: fetch-branch-names
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
script: |
const pulls = await github.paginate('GET /repos/:owner/:repo/pulls', {
owner: context.repo.owner,
repo: context.repo.repo
});
branches = [];
prs = [];
base_branch = null;
for (const pull of pulls) {
const branch = pull['head']['ref'];
console.log('Pull for branch: ' + branch);
if (branch.startsWith('${{ github.event.inputs.branchPrefix }}')) {
console.log('Branch matched: ' + branch);
statusOK = true;
if(${{ github.event.inputs.mustBeGreen }}) {
console.log('Checking green status: ' + branch);
const statuses = await github.paginate('GET /repos/{owner}/{repo}/commits/{ref}/status', {
owner: context.repo.owner,
repo: context.repo.repo,
ref: branch
});
if(statuses.length > 0) {
const latest_status = statuses[0]['state'];
console.log('Validating status: ' + latest_status);
if(latest_status != 'success') {
console.log('Discarding ' + branch + ' with status ' + latest_status);
statusOK = false;
}
}
}
console.log('Checking labels: ' + branch);
const labels = pull['labels'];
for(const label of labels) {
const labelName = label['name'];
console.log('Checking label: ' + labelName);
if(labelName == '${{ github.event.inputs.ignoreLabel }}') {
console.log('Discarding ' + branch + ' with label ' + labelName);
statusOK = false;
}
}
if (statusOK) {
console.log('Adding branch to array: ' + branch);
branches.push(branch);
prs.push('#' + pull['number'] + ' ' + pull['title']);
base_branch = pull['base']['ref'];
}
}
}
if (branches.length == 0) {
core.setFailed('No PRs/branches matched criteria');
return;
}
core.setOutput('base-branch', base_branch);
core.setOutput('prs-string', prs.join('\n'));
combined = branches.join(' ')
console.log('Combined: ' + combined);
return combined
- uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938 # v4.2.0
with:
ref: ${{ steps.fetch-branch-names.outputs.base-branch }}
fetch-depth: 0
- name: create-combined-branch
env:
BASE_BRANCH: ${{ steps.fetch-branch-names.outputs.base-branch }}
BRANCHES_TO_COMBINE: ${{ steps.fetch-branch-names.outputs.result }}
COMBINE_BRANCH_NAME: ${{ github.event.inputs.combineBranchName }}
run: |
echo "Branches to combine: $BRANCHES_TO_COMBINE"
sourcebranches="${BRANCHES_TO_COMBINE%\"}"
sourcebranches="${sourcebranches#\"}"
basebranch="${BASE_BRANCH%\"}"
basebranch="${basebranch#\"}"
git config pull.rebase false
git config user.name github-actions
git config user.email [email protected]
git branch $COMBINE_BRANCH_NAME $basebranch
git checkout $COMBINE_BRANCH_NAME
# merge all branches into the new branch
git pull origin $sourcebranches --no-edit
# push the new branch to the remote
git push origin $COMBINE_BRANCH_NAME
- uses: actions/github-script@v4 # v5-v6 have pulls.create problems that I couldn't resolve, have not tested v7 yet
name: create-combined-pr
env:
PRS_STRING: ${{ steps.fetch-branch-names.outputs.prs-string }}
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
script: |
const prString = process.env.PRS_STRING;
const body = 'This PR was created by the Combine PRs action by combining the following PRs:\n' + prString;
await github.pulls.create({
owner: context.repo.owner,
repo: context.repo.repo,
title: 'Combined PR [${{ github.event.inputs.branchPrefix }}*]',
head: '${{ github.event.inputs.combineBranchName }}',
base: '${{ steps.fetch-branch-names.outputs.base-branch }}',
body: body
});