Engineering Leadership

PR Size, Batching, and Queue Discipline

Limits and batching rules that stop the queue from becoming the product.

Chapter 7 of 1412 min readOpen access

PR Size, Batching, and Queue Discipline is the supply-side lever on the queue Chapter 5 sized and Chapter 6 triaged. Size is not a matter of taste. It decides whether a change can be read in full by a person who has forty minutes, and that is a capacity question with published numbers attached.

Key takeaways

  • Google's engineering practices state that 100 lines is usually a reasonable size for a change and 1000 lines is usually too large, and that a 200-line change spread across 50 files would usually be too large.
  • The same guidance says reviewers have discretion to reject a change outright for the sole reason of it being too large. That sentence is the one to adopt as policy, because it makes the limit enforceable.
  • Sadowski and colleagues measured comments per change rising with size to a peak of 12.5 comments for changes of about 1250 lines, with larger changes attracting fewer comments because they tend to be generated code or large deletions.
  • Faros AI, which sells engineering-productivity analytics, reports average pull request size up 51.3%, files edited per pull request up 59.7% and files touched per developer per month up 149.9% as of March 2026.
  • A merge queue is a batching mechanism with explicit failure semantics: GitHub's documentation states that a queued pull request failing its checks in a group is removed from the queue and the temporary branches are recreated without it.

Read this immediately after Chapter 6, since size determines how much of the arriving change can safely take the automated exits, and before Chapter 8, which handles the case where a small change still causes an incident. Chapter 2 set the scope rule this chapter enforces.

The pull request is 1,214 lines across 34 files. It does three things: a schema migration, a new read path, and a rename that touches everything.

The reviewer reads the migration carefully, because that is the frightening part. They read the new read path with attention. Then they scroll through nine hundred lines of mechanical rename and approve.

The rename was fine. The read path had a bug in its cache invalidation, on line 640, in the middle of the part that got the last ten minutes. The approval was honest. The reading was not complete.

Size is a capacity decision, not a style preference

There is a hard limit on how much code a person can read carefully, and it is much smaller than the amount they can read.

Careful reading means reconstructing intent, checking each branch, and asking what happens on failure. Skimming means confirming the code looks like code. Both feel like reviewing while you do them, and only one of them finds anything.

So a size limit is really a statement about which of those two activities you are buying. A change small enough to be read in one sitting gets careful reading. A change that is not gets skimmed. The approval then means almost nothing.

The reason this got urgent is arithmetic rather than principle. Faros AI, which sells engineering-productivity analytics, reports average pull request size up 51.3% and files edited per pull request up 59.7%. Those come from between-quarter comparisons across 22,000 developers as of March 2026, and Faros AI notes that its prior report showed a larger size increase, so the comparison is directional.

Google's published numbers, and how to use them

Google's engineering practices give the only widely cited public anchor, and its exact wording matters. 100 lines is usually a reasonable size for a change, and 1000 lines is usually too large, but it is up to the judgment of the reviewer.

The same page adds a second dimension that most teams ignore. A 200-line change in one file might be acceptable, and spread across 50 files it would usually be too large. Files touched is a better predictor of review difficulty than lines, because each file is a separate context to load.

Then the sentence to lift into your own policy verbatim. Reviewers have discretion to reject a change outright for the sole reason of it being too large.

That sentence does something no threshold can. It removes the social cost of refusing, which is the actual reason large changes get approved. A reviewer who has to justify rejecting will skim instead. Nobody wants that argument on a Friday.

Comments per change peak, and then fall

There is a measured relationship between size and review attention, and its shape is the useful part. Sadowski and colleagues, in their 2018 study of Google's review logs covering 9 million changes, found the average number of comments per change grows with lines changed, reaching a peak of 12.5 comments per change for changes of about 1250 lines.

Above that, comments fall. The paper gives the honest reason rather than a dramatic one: changes larger than that often contain auto-generated code or large deletions, which attract fewer comments.

I would not read that as reviewers giving up, because the authors do not. I would read it as evidence that very large changes are usually a different kind of change, and that mixing a mechanical bulk edit into a change containing real logic is what makes the logic invisible.

That gives a rule worth more than any line count. One change does one kind of thing. A mechanical rename goes in its own pull request, and it may be enormous. Size is not the sin. Mixing is.

What DORA found about working in small batches

DORA's State of AI-assisted Software Development 2025, published 24 September 2025 from 4,867 respondents, includes working in small batches as one of its seven named AI capabilities, and the finding is more specific than the usual advice.

DORA reports, with a high degree of certainty, that where teams work in small batches AI's positive influence on product performance is amplified, and AI's neutral effect on friction is made beneficial and shown to decrease friction. It also reports that AI's benefits for individual effectiveness are slightly reduced in those teams. DORA argues the trade is worth taking, because individual effectiveness is a means rather than a goal. I agree, and it is worth saying out loud to the engineers who will feel the reduction.

Note how DORA measures batch size, because it is a better operational definition than most teams use. Lines of code committed in the most recent change. The number of changes typically combined into a single release. And how long it takes a developer to complete one assigned task.

These are estimated standardised effects from a self-reported survey with 89% credible intervals. They are not measured delivery outcomes, and DORA does not present them as such.

The limits worth enforcing, and where

The table below is the compact form, and the third column is the one that decides whether any of it holds.

LimitValue I would start fromEnforced where
Lines changed, excluding generated files and lock files400 soft, 1000 hardIn the pipeline, before review is requested
Files touched20 soft, 50 hardSame check
Kinds of change in one pull requestOneThe agent's standing context, and a reviewer's discretion
Concurrent pull requests open per author3The queue dashboard, reviewed weekly
Changes per merge groupSet to your pipeline's reliabilityThe merge queue configuration

Three notes on that table. The soft limits warn and the hard limits block, because a policy with no exceptions gets routed around. The exclusions are essential. Counting lock files and generated code turns the limit into noise, and a noisy limit teaches people to ignore limits. The fourth row is the one almost nobody has, which is the next section.

Work in progress is the limit nobody sets

Size limits alone push the problem sideways. Split a large change into eight and you now have eight open pull requests per author, which is a different flavour of the same overload.

Faros AI reports daily pull request contexts per developer up 67.4% and stalled tasks up 26%, alongside files touched per developer per month up 149.9% and repositories touched per developer per month up 11.7%. Those are between-quarter correlations, not experiments. They describe attention spread thinner across more places.

A work in progress limit is the control, and it is uncomfortable in exactly the way it should be. Cap open changes per author, cap the number of changes waiting on one reviewer, and treat hitting the cap as a signal to finish something rather than to start something.

The objection to this is always that it reduces utilisation. It does. Utilisation was never the goal. A queue held at high utilisation has long waiting times as a mathematical consequence rather than as a management failure, and no amount of encouragement changes that.

The merge queue is batching with failure semantics

Once volume rises, serialised merges become their own bottleneck, and a merge queue is the standard answer. GitHub's documentation describes it as increasing velocity by automating merges into a busy branch while ensuring the branch is never broken by incompatible changes.

The mechanics are worth knowing precisely, because they determine the trade-off. Queued pull requests are grouped into a merge group with the base branch and the changes ahead of them. A pull request whose checks fail in a group is removed from the queue, and the temporary branches are recreated without it.

That last behaviour is the cost of batching. One failing member forces the group to be rebuilt, so larger groups mean faster throughput when things are green and more wasted pipeline time when they are not. GitHub exposes the knobs for exactly this: maximum pull requests per merge group, minimum before merging, wait timeout, and a concurrent build limit.

One constraint to check before planning around it. GitHub's documentation states that a merge queue cannot be enabled on branch protection rules that use wildcards.

A worked example, composited and labelled

The details here are composited from ordinary production shapes rather than one system, and the shape is exact.

The 1,214-line change from the top of this chapter gets decomposed, and the decomposition follows the kinds of work rather than a line target. It becomes four pull requests.

The migration ships first, additive only, with no reader. The new read path ships second, behind a flag that is off. The rename ships third, alone, and it is 890 lines of pure mechanical edit that a reviewer approves in four minutes with a diff filter. The flag flip ships fourth, as a one-line change that a named owner reads.

Total lines are unchanged. Total review time falls, because only about three hundred lines needed careful reading and the reviewer could tell which three hundred. The cache invalidation bug is caught in the second pull request, where it is the only interesting thing on the page.

There is a second benefit that matters more later. Each of the four is separately revertible, and the flag flip is revertible without a deployment at all.

The objection: more small changes are more overhead

The objection is real and I would not dismiss it. Eight pull requests need eight descriptions, eight pipeline runs, eight approvals and eight merges, which is more ceremony than one.

Three parts to the answer. The ceremony is mostly automatable and the reading is not, so you are trading a cost machines absorb for a cost only people can pay. Splitting by kind of change rather than by arbitrary line count removes most of the artificial splits, because the parts were genuinely different work. And the pipeline cost is real, which is why Chapter 12 counts compute as a cost line rather than pretending it is free.

Where the objection genuinely holds is a change that cannot be decomposed without being broken in the middle. A schema migration with a dependent code change is the classic case, and the answer is not a rule but a technique: land the migration behind a flag, ship the code path dark, then flip. That is Chapter 8's machinery being used to buy reviewability.

The residual honest cost is author time. Sequencing eight changes takes longer than opening one, and it is work the author does so a reviewer does not. That is the correct direction for the cost to flow, given which resource is scarce.

Chapter summary

Change size decides whether a reviewer reads carefully or skims, so it is a capacity control rather than a style preference. Google's engineering practices anchor the numbers, stating that 100 lines is usually reasonable and 1000 usually too large, that a 200-line change across 50 files would usually be too large, and, most usefully as policy, that reviewers have discretion to reject a change outright for the sole reason of being too large, which removes the social cost of refusing. Sadowski and colleagues measured comments per change rising with size to a peak of 12.5 comments at about 1250 lines and falling above that, attributing the fall to those changes tending to be generated code or large deletions, which yields the rule that one pull request does one kind of thing and a mechanical bulk edit ships alone. DORA's report of 24 September 2025 found, with high certainty and as an estimated survey effect with 89% credible intervals, that small batches amplify AI's positive influence on product performance and turn its neutral effect on friction into a decrease, measuring batch size as lines in the most recent change, changes per release, and time to complete one task. Enforce soft and hard limits on lines and files in the pipeline before review is requested, excluding generated and lock files, and cap concurrent open changes per author, because Faros AI reports daily pull request contexts per developer up 67.4% and stalled tasks up 26%. A merge queue batches with explicit failure semantics, removing a failing member and recreating the temporary branches without it, and cannot be enabled on wildcard branch protection rules.

Smaller changes and tighter queues reduce the damage a bad merge can do. They do not eliminate it, and Chapter 6 told you to let some changes through unread. Chapter 8 is Making a Revert Cheaper Than a Careful Read, which is the precondition that makes all of it defensible.

Sources

  1. Google eng-practices: Small CLsGoogle · Official documentation · verified
  2. Modern Code Review: A Case Study at GoogleSadowski, Soderberg, Church, Sipko, Bacchelli, ICSE-SEIP · 2018-05 · Research paper · verified
  3. Managing a merge queueGitHub Docs · Official documentation · verified
  4. State of AI-assisted Software Development 2025DORA, Google Cloud · 2025-09-24 · Industry report · verified
  5. AI Engineering Report 2026: The Acceleration WhiplashFaros AI · 2026-03 · Industry report · verified