Add branch protection ruleset as code#1992
Add branch protection ruleset as code#1992nicolasnoble wants to merge 1 commit intogrumpycoders:mainfrom
Conversation
Store the main branch required status checks and protection rules in a JSON file that can be imported via the GitHub API, replacing manual UI configuration. Drops the stale macos-intel-build-and-test check. Signed-off-by: Nicolas 'Pixel' Noble <nicolas@nobis-crew.org>
📝 WalkthroughWalkthroughA new GitHub branch ruleset configuration file is added at Changes
Estimated code review effort🎯 1 (Trivial) | ⏱️ ~5 minutes Poem
🚥 Pre-merge checks | ✅ 3✅ Passed checks (3 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 1
🧹 Nitpick comments (1)
.github/rulesets/main.json (1)
1-74: Test the ruleset import before applying to main.After correcting the status check contexts, test the import command safely before enforcing on the main branch:
- First, validate the JSON syntax:
jq empty .github/rulesets/main.json- Consider testing with a temporary branch pattern first by modifying line 7 to
"include": ["test-*"]and verifying with a test branch- Or use a dry-run approach by checking existing rulesets first:
gh api repos/grumpycoders/pcsx-redux/rulesets- Only after verification, import the actual ruleset for the main branch
This prevents accidentally blocking all PRs due to misconfigured status checks.
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In @.github/rulesets/main.json around lines 1 - 74, Validate and test the ruleset JSON and import process before applying to the default branch: run a JSON syntax check on the document and confirm the "ref_name" include value (currently "~DEFAULT_BRANCH") is correct; temporarily change "ref_name"."include" to "test-*" and apply to a test branch to verify the "required_status_checks" array and contexts behave as expected; alternatively list existing rulesets via the API (e.g., using gh api) to perform a dry-run validation before importing; only restore "ref_name"."include" back to "~DEFAULT_BRANCH" and import the ruleset to enforce on main once verified.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In @.github/rulesets/main.json:
- Around line 44-63: Update the status check context strings to match GitHub
Actions' reported names so the required checks map to actual workflow job names:
replace "build-openbios" with "macOS CI / build-openbios", "build" with "Linux
CI / build", "coverage" with "Linux CI coverage / coverage", "cross-arm64" with
"Linux CI cross / cross-arm64", "asan" with "Linux CI asan / asan", and
"toolchain" with "Linux CI toolchain / toolchain" for the entries that share
integration_id 15368 so the contexts match the workflow "workflow-name / job-id"
format and allow the checks to pass.
---
Nitpick comments:
In @.github/rulesets/main.json:
- Around line 1-74: Validate and test the ruleset JSON and import process before
applying to the default branch: run a JSON syntax check on the document and
confirm the "ref_name" include value (currently "~DEFAULT_BRANCH") is correct;
temporarily change "ref_name"."include" to "test-*" and apply to a test branch
to verify the "required_status_checks" array and contexts behave as expected;
alternatively list existing rulesets via the API (e.g., using gh api) to perform
a dry-run validation before importing; only restore "ref_name"."include" back to
"~DEFAULT_BRANCH" and import the ruleset to enforce on main once verified.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 71adcb2d-090f-4935-b7bd-eeef844284f1
📒 Files selected for processing (1)
.github/rulesets/main.json
| { | ||
| "context": "build-openbios", | ||
| "integration_id": 15368 | ||
| }, | ||
| { | ||
| "context": "build", | ||
| "integration_id": 15368 | ||
| }, | ||
| { | ||
| "context": "coverage", | ||
| "integration_id": 15368 | ||
| }, | ||
| { | ||
| "context": "cross-arm64", | ||
| "integration_id": 15368 | ||
| }, | ||
| { | ||
| "context": "asan", | ||
| "integration_id": 15368 | ||
| }, |
There was a problem hiding this comment.
🧩 Analysis chain
🏁 Script executed:
#!/bin/bash
# Description: Extract workflow names and job IDs to determine correct status check contexts
echo "=== GitHub Actions Workflows and Jobs ==="
echo
for workflow in .github/workflows/*.yml .github/workflows/*.yaml; do
if [ -f "$workflow" ]; then
echo "File: $workflow"
echo -n " Workflow name: "
gawk '/^name:/ {gsub(/^name: */, ""); gsub(/"/, ""); print; exit}' "$workflow"
echo " Job IDs:"
gawk '/^jobs:/,/^[^ ]/ {if ($0 ~ /^ [a-zA-Z0-9_-]+:$/) {gsub(/:/, ""); gsub(/^ /, ""); print " - " $0}}' "$workflow"
echo
fi
doneRepository: grumpycoders/pcsx-redux
Length of output: 1043
🏁 Script executed:
#!/bin/bash
# Extract job definitions from workflow files more reliably
echo "=== Job Extraction from Workflows ==="
echo
for workflow in .github/workflows/macos-build.yml .github/workflows/linux-build.yml .github/workflows/linux-coverage.yml .github/workflows/linux-asan.yml .github/workflows/linux-cross.yml .github/workflows/linux-toolchain.yml; do
if [ -f "$workflow" ]; then
echo "File: $(basename $workflow)"
echo -n " Workflow name: "
grep "^name:" "$workflow" | head -1 | sed 's/^name: *//; s/"//g'
echo " Jobs:"
# Use a more robust approach: find job IDs and check for explicit 'name:' fields
python3 << 'PYSCRIPT'
import sys
import re
workflow = sys.argv[1]
with open(workflow) as f:
content = f.read()
# Parse YAML-like structure
lines = content.split('\n')
in_jobs = False
current_job = None
for i, line in enumerate(lines):
if line.startswith('jobs:'):
in_jobs = True
continue
if in_jobs and line and not line[0].isspace():
break
if in_jobs and re.match(r'^ [a-zA-Z0-9_-]+:', line):
current_job = line.strip().rstrip(':')
job_name = None
# Look ahead for explicit 'name:' field
for j in range(i+1, min(i+10, len(lines))):
if re.match(r'^ name:', lines[j]):
job_name = lines[j].split('name:')[1].strip().strip("'\"")
break
if re.match(r'^ [a-zA-Z0-9_-]+:', lines[j]):
break
if job_name:
print(f" - {current_job} (name: {job_name})")
else:
print(f" - {current_job}")
PYSCRIPT
fi
doneRepository: grumpycoders/pcsx-redux
Length of output: 1148
🏁 Script executed:
cat -n .github/rulesets/main.json | grep -A 2 -B 2 '"context"'Repository: grumpycoders/pcsx-redux
Length of output: 1273
🏁 Script executed:
echo "=== macos-build.yml jobs ===" && sed -n '/^jobs:/,/^[^ ]/p' .github/workflows/macos-build.yml | head -20
echo ""
echo "=== linux-build.yml jobs ===" && sed -n '/^jobs:/,/^[^ ]/p' .github/workflows/linux-build.yml | head -20
echo ""
echo "=== linux-coverage.yml jobs ===" && sed -n '/^jobs:/,/^[^ ]/p' .github/workflows/linux-coverage.yml | head -20
echo ""
echo "=== linux-asan.yml jobs ===" && sed -n '/^jobs:/,/^[^ ]/p' .github/workflows/linux-asan.yml | head -20
echo ""
echo "=== linux-cross.yml jobs ===" && sed -n '/^jobs:/,/^[^ ]/p' .github/workflows/linux-cross.yml | head -20
echo ""
echo "=== linux-toolchain.yml jobs ===" && sed -n '/^jobs:/,/^[^ ]/p' .github/workflows/linux-toolchain.yml | head -20Repository: grumpycoders/pcsx-redux
Length of output: 4057
🏁 Script executed:
for workflow in .github/workflows/macos-build.yml .github/workflows/linux-build.yml .github/workflows/linux-coverage.yml .github/workflows/linux-asan.yml .github/workflows/linux-cross.yml .github/workflows/linux-toolchain.yml; do
echo "=== $(basename $workflow) ==="
# Extract job section and check for 'name:' fields at job level (4 spaces indent)
sed -n '/^jobs:/,/^[^ ]/p' "$workflow" | grep -E "^ [a-zA-Z0-9_-]+:|^ name:" | head -10
echo ""
doneRepository: grumpycoders/pcsx-redux
Length of output: 395
🏁 Script executed:
# Check if there's any Windows build workflow in GitHub Actions
ls -la .github/workflows/ | grep -i windows
echo ""
echo "Windows build checks in ruleset:"
grep -B 1 -A 1 '"integration_id": 9426' .github/rulesets/main.jsonRepository: grumpycoders/pcsx-redux
Length of output: 404
🏁 Script executed:
# Verify the exact behavior by checking GitHub Actions documentation
# Also double-check if any of the jobs have name: fields deeper in their definitions
for job_section in "build-openbios" "build" "coverage" "asan" "cross-arm64" "toolchain"; do
echo "=== Checking for 'name:' in job definitions ==="
grep -n "name:" .github/workflows/*.yml | grep -i "$job_section" | head -5
doneRepository: grumpycoders/pcsx-redux
Length of output: 1474
🏁 Script executed:
# Check macos-build.yml for build-openbios job definition
echo "=== macos-build.yml: build-openbios job ==="
sed -n '/^ build-openbios:/,/^ [a-z]/p' .github/workflows/macos-build.yml | head -20
echo ""
echo "=== linux-build.yml: build job ==="
sed -n '/^ build:/,/^ [a-z]/p' .github/workflows/linux-build.yml | head -20
echo ""
echo "=== linux-coverage.yml: coverage job ==="
sed -n '/^ coverage:/,/^ [a-z]/p' .github/workflows/linux-coverage.yml | head -20Repository: grumpycoders/pcsx-redux
Length of output: 2126
Critical: Status check names won't match GitHub Actions reporting.
The status check context names for GitHub Actions jobs (integration_id 15368) don't match how GitHub actually reports them. When a workflow job has no explicit name: field, GitHub reports the check as "workflow-name / job-id", not just "job-id".
Based on the workflow configurations:
- Line 45:
"build-openbios"should be"macOS CI / build-openbios" - Line 49:
"build"should be"Linux CI / build" - Line 53:
"coverage"should be"Linux CI coverage / coverage" - Line 57:
"cross-arm64"should be"Linux CI cross / cross-arm64" - Line 61:
"asan"should be"Linux CI asan / asan" - Line 65:
"toolchain"should be"Linux CI toolchain / toolchain"
Without correction, these required checks will never pass and PRs will be permanently blocked from merging.
🔧 Proposed fix
{
- "context": "build-openbios",
+ "context": "macOS CI / build-openbios",
"integration_id": 15368
},
{
- "context": "build",
+ "context": "Linux CI / build",
"integration_id": 15368
},
{
- "context": "coverage",
+ "context": "Linux CI coverage / coverage",
"integration_id": 15368
},
{
- "context": "cross-arm64",
+ "context": "Linux CI cross / cross-arm64",
"integration_id": 15368
},
{
- "context": "asan",
+ "context": "Linux CI asan / asan",
"integration_id": 15368
},
{
- "context": "toolchain",
+ "context": "Linux CI toolchain / toolchain",
"integration_id": 15368
}🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.
In @.github/rulesets/main.json around lines 44 - 63, Update the status check
context strings to match GitHub Actions' reported names so the required checks
map to actual workflow job names: replace "build-openbios" with "macOS CI /
build-openbios", "build" with "Linux CI / build", "coverage" with "Linux CI
coverage / coverage", "cross-arm64" with "Linux CI cross / cross-arm64", "asan"
with "Linux CI asan / asan", and "toolchain" with "Linux CI toolchain /
toolchain" for the entries that share integration_id 15368 so the contexts match
the workflow "workflow-name / job-id" format and allow the checks to pass.
Store the main branch required status checks and protection rules in a JSON file
that can be imported via the GitHub API, replacing manual UI configuration.
To apply:
gh api --method POST -H "Accept: application/vnd.github+json" /repos/grumpycoders/pcsx-redux/rulesets --input .github/rulesets/main.jsonChanges from current UI config:
macos-intel-build-and-testcheck