-
Notifications
You must be signed in to change notification settings - Fork 4.1k
/
Copy pathassign-r2-priority.js
160 lines (136 loc) · 4.94 KB
/
assign-r2-priority.js
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
152
153
154
155
156
157
158
159
160
/**
* Processes open PRs every 6 hours during weekdays to identify and assign R2 priority. A PR qualifies
* for R2 when it has received approval but has failing or pending checks, regardless of its current
* priority or status. These PRs are either added to the project board with R2 priority and Ready status
* (if not already in board) or updated to R2 priority (if already in board with different priority).
*/
const { PRIORITIES, LABELS, STATUS, ...PROJECT_CONFIG } = require("./project-config");
const {
updateProjectField,
updateProjectDateField,
addItemToProject,
fetchProjectFields,
fetchOpenPullRequests,
fetchProjectItem,
} = require('./project-api');
module.exports = async ({ github }) => {
let allPRs = [];
let hasNextPage = true;
let cursor = null;
// Fetch all PRs using pagination
while (hasNextPage) {
const result = await fetchOpenPullRequests({
github,
org: PROJECT_CONFIG.org,
repo: PROJECT_CONFIG.repo,
cursor: cursor,
});
const pullRequests = result.organization.repository.pullRequests;
allPRs = allPRs.concat(pullRequests.nodes);
// Update pagination info
hasNextPage = pullRequests.pageInfo.hasNextPage;
cursor = pullRequests.pageInfo.endCursor;
}
console.log(`Total PRs fetched: ${allPRs.length}`);
// Get project fields
const projectFields = await fetchProjectFields({
github,
org: PROJECT_CONFIG.org,
number: PROJECT_CONFIG.projectNumber
});
const priorityField = projectFields.organization.projectV2.fields.nodes.find(
(field) => field.id === PROJECT_CONFIG.priorityFieldId
);
const statusField = projectFields.organization.projectV2.fields.nodes.find(
(field) => field.id === PROJECT_CONFIG.statusFieldId
);
const r2OptionId = priorityField.options.find(
(option) => option.name === PRIORITIES.R2
)?.id;
const readyStatusId = statusField.options.find(
(option) => option.name === STATUS.READY
)?.id;
for (const pr of allPRs) {
try {
console.log(`Processing PR #${pr.number}....`);
// Check PR status
const approvals = pr.reviews.nodes.filter(
(review) => review.state === "APPROVED"
);
if (approvals.length < 2) {
console.log(`Observed approval count: ${approvals.length}. Skipping as it is less than 2...`);
continue;
}
// Check status of checks
const checksState = pr.commits.nodes[0]?.commit.statusCheckRollup?.state;
const checksNotPassing = checksState !== "SUCCESS";
// Skip if PR checks is not passing
if (!checksNotPassing) {
console.log(`PR checks are failing. Skipping...`);
continue;
}
// Get all projects the PR added to
const result = await fetchProjectItem({
github,
contentId: pr.id
});
// Filter our specific project
const projectItem = result?.node?.projectItems?.nodes
?.find(item => item.project.id === PROJECT_CONFIG.projectId);
if (projectItem) {
// PR already in project
const currentPriority = projectItem.fieldValues.nodes
.find(fv => fv.field?.name === 'Priority')?.name;
if (currentPriority === PRIORITIES.R2) {
console.log(`PR #${pr.number} already has ${PRIORITIES.R2} priority. Skipping.`);
continue;
}
// Update priority only, maintain existing status
console.log(`Updating PR #${pr.number} from ${currentPriority} to ${PRIORITIES.R2} priority`);
await updateProjectField({
github,
projectId: PROJECT_CONFIG.projectId,
itemId: projectItem.id,
fieldId: PROJECT_CONFIG.priorityFieldId,
value: r2OptionId,
});
} else {
// Add new PR to project with R2 priority and Ready status
console.log(`Adding PR #${pr.number} to project with ${PRIORITIES.R2} priority`);
const addResult = await addItemToProject({
github,
projectId: PROJECT_CONFIG.projectId,
contentId: pr.id,
});
itemId = addResult.addProjectV2ItemById.item.id;
// Set priority, Ready status and current date for new items
await Promise.all([
updateProjectField({
github,
projectId: PROJECT_CONFIG.projectId,
itemId: itemId,
fieldId: PROJECT_CONFIG.priorityFieldId,
value: r2OptionId,
}),
updateProjectField({
github,
projectId: PROJECT_CONFIG.projectId,
itemId: itemId,
fieldId: PROJECT_CONFIG.statusFieldId,
value: readyStatusId,
}),
updateProjectDateField({
github,
projectId: PROJECT_CONFIG.projectId,
itemId: itemId,
fieldId: PROJECT_CONFIG.addedOnFieldId,
date: new Date().toISOString(),
})
]);
}
} catch (error) {
console.error(`Error processing PR #${pr.number}:`, error);
continue;
}
}
};