Mergify Merge Queue#
The Mergify Merge Queue is an automated pull request management system implemented in the EvilBit-Labs/opnDossier repository that provides intelligent, tiered PR processing based on contributor type and trust level. The system uses five author-specific merge queues with tailored CI requirements to differentiate between bot PRs (dosubot and Dependabot), maintainer PRs, and external contributor PRs, ensuring appropriate review depth and automation levels for each category while enforcing strict quality standards across all contributions.
Configured through a declarative .mergify.yml file, the merge queue system addresses a common challenge in sole-maintainer or small-team projects: how to balance the need for thorough review of external contributions with the efficiency of automated dependency updates and self-merges for maintainer code. The implementation enforces Conventional Commits format (except for bot PRs), uses tiered CI requirements (lint-only for low-risk bot changes, full CI for code changes), and maintains PR freshness by requiring pull requests to be within 10 commits of the base branch.
All merged commits use squash merge strategy to maintain a clean, linear commit history on the main branch while preserving the PR title as the final commit message. This approach simplifies git history navigation and ensures every merged commit follows the project's commit message standards without requiring individual commit cleanup during PR development.
Architecture and Design#
Five Author-Specific Queues with Tiered CI#
The Mergify configuration implements five distinct merge queues. Automatic queueing is configured via auto_merge_conditions in merge_protections_settings rather than per-queue settings, allowing PRs to automatically enter their queues when conditions match. This architecture enables different CI requirements based on author type and change scope while maintaining consistent quality gates appropriate for each contribution category.
Queue Overview:
| Queue Name | Author | Additional Conditions | CI Requirements |
|---|---|---|---|
dosubot | dosubot[bot] | None | Lint only |
dependabot-workflows | dependabot[bot] | Only .github/workflows/ files | Lint only |
dependabot | dependabot[bot] | Any files | Full CI (11 checks) |
maintainer | unclesp1d3r | Requires lgtm label | Full CI (11 checks) |
external | Anyone else | Requires approval | Full CI (11 checks) |
All queues use merge_method: squash and share the base condition base = main and label != do-not-merge.
Queue 1: dosubot (Bot-Generated PRs)#
This queue handles PRs from dosubot[bot], a trusted bot account that generates automated PRs for documentation and maintenance tasks. Bot-generated changes require minimal validation since they follow predictable patterns.
Queue Conditions:
base = mainauthor = dosubot[bot]label != do-not-merge
Merge Requirements:
check-success = Lint
Auto-Approval: Dosubot PRs are auto-approved with the message "Automatically approved by Mergify".
Rationale: Bot-generated PRs are low-risk and highly predictable, requiring only linting validation to catch syntax errors.
Queue 2: dependabot-workflows (Workflow-Only Dependency Updates)#
This queue handles Dependabot PRs that modify only files within .github/workflows/. Workflow dependency updates (typically GitHub Actions version bumps) are lower risk than code dependencies since they don't affect application behavior.
Queue Conditions:
base = mainauthor = dependabot[bot]-files ~= ^(?!\.github/workflows/)- Negative regex matches ONLY workflow fileslabel != do-not-merge
Merge Requirements:
check-success = Lint
Auto-Approval: Dependabot PRs are auto-approved with the message "Automatically approved by Mergify".
File Scope Logic: The regex ^(?!\.github/workflows/) uses negative lookahead to match files that do NOT start with .github/workflows/. The -files prefix inverts this condition, so the rule matches when all files ARE within .github/workflows/.
Rationale: GitHub Actions version updates rarely introduce breaking changes and don't affect application code, making them safe to merge with minimal validation.
Queue 3: dependabot (Code Dependency Updates)#
This queue handles Dependabot PRs that include files outside .github/workflows/, meaning they modify application code, build configuration, or dependencies. These changes require full CI validation to ensure compatibility and prevent regressions.
Queue Conditions:
base = mainauthor = dependabot[bot]label != do-not-merge
Merge Requirements:
check-success = Lintcheck-success = Buildcheck-success = Test (ubuntu-latest, stable)check-success = Test (ubuntu-latest, oldstable)check-success = Test (macos-latest, stable)check-success = Test (macos-latest, oldstable)check-success = Test (windows-latest, stable)check-success = Test (windows-latest, oldstable)check-success = Integration Testscheck-success = Coveragecheck-success = codecov/project
Auto-Approval: Dependabot PRs are auto-approved with the message "Automatically approved by Mergify".
Queue Priority: This queue takes precedence over dependabot-workflows when a Dependabot PR includes both workflow and non-workflow files. The broader condition (any files) matches after the more specific condition (workflow-only) is evaluated.
Rationale: Code dependency updates can introduce breaking changes, API incompatibilities, or behavioral regressions, requiring comprehensive testing across all supported platforms.
Queue 4: maintainer (Maintainer Self-Merge)#
This queue addresses the sole-maintainer self-merge problem by allowing the maintainer (unclesp1d3r) to explicitly signal readiness for merge through the lgtm ("looks good to me") label. This workflow enables the maintainer to self-approve their own work while maintaining an audit trail and ensuring CI validation.
Queue Conditions:
base = mainauthor = unclesp1d3r- Sole maintainer accountlabel = lgtm- Explicit approval signallabel != do-not-merge
Merge Requirements:
check-success = Lintcheck-success = Buildcheck-success = Test (ubuntu-latest, stable)check-success = Test (ubuntu-latest, oldstable)check-success = Test (macos-latest, stable)check-success = Test (macos-latest, oldstable)check-success = Test (windows-latest, stable)check-success = Test (windows-latest, oldstable)check-success = Integration Testscheck-success = Coveragecheck-success = codecov/project
No external approval required - The maintainer can queue their own PRs without waiting for another reviewer, solving a common bottleneck in sole-maintainer projects.
Rationale: GitHub's branch protection rules prevent repository owners from approving their own PRs. The lgtm label provides an explicit signal that the maintainer has reviewed their own code and considers it ready to merge, while still requiring full CI validation.
Queue 5: external (Community Contributions)#
This queue ensures community contributions receive proper human oversight before entering the merge queue, maintaining code quality and security standards for external contributions.
Queue Conditions:
base = mainauthor != dependabot[bot]- Not a bot accountauthor != dosubot[bot]- Not a bot accountauthor != unclesp1d3r- Not the maintainerbranch-protection-review-decision = APPROVED- GitHub approval statuslabel != do-not-merge
Merge Requirements:
check-success = Lintcheck-success = Buildcheck-success = Test (ubuntu-latest, stable)check-success = Test (ubuntu-latest, oldstable)check-success = Test (macos-latest, stable)check-success = Test (macos-latest, oldstable)check-success = Test (windows-latest, stable)check-success = Test (windows-latest, oldstable)check-success = Integration Testscheck-success = Coveragecheck-success = codecov/project
Human approval required - External PRs cannot enter the merge queue without explicit maintainer code review and approval via GitHub's review system.
Rationale: External contributions require human review to assess code quality, security implications, and architectural fit. The branch-protection-review-decision = APPROVED condition ensures GitHub branch protection rules are satisfied before queueing.
Automatic Queueing Behavior#
Automatic queue entry is configured through the auto_merge_conditions setting in merge_protections_settings, which defines conditions that trigger automatic queueing for PRs. When these global conditions match, PRs are automatically added to their respective queues based on author and other criteria. There are no explicit queue: actions in the pull_request_rules section—the queueing happens automatically through condition evaluation.
How It Works:
- When a PR is opened or updated, Mergify evaluates the
auto_merge_conditionsinmerge_protections_settings - If a PR matches the conditions, it is automatically enqueued to the appropriate queue based on author
- PRs remain in the queue until
merge_conditionsare satisfied - Once merge conditions pass, the PR is automatically merged with squash strategy
This architecture eliminates the need for manual queue management and reduces the complexity of pull request routing rules.
Pull Request Rules#
The configuration includes two pull request rules that operate independently of the queue system.
Auto-Approval Rules#
Two rules provide automatic approval for bot PRs:
Rule 1: Auto-approve dosubot PRs
- Condition:
author = dosubot[bot]andbase = main - Action: Approve with message "Automatically approved by Mergify"
Rule 2: Auto-approve dependabot PRs
- Condition:
author = dependabot[bot]andbase = main - Action: Approve with message "Automatically approved by Mergify"
These approval actions satisfy GitHub's branch protection requirements for PRs, allowing the merge queues to proceed without manual approval.
Automatic PR Update Rule#
Rule: "Keep PRs up to date with main"
This rule automatically keeps all non-conflicted, non-draft PRs synchronized with the latest main branch changes, preventing stale PRs from accumulating.
Update Conditions:
base = main- Target branch is main-conflict- No merge conflicts present-draft- Not a draft PR
Behavior: When these conditions are met, Mergify automatically updates the PR branch with the latest changes from main. Unlike the previous configuration, this rule no longer excludes Dependabot PRs or requires the do-not-merge label check—it applies universally to all PRs meeting the basic criteria.
Conflict Handling: When merge conflicts occur, the -conflict condition prevents automatic updates. PRs with conflicts require manual developer intervention to resolve conflicts before Mergify will resume automatic updates.
Merge Protections and Quality Gates#
The configuration implements four merge protection rules that prevent PRs from merging if they don't meet quality standards. These protections apply to all merge attempts, including manual merges that might bypass the queue.
Protection 1: Conventional Commit Format (Excluding Bots)#
Rule: "Enforce conventional commit"
This protection enforces Conventional Commits v1.0.0 format on PR titles for non-bot contributors. Since the merge queue uses squash merge strategy, the PR title becomes the final commit message in the main branch.
Applies When:
base = mainauthor != dependabot[bot]- Excludes Dependabotauthor != dosubot[bot]- Excludes dosubot
Validation Pattern: Regex pattern
^(fix|feat|docs|style|refactor|perf|test|build|ci|chore|revert)(?:\(.+\))?:
Rationale: Bot PRs often use automated commit messages that may not follow conventional commit format. Excluding bots from this check prevents unnecessary CI failures while maintaining commit message quality for human-authored contributions.
Required Format: <type>(<scope>): <description>
Valid Types:
feat- New featuresfix- Bug fixesdocs- Documentation changesstyle- Code formattingrefactor- Code refactoringperf- Performance improvementstest- Test additions/changesbuild- Build system changesci- CI/CD changeschore- Maintenance tasksrevert- Revert previous commits
Scope Guidance: Documentation states scopes are required, though the regex makes them technically optional. Recommended scopes include: parser, converter, audit, cli, model, plugin, builder, display, config, docs, schema.
Example Valid Titles:
feat(parser): add support for OPNsense 24.1 config formatfix(converter): handle empty VLAN configurations gracefullydocs(readme): update installation instructionsperf(converter): optimize markdown generation
Protection 2: Full CI Check Requirements#
This protection requires all CI checks to pass before merging. It activates for non-bot authors OR when Dependabot PRs include files outside .github/workflows/.
Note: The codecov/patch commit status check was removed from merge requirements because it does not reliably post on all PR heads, which can cause Mergify Merge Protections to remain pending indefinitely even after all other CI checks complete. Coverage requirements remain enforced through the GitHub Actions Coverage job (which is still required) and the codecov/project check.
Applies When:
base = main- AND one of:
- Non-bot authors (
author != dependabot[bot]ANDauthor != dosubot[bot]) - OR Dependabot with non-workflow changes (
author = dependabot[bot]ANDfiles ~= ^(?!\.github/workflows/))
- Non-bot authors (
Required CI Checks (from ci.yml workflow):
- Lint (ubuntu-latest) - golangci-lint v2.9 validation
- Build (ubuntu-latest) - Cross-compilation for FreeBSD, Linux, macOS, Windows
- Test (ubuntu-latest, stable) - Full test suite with race detection on current stable Go
- Test (ubuntu-latest, oldstable) - Full test suite with race detection on previous stable Go
- Test (macos-latest, stable) - Full test suite with race detection on current stable Go
- Test (macos-latest, oldstable) - Full test suite with race detection on previous stable Go
- Test (windows-latest, stable) - Smoke tests only on current stable Go (for performance reasons)
- Test (windows-latest, oldstable) - Smoke tests only on previous stable Go (for performance reasons)
- Integration Tests (ubuntu-latest) - Integration test suite with 5m timeout
- Coverage (ubuntu-latest) - Code coverage reporting to Codecov
- codecov/project - Codecov project coverage gate (80% minimum)
Go Version Matrix: Tests run on both stable (current Go release) and oldstable (previous Go release), matching Go's upstream support policy. This ensures compatibility with the two most recent stable Go versions (N and N-1).
CI Check Naming: CI check names in Mergify must match the name: field in workflow jobs (e.g., Lint, Build, Test (ubuntu-latest, stable)), NOT the job ID (lint, build, test).
DCO Sign-Off: DCO (Developer Certificate of Origin) sign-off is enforced by a GitHub App, not a CI check. There is no DCO check name in the CI workflow.
Fail-Fast Strategy: All jobs except Lint depend on Lint passing first, creating a fail-fast pipeline that provides quick feedback on code quality issues.
Protection 3: Lint-Only for Bot Workflow PRs#
Rule: "Lint must pass for bot workflow PRs"
This protection requires only the Lint check to pass for bot PRs that modify only workflow files.
Applies When:
base = main- AND one of:
author = dosubot[bot](all dosubot PRs)- OR
author = dependabot[bot]AND-files ~= ^(?!\.github/workflows/)(only workflow files)
Required CI Checks:
check-success = Lint
Rationale: Workflow-only changes and bot-generated PRs have minimal risk and don't affect application behavior, so comprehensive testing is unnecessary. Lint validation catches syntax errors and configuration issues.
Protection 4: PR Freshness Requirement#
Rule: "Do not merge outdated PRs"
This protection prevents merging significantly outdated code by requiring PRs to be reasonably current with the base branch.
Freshness Requirement: #commits-behind <= 10
PRs that fall more than 10 commits behind the main branch must be updated (manually or via auto-update rule) before they can merge.
Universal Emergency Brake: do-not-merge Label#
The do-not-merge label appears as a blocking condition in all five queue definitions, providing a universal mechanism to pause any PR from entering its respective merge queue.
Blocked Actions When Label Present:
- dosubot queue entry
- dependabot-workflows queue entry
- dependabot queue entry
- maintainer queue entry
- external queue entry
Use Cases: The label provides an escape hatch for situations requiring manual intervention, such as coordinating dependent PRs, waiting for upstream fixes, or pausing during incident response.
Integration with CodeRabbit AI Review#
CodeRabbit AI-assisted code review is configured through a 516-line configuration file that integrates with the merge workflow. Acknowledging CodeRabbit findings is mandatory before merging any pull request, creating a critical checkpoint in the merge workflow.
CodeRabbit provides automatic reviews for all PRs to the main branch (excluding drafts and WIP PRs) with path-specific review instructions that provide specialized focus for different code areas. The system integrates with 51 analysis tools including golangci-lint, shellcheck, markdownlint, yamllint, gitleaks, checkov, semgrep, and actionlint.
Developer Workflow#
For Maintainers#
- Create PR targeting main branch
- Wait for CI checks to pass (all 11 checks for code changes)
- Review and acknowledge CodeRabbit findings (mandatory)
- Add
lgtmlabel to signal readiness - PR automatically enters maintainer queue when conditions match
- PR is squash-merged with title as commit message when merge conditions are satisfied
For External Contributors#
- Create PR targeting main branch
- Ensure PR title follows Conventional Commits format
- Sign all commits with DCO (
git commit -s) - Wait for CI checks to pass (all 11 checks)
- Request review from maintainer
- Maintainer reviews and approves PR via GitHub review system
- PR automatically enters external queue when
branch-protection-review-decision = APPROVED - PR is squash-merged when queue processes it
For Dependabot Updates#
Dependabot monitors four package ecosystems with weekly automated updates:
- Dependabot creates PR for dependency update
- Mergify auto-approves the PR
- CI checks run automatically
- PR automatically enters appropriate queue when conditions match:
dependabot-workflowsqueue if only.github/workflows/files modified (lint only)dependabotqueue if other files modified (full CI required)
- PR is squash-merged with no human intervention once checks pass
Manual Override: Maintainers can add the do-not-merge label to pause any Dependabot PR that requires special attention.
For Dosubot Updates#
- Dosubot creates PR for automated task (documentation, maintenance)
- Mergify auto-approves the PR
- Lint check runs automatically
- PR automatically enters dosubot queue when conditions match
- PR is squash-merged when lint passes
Complete Merge Pipeline Requirements#
The complete merge criteria documented in Pipeline v2 Compliance includes:
- Pass all linters (golangci-lint with 70+ rules)
- Pass format checks (gofumpt, goimports)
- Pass all tests with race detection across both stable and oldstable Go versions, with codecov gates at 80% minimum (for code changes)
- Acknowledge CodeRabbit.ai findings (mandatory checkpoint)
- Pass security gates (OSSF Scorecard, vulnerability scanning)
- Use valid Conventional Commits format (except for bot PRs)
- Pass license compliance (FOSSA)
- Obtain appropriate approvals based on PR author:
- Bots: Auto-approved by Mergify
- Maintainer:
lgtmlabel self-approval - External: Maintainer code review via GitHub
- DCO sign-off on all commits (enforced by GitHub App)
Monitoring and Maintenance#
The OSSF Scorecard workflow runs every Saturday at 08:32 UTC to assess the overall quality and security posture, including validation of merge queue effectiveness. Results are uploaded to the GitHub Security tab for visibility.
Benefits and Design Rationale#
Author-Specific Queue Routing: The five-queue architecture provides precise routing based on PR author and file scope, eliminating the need for complex conditional logic in pull request rules while maintaining clear separation of concerns.
Tiered CI Requirements: Low-risk changes (bot-generated PRs, workflow-only updates) require only linting, while code changes require comprehensive testing. This balance reduces CI resource consumption while maintaining quality assurance where it matters.
Fully Automated Bot Updates: Dosubot and Dependabot PRs are auto-approved and automatically queued, eliminating manual review and merge of routine updates while still maintaining safety through automated CI validation.
Sole-Maintainer Self-Merge Solution: The maintainer queue solves the common problem where sole maintainers cannot approve their own PRs in GitHub's standard branch protection. The explicit lgtm label provides an audit trail while enabling efficient self-merge.
Security-First External Contributions: The external queue ensures human review of all external code through GitHub's branch protection system before automatic queueing, providing transparent status through automated queue management.
Automatic Queue Entry: Automatic queueing is configured through auto_merge_conditions in merge_protections_settings, eliminating manual queue management—PRs are automatically routed to the appropriate queue based on author and conditions, reducing configuration complexity.
Clean Git History: Squash merge strategy maintains a linear, readable git history where every commit on main branch represents a complete feature or fix with a properly formatted commit message.
Related Concepts#
- Conventional Commits: Standardized commit message format specification
- Squash Merge: Git merge strategy that combines all PR commits into a single commit
- Branch Protection Rules: GitHub feature for enforcing quality gates on protected branches
- Dependabot: GitHub's automated dependency update service
- CI/CD Pipelines: Automated testing and deployment workflows
- Code Review Automation: AI-assisted code review systems like CodeRabbit
- Developer Certificate of Origin (DCO): Lightweight process for tracking contributions
Relevant Code Files#
| File Path | Description | Key Content |
|---|---|---|
.mergify.yml | Primary Mergify configuration | Five author-specific queues with tiered CI, autoqueue behavior, merge protections, auto-approval rules |
.github/workflows/ci.yml | CI workflow definition | Eleven CI checks: Lint, Build, Test x6 (3 platforms × 2 Go versions), Integration Tests, Coverage, plus codecov/project gate |
.coderabbit.yaml | CodeRabbit AI review configuration | 516-line configuration with path-specific instructions, 51 tool integrations |
CONTRIBUTING.md | Contributor guidelines | Commit format examples, DCO requirements, PR submission workflow |
docs/pipeline-v2-compliance.md | Complete pipeline requirements | Full merge criteria including CodeRabbit acknowledgment requirement |
.github/dependabot.yml | Dependabot configuration | Weekly dependency scanning for Go modules, GitHub Actions, Docker, Dev Containers |
.github/workflows/scorecard.yml | OSSF Scorecard workflow | Weekly security assessment including merge queue validation |
AGENTS.md | AI agent guidelines | Commit message format rules, repository roles, Mergify queue documentation, CI check naming requirements |
docs/development/standards.md | Development standards | Formal Conventional Commits specification with examples |