Statly Code
Branch Protection

Branch Protection

Branch protection rules prevent unauthorized changes to important branches like main or release/*.

Creating a Protection Rule

Navigate to Settings

Go to Repository Settings → Branches

Add Rule

Click Add Rule and configure:

  1. Branch pattern: e.g., main, release/*, hotfix-*
  2. Requirements: Select which checks must pass
  3. Restrictions: Who can push directly

Protection Options

Pull Request Requirements

SettingDescriptionDefault
requirePullRequestRequire PR for all changestrue
requiredApprovalsMinimum approving reviews1
dismissStaleReviewsDismiss approvals when PR is updatedfalse
requireCodeOwnerReviewRequire review from CODEOWNERSfalse

Commit Requirements

SettingDescriptionDefault
requireSignedCommitsAll commits must be GPG signedfalse
requireLinearHistoryNo merge commits allowedfalse

Push Restrictions

SettingDescriptionDefault
allowForcePushAllow --force pushfalse
allowDeletionsAllow branch deletionfalse
restrictPushUsersOnly specific users can push[]

Status Check Requirements

SettingDescriptionDefault
requireStatusChecksRequire passing CI checksfalse
requiredStatusChecksList of required check contexts[]

Branch Patterns

Use glob patterns to match multiple branches:

PatternMatches
mainOnly main branch
release/*release/1.0, release/2.0, etc.
feature/**Any branch under feature/
hotfix-*hotfix-123, hotfix-bug, etc.

Required Status Checks

Status checks integrate with CI to block merges until tests pass:

{
  "requireStatusChecks": true,
  "requiredStatusChecks": ["ci/test", "ci/lint", "ci/build"]
}

CI Integration

When CI runs, it reports status to the branch protection system:

  1. PR is created/updated
  2. CI runs tests
  3. Status check is reported (pending → success/failure)
  4. Branch protection allows/blocks merge

Status Check States

StateDescriptionBlocks Merge?
pendingCheck is runningYes
successCheck passedNo
failureCheck failedYes
errorCheck erroredYes

CODEOWNERS Integration

When requireCodeOwnerReview is enabled:

  1. CODEOWNERS file is parsed on PR creation
  2. Owners are auto-assigned as reviewers
  3. At least one owner must approve
  4. Owner approval is required to merge
# CODEOWNERS file
* @team-lead
/src/api/** @backend-team
*.tsx @frontend-team

Bypass Permissions

Admins can configure bypass rules:

PermissionCan Bypass
Repository AdminAll rules
Org OwnerAll rules
Configured UsersSpecific rules
⚠️

Bypassing branch protection is logged in the audit trail.

API Reference

Get Protection Rules

GET /api/v1/code/repos/{org}/{repo}/branches/protection
 
# Response
{
  "rules": [
    {
      "id": "rule_xxx",
      "branchPattern": "main",
      "requirePullRequest": true,
      "requiredApprovals": 2,
      "requireStatusChecks": true,
      "requiredStatusChecks": ["ci/test"]
    }
  ]
}

Create Protection Rule

POST /api/v1/code/repos/{org}/{repo}/branches/protection
Content-Type: application/json
 
{
  "branchPattern": "main",
  "requirePullRequest": true,
  "requiredApprovals": 2,
  "dismissStaleReviews": true,
  "requireCodeOwnerReview": true,
  "requireStatusChecks": true,
  "requiredStatusChecks": ["ci/test", "ci/lint"],
  "requireSignedCommits": false,
  "allowForcePush": false,
  "allowDeletions": false
}

Update Protection Rule

PATCH /api/v1/code/repos/{org}/{repo}/branches/protection/{ruleId}
Content-Type: application/json
 
{
  "requiredApprovals": 3
}

Delete Protection Rule

DELETE /api/v1/code/repos/{org}/{repo}/branches/protection/{ruleId}

Best Practices

For Main Branch

{
  "branchPattern": "main",
  "requirePullRequest": true,
  "requiredApprovals": 2,
  "dismissStaleReviews": true,
  "requireCodeOwnerReview": true,
  "requireStatusChecks": true,
  "requiredStatusChecks": ["ci/test", "ci/lint", "ci/build"],
  "allowForcePush": false,
  "allowDeletions": false
}

For Release Branches

{
  "branchPattern": "release/*",
  "requirePullRequest": true,
  "requiredApprovals": 1,
  "requireSignedCommits": true,
  "allowForcePush": false,
  "allowDeletions": false
}

For Feature Branches

Feature branches typically don't need protection rules, but you can add lightweight rules:

{
  "branchPattern": "feature/**",
  "requirePullRequest": false,
  "allowForcePush": true,
  "allowDeletions": true
}

Plan Limits

PlanProtection Features
FreeBasic (require PR, approvals)
ProAdvanced (status checks, CODEOWNERS)
EnterpriseFull (signed commits, restrict users)