# Overview **PullApprove is an alternative to CODEOWNERS, combining code ownership with approval requirements. It's designed to work for individual teams or entire organizations, across multiple repos or inside large monorepos.** For many large companies, code review is a strict requirement for compliance or regulatory purposes. PullApprove is designed to enforce these requirements in a highly customizable and scalable way, without becoming a burden on developers. For the developer: - **Low-friction** - For the authors and reviewers, the day-to-day experience does not drastically change from what they're used to. They still discuss, review, and approve PRs using the official GitHub/GitLab/Bitbucket products. - **Automatic** - As soon as a PR is opened, the appropriate reviewers are automatically requested and everyone is reminded of the process to get the PR merged. - **Clear** - Designed to bring clarity at every step of the way — from the `CODEREVIEW.toml` layout to the PR comments and statuses. For the organization: - **Customizable** - A more configurable review assignment and approval requirement system than GitHub/GitLab/Bitbucket provide. - **Scalable** - Designed to scale across hundreds of repos, inside of large monorepos, and for high volumes of activity. - **Auditable** - The *entire configuration* is stored in the repo, so it can be easily audited using existing git tooling. ## `CODEREVIEW.toml` PullApprove is configured directly in each repo with a `CODEREVIEW.toml` file. This file defines review `scopes`, which are path-based rules for who needs to review a change. A simple example: ```toml # CODEREVIEW.toml [[scopes]] name = "admins" paths = ["**/*"] reviewers = ["admin1", "admin2"] request = 1 require = 1 [[scopes]] name = "app" paths = ["app/**/*"] reviewers = ["dev1", "dev2", "dev3", "dev4"] request = 2 require = 1 ``` When a change is evaluated, files are matched to scopes based on their paths. ```console $ git diff --name-only README.md app/package.json $ pullapprove match --diff README.md -> global app/package.json -> app ``` Once this change is opened as a pull request, the scopes are used to `request` (or not request) reviewers and `require` (or not require) their approvals. When all scopes are satisfied, the PR gets a "success" status. ### Scopes (basic) - [`name`](./config/scopes/name.md) - the unique name of the scope - [`description`](./config/scopes/description.md) - a human-readable description of the scope - [`reviewers`](./config/scopes/reviewers.md) - who can approve changes in this scope - [`request`](./config/scopes/request.md) - how many reviewers to request - [`require`](./config/scopes/require.md) - how many approvals are needed - [`paths`](./config/scopes/paths.md) - which files are in this scope ### Scopes (advanced) - [`instructions`](./config/scopes/instructions.md) - additional instructions for reviewers - [`ownership`](./config/scopes/ownership.md) - how scopes are combined - [`reviewed-for`](./config/scopes/reviewed-for.md) - require explicit scope review (GitHub only) - [`alternates`](./config/scopes/alternates.md) - additionally allowed reviewers that aren't requested - [`labels`](./config/scopes/labels.md) - label syncing for scopes - [`code`](./config/scopes/code.md) - which lines of code match this scope - [`authors`](./config/scopes/authors.md) - which PR sauthors match this scope - [`author-value`](./config/scopes/author-value.md) - implicit approval by the PR author ### Other root settings - [`aliases`](./config/aliases.md) - groups of reviewers that can be used in scopes - [`branches`](./config/branches.md) - when PullApprove runs - [`large_scale_change`](./config/large-scale-change.md) - special handling of refactors and other large diffs - [`template`](./config/template.md) - mark a file as a template ## Comparison of code review tooling | Feature | v5 | [v3](https://v3-docs.pullapprove.com/) | [v4 (GUI)](https://4.pullapprove.com/docs/) | [GitHub
CODEOWNERS](https://docs.github.com/en/repositories/managing-your-repositorys-settings-and-features/customizing-your-repository/about-code-owners) | [GitLab
CODEOWNERS](https://docs.gitlab.com/ee/user/project/codeowners/)| [Bitbucket
CODEOWNERS](https://support.atlassian.com/bitbucket-cloud/docs/set-up-and-use-code-owners/) | [Kubernetes
OWNERS](https://www.kubernetes.dev/docs/guide/owners/) | | --- | --- | --- | --- | --- | --- | --- | --- | | Config-as-code | ✅ | ✅ | ❌ | ✅ | ✅ | ✅ | ✅ | | Path-based assignment | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | | Line-based assignment | ✅ | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Label-based assignment | ✅ | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Branch-based assignment | ? | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Expression-based assignment | ❌ | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Implicit author approvals | ✅ | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Implicit co-author approvals | ✅ | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Per-team/scope approval requirements | ✅ | ✅ | ✅ | ❌ | ✅ | ❌ | ❌ | | Request N reviewers | ✅ | ✅ | ✅ | ✅ | ❌ | ✅ | ❌ | | PR labeling | ✅ | ✅ | ✅ | ❌ | ❌ | ❌ | ✅ | | Eligible, unrequested reviewers | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | | Config sharing | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | | Multiple config files | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | | Ownership hierarchy | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | | Ownership coverage | ? | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | | Review instructions | ✅ | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Unavailable reviewers | ? | ✅ | ❌ | ✅ | ❌ | ❌ | ❌ | | Hotfix/bypass | ? | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Post-merge reviews | ? | ❌ | ✅ | ❌ | ❌ | ❌ | ❌ | | Phased reviews | ? | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | | Review nudge/reminder | ? | ❌ | ✅ | ❌ | ❌ | ❌ | ❌ | | Suggested owner changes | ? | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ |