Skip to content

Feat/auto subtitle generation #2671

Feat/auto subtitle generation

Feat/auto subtitle generation #2671

Workflow file for this run

name: 🔍 PR Validator
on:
pull_request_target:
types: [opened, edited, synchronize, reopened]
permissions:
pull-requests: write
issues: write
concurrency:
group: pr-validator-${{ github.event.pull_request.number }}
cancel-in-progress: true
jobs:
validate:
runs-on: ubuntu-latest
steps:
- name: Validate PR format
uses: actions/github-script@v9
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
script: |
const pr = context.payload.pull_request;
const owner = context.repo.owner;
const repo = context.repo.repo;
const number = pr.number;
const body = pr.body || '';
const title = pr.title || '';
const username = pr.user.login;
if (pr.user.type === 'Bot') return;
const warnings = [];
// Check conventional title
const conventionalRegex = /^(feat|fix|docs|style|refactor|perf|test|build|ci|chore|security)(\(.+\))?: .+/i;
if (!conventionalRegex.test(title)) {
warnings.push('⚠️ Use a conventional PR title. Examples:\n - `feat: add dark mode support`\n - `fix: resolve aria label missing on slider`\n - `docs: add deployment guide to README`');
}
// Check linked issue
const issueRegex = /(close|closes|closed|fix|fixes|fixed|resolve|resolves|resolved)\s+#\d+/i;
if (!issueRegex.test(body)) {
warnings.push('⚠️ No linked issue found. Add `Closes #<issue-number>` to your PR description.');
}
// Check if targeting main (warn, don't block)
if (pr.base.ref !== 'main') {
warnings.push(`⚠️ Your PR targets \`${pr.base.ref}\` instead of \`main\`. Please check your base branch.`);
}
const MARKER = '<!-- pr-validator-reframe-v1 -->';
const { data: comments } = await github.rest.issues.listComments({
owner, repo, issue_number: number, per_page: 100
});
const existingComment = comments.find(c => c.body.includes(MARKER));
let commentBody;
if (warnings.length > 0) {
commentBody = [
MARKER,
`## ⚠️ PR Format Issues — @${username}`,
``,
`Please fix the following before your PR can be reviewed:`,
``,
...warnings.map(w => `- ${w}`),
``,
`Push new commits after fixing — this comment will update automatically.`,
``,
`📖 [CONTRIBUTING.md](https://github.com/${owner}/${repo}/blob/main/CONTRIBUTING.md)`,
].join('\n');
} else {
commentBody = [
MARKER,
`## ✅ PR Format Check Passed — @${username}`,
``,
`Basic format checks passed. A maintainer will review your code changes.`,
``,
`_This does not mean the PR is approved — it just means the format is correct._`,
].join('\n');
}
if (existingComment) {
await github.rest.issues.updateComment({
owner, repo, comment_id: existingComment.id, body: commentBody
});
} else {
await github.rest.issues.createComment({
owner, repo, issue_number: number, body: commentBody
});
}