A powerful GitHub Action for automatically managing staging branches with configurable sync, reset, and PR labeling functionality.
- ✅ Auto-sync staging branch - Automatically syncs commits from main branch to staging branch
- ✅ Scheduled reset - Resets staging branch to main on a configurable schedule (default: every Sunday at midnight)
- ✅ PR labeling - Automatically stage PRs when labeled with
to-stage, and mark them asstagedwhen complete - ✅ Smart label management - Removes
stagedlabels when PRs are removed from staging or when commits are no longer staged - ✅ Manual sync detection - Detects when commits are manually added to staging and syncs if needed
- ✅ Fully configurable - All branch names, labels, and behaviors are configurable
Create a workflow file (e.g., .github/workflows/auto-staging.yml) in your repository:
name: Auto Staging
on:
# Scheduled reset every Sunday at midnight
schedule:
- cron: '0 0 * * 0' # Sunday midnight UTC
# Trigger on push to main or staging
push:
branches:
- main
- staging
# Trigger on PR events (including label events)
pull_request:
branches:
- main
types: [opened, reopened, synchronize, labeled, unlabeled]
# Allow manual triggering
workflow_dispatch:
jobs:
auto-staging:
runs-on: ubuntu-latest
permissions:
contents: write
pull-requests: write
issues: write
steps:
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
token: ${{ secrets.GITHUB_TOKEN }}
- name: Run Auto Staging
uses: Plexverse/auto-staging@v1
with:
main_branch: 'main'
staging_branch: 'staging'
to_stage_label: 'to-stage'
staged_label: 'staged'
github_token: ${{ secrets.GITHUB_TOKEN }}
enable_auto_sync: 'true'
enable_scheduled_reset: 'true'
enable_pr_labeling: 'true'All inputs are optional and have sensible defaults:
| Input | Description | Default | Required |
|---|---|---|---|
main_branch |
Name of the main branch | main |
No |
staging_branch |
Name of the staging branch | staging |
No |
to_stage_label |
Label to trigger staging a PR | to-stage |
No |
staged_label |
Label to mark a PR as staged | staged |
No |
github_token |
GitHub token for API calls | - | Yes |
reset_schedule |
Cron schedule for resetting staging branch | 0 0 * * 0 |
No |
enable_auto_sync |
Enable auto-sync of main branch commits to staging | true |
No |
enable_scheduled_reset |
Enable scheduled reset of staging branch | true |
No |
enable_pr_labeling |
Enable PR labeling functionality | true |
No |
When commits are pushed to the main branch, the action automatically:
- Checks if there are new commits in
mainthat aren't instaging - Merges those commits into
staging - Updates PR labels if any staged PRs are affected
On the configured schedule (default: Sunday midnight UTC), the action:
- Resets the
stagingbranch to matchmainexactly - Removes
stagedlabels from all PRs that were affected by the reset
When a PR is labeled with the to-stage label:
- The action fetches the current PR state from the API (to get up-to-date labels)
- Verifies the PR currently has the
to-stagelabel - Merges the PR into the
stagingbranch - Adds the
stagedlabel to the PR - If the merge fails (e.g., due to conflicts), the action posts a comment on the PR explaining the issue and doesn't add the
stagedlabel
Note: The action fetches current PR labels from the API (not from the event payload) to handle labels added after the PR was opened, since github.event.pull_request.labels only contains labels from when the PR was first created.
When a PR is reopened or synchronized:
- The action fetches the current PR state from the API
- Checks if the PR currently has the
stagedlabel - Verifies if all PR commits are still in the
stagingbranch - Removes the
stagedlabel if commits are no longer staged
When commits are manually pushed to the staging branch:
- The action detects the push event
- Checks if there are commits in
mainthat aren't instaging - Automatically syncs those commits if found
- name: Run Auto Staging
uses: Plexverse/auto-staging@v1
with:
main_branch: 'master'
staging_branch: 'develop'
github_token: ${{ secrets.GITHUB_TOKEN }}- name: Run Auto Staging
uses: Plexverse/auto-staging@v1
with:
to_stage_label: 'ready-for-staging'
staged_label: 'in-staging'
github_token: ${{ secrets.GITHUB_TOKEN }}- name: Run Auto Staging
uses: Plexverse/auto-staging@v1
with:
enable_scheduled_reset: 'false'
github_token: ${{ secrets.GITHUB_TOKEN }}- name: Run Auto Staging
uses: Plexverse/auto-staging@v1
with:
reset_schedule: '0 2 * * 1' # Every Monday at 2 AM UTC
github_token: ${{ secrets.GITHUB_TOKEN }}- name: Run Auto Staging
uses: Plexverse/auto-staging@v1
with:
enable_pr_labeling: 'false'
github_token: ${{ secrets.GITHUB_TOKEN }}The action requires the following permissions:
contents: write- To push changes to the staging branchpull-requests: write- To add/remove labels on PRsissues: write- To post comments on PRs (PRs are treated as issues in the GitHub API)
jq- The action will automatically installjqif it's not available- Git with proper authentication configured
- A GitHub token with appropriate permissions
The action will automatically create the staging branch from the main branch if it doesn't exist.
If a merge conflict occurs when syncing or staging a PR, the action will:
- Log a warning
- Abort the merge
- Not push any changes
- Post a comment on affected PRs explaining the conflict and how to resolve it
- For PR staging, not add the
stagedlabel
Ensure that:
- The
enable_pr_labelinginput is set totrue - The GitHub token has
pull-requests: writepermission - The labels (
to-stageandstaged) exist in your repository
This action is provided as-is. Modify as needed for your use case.
