> For the complete documentation index, see [llms.txt](https://developer.harness.io/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://developer.harness.io/code-repository/use-harness-code/pull-requests/merge-queue/set-up-merge-queue.md).

# Set Up Merge Queue

Configure the branch rule, Harness CI pipeline, and MergeQueue trigger that a Harness Code repository needs before it can use Merge Queue.

Merge Queue is configured per repository, because the required checks and the pipeline that produces them are repository-specific. This topic covers the branch rule, the pipeline, and the MergeQueue trigger, then validates the result with a test pull request. Go to [Merge Queue Overview](/code-repository/use-harness-code/pull-requests/merge-queue.md) to review the model before you configure it.

## Before you begin

Confirm the following before you create the branch rule:

* **A Harness CI pipeline:** the repository has a pipeline that clones the repository and runs the tests you want to gate merges on.
* **A known check identifier:** you know the exact identifier the pipeline reports. A Harness CI check commonly takes the form `<pipeline-identifier>-<stage-identifier>`, so a `budget` pipeline with a `verify` stage reports `budget-verify`. Confirm the value from a successful run rather than assuming it.
* **Reliable checks:** the checks you intend to require pass consistently. Go to [Merge Queue Overview](/code-repository/use-harness-code/pull-requests/merge-queue.md) to see what a flaky check costs a queue.
* **Repository administrator access:** you can create and edit branch rules on the repository. Go to [Rules](/code-repository/use-harness-code/manage-repositories/rules.md) to review how branch rules work.
* **Agreement on the restriction:** the repository owners accept that direct updates to the protected branch are blocked while the queue is active.

## Configure the repository and pipeline

{% stepper %}
{% step %}

### Create the branch rule

In the repository, go to **Settings**, select **Rules**, then click **Create rule** and select **Create branch rule**.

Give the rule a descriptive name and set the target branch or branch pattern it applies to. Configure the required approvals, the protections you want to keep, and the bypass policy in the same rule.
{% endstep %}

{% step %}

### Select the pull request checks

Under **Require status checks to pass**, select the checks that decide whether a pull request is eligible to enter the queue.

Pull request checks and Merge Queue checks answer different questions. A pull request check decides whether a pull request may join the queue. A Merge Queue check validates that pull request against the cumulative queued state. The same pipeline and identifier can serve both purposes.
{% endstep %}

{% step %}

### Enable Merge Queue

Select **Require merge queue**, then configure its settings:

* **Status checks:** enter the exact, case-sensitive identifier the Merge Queue pipeline reports. A mismatch leaves the queue waiting until the check duration expires, even when the pipeline succeeds.
* **Merge group size:** the maximum number of consecutive entries that one speculative commit validates. Start at `1`. The accepted range is `1` to `10`.
* **Checks concurrency:** the maximum number of groups with checks running at the same time. Start between `1` and `3`. The accepted range is `1` to `10`.
* **Maximum check duration:** set this above the high-percentile duration of the pipeline, including the time to schedule the run and provision infrastructure.

{% hint style="warning" %}
**Leave the up-to-date requirement disabled**

Do not enable **Require branch to be up to date before merging** alongside Merge Queue. The queue already validates each change against the correct target-branch state, and the two settings together return contributors to the rebase loop the queue exists to remove.
{% endhint %}
{% endstep %}

{% step %}

### Prepare the pipeline

The pipeline must take its build from the event rather than a fixed branch, clone the repository, and report its result against the commit it tested.

{% code title="pipeline.yaml" %}

```yaml
pipeline:
  properties:
    ci:
      codebase:
        repoName: my-repository
        build: <+input>
  stages:
    - stage:
        type: CI
        spec:
          cloneCodebase: true
```

{% endcode %}
{% endstep %}

{% step %}

### Create the MergeQueue trigger

In the pipeline, go to **Triggers**, then click **New Trigger**. Set the payload type to **Harness**, select the repository, set the event to **MergeQueue**, and enable the trigger.

Set the pipeline input so the build resolves from the trigger:

{% code title="Pipeline Input" %}

```yaml
pipeline:
  properties:
    ci:
      codebase:
        build:
          type: branch
          spec:
            branch: <+trigger.branch>
```

{% endcode %}

{% hint style="danger" %}
**Never hard-code the branch**

A literal value such as `branch: main` makes CI clone the tip of the target branch instead of the speculative commit. The pipeline succeeds, the check reports against code the queue never intended to test, and the target branch fast-forwards to a commit nothing validated.
{% endhint %}
{% endstep %}
{% endstepper %}

## Validate the setup

Run one pull request through the queue before you rely on the configuration.

{% stepper %}
{% step %}

### Make a pull request eligible

Complete the reviews, the pull request checks, the conflict evaluation, and the other requirements in the branch rule. The pull request then shows **Add to merge queue**.
{% endstep %}

{% step %}

### Confirm the queued state

After the pull request is admitted, Harness Code locks the source branch, creates the speculative commit, and starts the MergeQueue pipeline. Select **View queue**, or open **Merge Queue** from the repository branch view, to see the entry and its state.
{% endstep %}

{% step %}

### Verify that the speculative commit was tested

Add a step to the pipeline that compares the checked-out commit against the commit the trigger supplied:

{% code title="verify.sh" %}

```bash
set -e
SPEC="<+trigger.commitSha>"
HEAD="$(git rev-parse HEAD)"
echo "trigger.commitSha=$SPEC"
echo "HEAD=$HEAD"
test "$HEAD" = "$SPEC"
```

{% endcode %}

The comparison must pass. A passing comparison proves CI tested the speculative commit rather than the source branch or the tip of the target branch.
{% endstep %}

{% step %}

### Confirm the merge

When every required check reports success, Harness Code fast-forwards the target branch and the pull request becomes merged. The target branch now points at the commit that was tested.
{% endstep %}
{% endstepper %}

## Onboarding checklist

Use this checklist to confirm a repository is ready before you announce the queue to its contributors:

* [ ] The repository has enough merge concurrency and branch impact to justify a queue.
* [ ] The required checks are reliable and CI capacity is available.
* [ ] The pipeline uses `build: <+input>` and clones the codebase.
* [ ] A Harness MergeQueue trigger exists and is enabled.
* [ ] The pipeline input uses `<+trigger.branch>` rather than a literal branch name.
* [ ] The pull request and Merge Queue check identifiers match the branch rule exactly.
* [ ] Merge group size, checks concurrency, and maximum check duration are set.
* [ ] **Require branch to be up to date before merging** is disabled.
* [ ] A test pull request proves the checked-out commit equals `<+trigger.commitSha>`.
* [ ] The test pull request merges and the target branch points at the tested commit.

## Troubleshooting

<details>

<summary>No pipeline starts when a pull request enters the queue</summary>

Confirm the trigger is enabled, its payload type is **Harness**, its event is **MergeQueue**, and it points at the repository the branch rule protects.

</details>

<details>

<summary>The queue does not advance although the pipeline succeeded</summary>

The check identifier in the branch rule must match the identifier the pipeline reports, character for character and with the same casing. Confirm the pipeline reports the check against `<+trigger.commitSha>`. Until the identifiers match, the entry waits for the maximum check duration and is then removed.

</details>

<details>

<summary>The pipeline tested the wrong code</summary>

Confirm the stage clones the codebase, the pipeline input uses `<+trigger.branch>` rather than a literal branch name, and `git rev-parse HEAD` in the pipeline equals `<+trigger.commitSha>`.

</details>

<details>

<summary>A pull request was removed from the queue</summary>

Open the pull request activity to find the reason. An entry leaves the queue after a failed required check, a check duration timeout, a conflict with an earlier queued entry, a manual removal, or the queue being disabled on the branch rule.

</details>

## Next steps

Go to [Merge Queue Overview](/code-repository/use-harness-code/pull-requests/merge-queue.md) to read how batching, concurrency, and queue states affect throughput once the queue carries real traffic. Go to [Rules](/code-repository/use-harness-code/manage-repositories/rules.md) to review the other protections available on the same branch rule.

{% @harness-feedback/feedback module="code-repository" pagePath="code-repository/use-harness-code/pull-requests/merge-queue/set-up-merge-queue" %}
