Add GitHub workflow to automatically add PRs targeting 1.8.x branch to project 15

Co-authored-by: stnguyen90 <1477010+stnguyen90@users.noreply.github.com>
This commit is contained in:
copilot-swe-agent[bot]
2025-09-03 00:24:24 +00:00
co-authored by stnguyen90
parent 23ea5f8fc5
commit 6364c77170
+186
View File
@@ -0,0 +1,186 @@
---
name: Add to Project
on:
pull_request:
types: [opened, reopened]
branches: ['1.8.x']
jobs:
add-to-project:
name: Add PR or linked issue to project
runs-on: ubuntu-latest
permissions:
contents: read
pull-requests: read
issues: read
organization-projects: write
steps:
- name: Check if PR is from Core team
id: check-core-team
uses: actions/github-script@v7
with:
script: |
const { data: user } = await github.rest.users.getByUsername({
username: context.payload.pull_request.user.login
});
// Check if user is a member of the Appwrite organization
try {
const { data: membership } =
await github.rest.orgs.getMembershipForUser({
org: 'appwrite',
username: context.payload.pull_request.user.login
});
// Check if user has admin or write permissions (Core team)
const isCoreTeam = membership.role === 'admin' ||
(membership.state === 'active' &&
['admin', 'member'].includes(membership.role));
console.log(
`User ${context.payload.pull_request.user.login} ` +
`is core team: ${isCoreTeam}`
);
core.setOutput('is-core-team', isCoreTeam);
return isCoreTeam;
} catch (error) {
console.log(
`User ${context.payload.pull_request.user.login} ` +
`is not a member of appwrite org`
);
core.setOutput('is-core-team', false);
return false;
}
- name: Get linked issues
id: get-linked-issues
if: steps.check-core-team.outputs.is-core-team == 'true'
uses: actions/github-script@v7
with:
script: |
const prNumber = context.payload.pull_request.number;
// Get PR body and check for linked issues
const prBody = context.payload.pull_request.body || '';
// Look for common patterns that indicate linked issues
const patterns = [
/(?:close[sd]?|fix(?:e[sd])?|resolve[sd]?)\s+#(\d+)/gi,
/(?:close[sd]?|fix(?:e[sd])?|resolve[sd]?)\s+(?:https?:\/\/github\.com\/[^\/]+\/[^\/]+\/issues\/)(\d+)/gi,
/#(\d+)/g
];
const linkedIssues = new Set();
for (const pattern of patterns) {
let match;
while ((match = pattern.exec(prBody)) !== null) {
linkedIssues.add(parseInt(match[1]));
}
}
const linkedIssuesArray = Array.from(linkedIssues);
console.log(`Found linked issues: ${linkedIssuesArray.join(', ')}`);
core.setOutput('linked-issues', JSON.stringify(linkedIssuesArray));
core.setOutput('has-linked-issues', linkedIssuesArray.length > 0);
return linkedIssuesArray;
- name: Add PR to project (no linked issues)
if: >
steps.check-core-team.outputs.is-core-team == 'true' &&
steps.get-linked-issues.outputs.has-linked-issues == 'false'
uses: actions/github-script@v7
with:
script: |
const projectId = 15; // GitHub project ID
const prNumber = context.payload.pull_request.number;
try {
// Add PR to project using GraphQL
const mutation = `
mutation($projectId: ID!, $contentId: ID!) {
addProjectV2ItemById(input: {
projectId: $projectId,
contentId: $contentId
}) {
item {
id
}
}
}
`;
// Get the PR node ID
const { data: pr } = await github.rest.pulls.get({
owner: context.repo.owner,
repo: context.repo.repo,
pull_number: prNumber
});
await github.graphql(mutation, {
projectId: `PVT_kwDOAAH2fM4Afpv_`,
contentId: pr.node_id
});
console.log(`Successfully added PR #${prNumber} to project`);
} catch (error) {
console.error(`Failed to add PR to project: ${error.message}`);
core.setFailed(`Failed to add PR to project: ${error.message}`);
}
- name: Add linked issues to project
if: >
steps.check-core-team.outputs.is-core-team == 'true' &&
steps.get-linked-issues.outputs.has-linked-issues == 'true'
uses: actions/github-script@v7
with:
script: |
const projectId = 15;
const linkedIssues = JSON.parse(
'${{ steps.get-linked-issues.outputs.linked-issues }}'
);
for (const issueNumber of linkedIssues) {
try {
// Get the issue node ID
const { data: issue } = await github.rest.issues.get({
owner: context.repo.owner,
repo: context.repo.repo,
issue_number: issueNumber
});
// Add issue to project using GraphQL
const mutation = `
mutation($projectId: ID!, $contentId: ID!) {
addProjectV2ItemById(input: {
projectId: $projectId,
contentId: $contentId
}) {
item {
id
}
}
}
`;
await github.graphql(mutation, {
projectId: `PVT_kwDOAAH2fM4Afpv_`,
contentId: issue.node_id
});
console.log(
`Successfully added issue #${issueNumber} to project`
);
} catch (error) {
console.error(
`Failed to add issue #${issueNumber} to project: ` +
`${error.message}`
);
// Continue with other issues even if one fails
}
}