Skip to content

Commit 84ebd36

Browse files
committed
ci: add conventional commit PR title check and PR-base validation
Adds .github/workflows/lint-pr.yaml with two checks: 1. Conventional Commits: validates the PR title using amannn/action-semantic-pull-request (matches the pattern used in scale-agentex and agentex). Bypassable via the skip-conventional-commit-check label for automation that needs it. 2. PR base validation: fails on PRs targeting main, with exemptions for known automation accounts (stainless-app, release-please, github-actions, dependabot) and an opt-out via the target-main label. Encourages developer PRs to target next, where Stainless codegen and release-please integrate, while keeping main accessible for hotfixes.
1 parent cf249b9 commit 84ebd36

1 file changed

Lines changed: 68 additions & 0 deletions

File tree

.github/workflows/lint-pr.yaml

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
name: Lint PR
2+
3+
on:
4+
pull_request:
5+
types:
6+
- opened
7+
- edited
8+
- synchronize
9+
- reopened
10+
- labeled
11+
- unlabeled
12+
13+
jobs:
14+
validate-pr-title:
15+
name: Validate PR title (Conventional Commits)
16+
runs-on: ubuntu-latest
17+
permissions:
18+
statuses: write
19+
pull-requests: read
20+
steps:
21+
- uses: amannn/action-semantic-pull-request@48f256284bd46cdaab1048c3721360e808335d50 # v6.1.1
22+
env:
23+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
24+
with:
25+
types: |
26+
feat
27+
fix
28+
docs
29+
style
30+
refactor
31+
test
32+
chore
33+
ci
34+
build
35+
perf
36+
revert
37+
requireScope: false
38+
# Allow skipping this check with a label (e.g. for automated/bot PRs)
39+
ignoreLabels: |
40+
skip-conventional-commit-check
41+
42+
validate-pr-base:
43+
name: Validate PR base branch
44+
runs-on: ubuntu-latest
45+
if: github.event.pull_request.base.ref == 'main'
46+
permissions:
47+
pull-requests: read
48+
steps:
49+
- name: Check base branch
50+
env:
51+
PR_AUTHOR: ${{ github.event.pull_request.user.login }}
52+
HAS_LABEL: ${{ contains(github.event.pull_request.labels.*.name, 'target-main') }}
53+
run: |
54+
# Exempt automated PRs (Stainless codegen, release-please, dependabot, etc.)
55+
case "$PR_AUTHOR" in
56+
stainless-app|stainless-app[bot]|release-please[bot]|github-actions[bot]|dependabot[bot])
57+
echo "PR is from automation ($PR_AUTHOR); allowing PR targeting main."
58+
exit 0
59+
;;
60+
esac
61+
62+
if [ "$HAS_LABEL" = "true" ]; then
63+
echo "Found 'target-main' label; allowing PR targeting main."
64+
exit 0
65+
fi
66+
67+
echo "::error title=PR should target 'next'::PRs should target the 'next' branch by default. The 'main' branch is reserved for release-please and Stainless automation. If this PR is an intentional hotfix or automation exception, add the 'target-main' label to bypass this check, or re-target the PR base to 'next'."
68+
exit 1

0 commit comments

Comments
 (0)