149 lines
5.3 KiB
YAML
149 lines
5.3 KiB
YAML
name: PR Check Command
|
|
|
|
on:
|
|
issue_comment:
|
|
types: [created]
|
|
|
|
jobs:
|
|
check-pr:
|
|
# Only run on PR comments that start with /check
|
|
if: github.event.issue.pull_request && startsWith(github.event.comment.body, '/check')
|
|
runs-on: ubuntu-latest
|
|
permissions:
|
|
pull-requests: write
|
|
issues: write
|
|
|
|
steps:
|
|
- name: Check PR requirements
|
|
uses: actions/github-script@v7
|
|
with:
|
|
script: |
|
|
const prNumber = context.payload.issue.number;
|
|
console.log(`Triggered by /check comment on PR #${prNumber}`);
|
|
|
|
// Fetch PR data
|
|
const { data: pr } = await github.rest.pulls.get({
|
|
owner: context.repo.owner,
|
|
repo: context.repo.repo,
|
|
pull_number: prNumber,
|
|
});
|
|
|
|
const prBody = pr.body || '';
|
|
const prTitle = pr.title || '';
|
|
const prAuthor = pr.user.login;
|
|
|
|
// Extract issue numbers
|
|
const issuePattern = /(?:close[sd]?|fix(?:e[sd])?|resolve[sd]?)?\s*#(\d+)/gi;
|
|
const allText = `${prTitle} ${prBody}`;
|
|
const matches = [...allText.matchAll(issuePattern)];
|
|
const issueNumbers = [...new Set(matches.map(m => parseInt(m[1], 10)))];
|
|
|
|
console.log(`PR #${prNumber}:`);
|
|
console.log(` Author: ${prAuthor}`);
|
|
console.log(` Found issue references: ${issueNumbers.length > 0 ? issueNumbers.join(', ') : 'none'}`);
|
|
|
|
if (issueNumbers.length === 0) {
|
|
const message = `## PR Closed - Requirements Not Met
|
|
|
|
This PR has been automatically closed because it doesn't meet the requirements.
|
|
|
|
**Missing:** No linked issue found.
|
|
|
|
**To fix:**
|
|
1. Create or find an existing issue for this work
|
|
2. Assign yourself to the issue
|
|
3. Re-open this PR and add \`Fixes #123\` in the description
|
|
|
|
**Why is this required?** See #472 for details.`;
|
|
|
|
await github.rest.issues.createComment({
|
|
owner: context.repo.owner,
|
|
repo: context.repo.repo,
|
|
issue_number: prNumber,
|
|
body: message,
|
|
});
|
|
|
|
await github.rest.pulls.update({
|
|
owner: context.repo.owner,
|
|
repo: context.repo.repo,
|
|
pull_number: prNumber,
|
|
state: 'closed',
|
|
});
|
|
|
|
core.setFailed('PR must reference an issue');
|
|
return;
|
|
}
|
|
|
|
// Check if PR author is assigned to any linked issue
|
|
let issueWithAuthorAssigned = null;
|
|
let issuesWithoutAuthor = [];
|
|
|
|
for (const issueNum of issueNumbers) {
|
|
try {
|
|
const { data: issue } = await github.rest.issues.get({
|
|
owner: context.repo.owner,
|
|
repo: context.repo.repo,
|
|
issue_number: issueNum,
|
|
});
|
|
|
|
const assigneeLogins = (issue.assignees || []).map(a => a.login);
|
|
if (assigneeLogins.includes(prAuthor)) {
|
|
issueWithAuthorAssigned = issueNum;
|
|
console.log(` Issue #${issueNum} has PR author ${prAuthor} as assignee`);
|
|
break;
|
|
} else {
|
|
issuesWithoutAuthor.push({
|
|
number: issueNum,
|
|
assignees: assigneeLogins
|
|
});
|
|
console.log(` Issue #${issueNum} assignees: ${assigneeLogins.length > 0 ? assigneeLogins.join(', ') : 'none'}`);
|
|
}
|
|
} catch (error) {
|
|
console.log(` Issue #${issueNum} not found`);
|
|
}
|
|
}
|
|
|
|
if (!issueWithAuthorAssigned) {
|
|
const issueList = issuesWithoutAuthor.map(i =>
|
|
`#${i.number} (assignees: ${i.assignees.length > 0 ? i.assignees.join(', ') : 'none'})`
|
|
).join(', ');
|
|
|
|
const message = `## PR Closed - Requirements Not Met
|
|
|
|
This PR has been automatically closed because it doesn't meet the requirements.
|
|
|
|
**PR Author:** @${prAuthor}
|
|
**Found issues:** ${issueList}
|
|
**Problem:** The PR author must be assigned to the linked issue.
|
|
|
|
**To fix:**
|
|
1. Assign yourself (@${prAuthor}) to one of the linked issues
|
|
2. Re-open this PR
|
|
|
|
**Why is this required?** See #472 for details.`;
|
|
|
|
await github.rest.issues.createComment({
|
|
owner: context.repo.owner,
|
|
repo: context.repo.repo,
|
|
issue_number: prNumber,
|
|
body: message,
|
|
});
|
|
|
|
await github.rest.pulls.update({
|
|
owner: context.repo.owner,
|
|
repo: context.repo.repo,
|
|
pull_number: prNumber,
|
|
state: 'closed',
|
|
});
|
|
|
|
core.setFailed('PR author must be assigned to the linked issue');
|
|
} else {
|
|
await github.rest.issues.createComment({
|
|
owner: context.repo.owner,
|
|
repo: context.repo.repo,
|
|
issue_number: prNumber,
|
|
body: `✅ PR requirements met! Issue #${issueWithAuthorAssigned} has @${prAuthor} as assignee.`,
|
|
});
|
|
console.log(`PR requirements met!`);
|
|
}
|