BUSFACTOR.TECH
Code Review

Your Review Stats Only Count the PRs That Got Reviewed

The bottleneck

YOUR REVIEW STATS ONLY COUNT

Latency dashboards only see reviewed PRs. The ones merged without review vanish from the math. How to measure coverage, self-merge share, and close the gap.

4 receipts in this article ↓

TL;DR: Every review metric on your dashboard - pickup time, review time, the lot - is computed over the PRs that got reviewed. The ones that merged without review contribute nothing: no pickup timestamp, no duration, no data point. So the dashboard can improve while the review culture erodes, because every PR that skips the queue makes the queue look faster. Separate coverage from latency, count your self-merges by repo and author, and look hard at the areas where nobody but the author is able to review. That's where the unreviewed code clusters, and that's the actual fix.

An engineer tells you in a one-on-one that reviews here are painfully slow. You check the dashboard: median pickup four hours, review time trending down two quarters straight. You conclude the engineer is exaggerating. Here's the version where you're both right: they wait in the review queue, and a meaningful share of their colleagues don't. Those colleagues' PRs merge with no review at all, contributing zero slow data points to your averages. The dashboard describes only the subset of your review process that happens, for the subset of people it happens to.

That's the uncomfortable sentence hiding in most orgs' merged-PR data: you don't have a review culture. You have a review culture for some people and some code, and the code that skips it isn't random. It's the infra scripts, the one-owner subsystem, the principal engineer nobody feels entitled to question. The exact code where a second reader matters most.

The dashboard only grades the survivors

The mechanism is worth spelling out because it's genuinely counterintuitive: review latency is conditioned on review existing. A PR with no review has no pickup time. There is nothing to measure, so it silently exits the denominator of every speed metric you track. Push that to the limit: a team where almost every PR self-merges and one small PR a week gets a fast look would post elite latency numbers. Speed metrics are structurally incapable of noticing that review is disappearing, because disappearing review only ever removes data points - mostly slow ones.

So the first question isn't "how fast are reviews?" It's "how many PRs merged without review?" That existence check comes before every other number in this pillar, and it's the one review coverage exists to answer. For calibration on what's achievable: at Google, essentially every change to the main codebase is reviewed before landing, across ~9 million changes, with a median of one approver, and small changes seeing first feedback in under an hour. Full coverage at speed is not a fantasy trade-off. And coverage isn't hygiene theater: McIntosh et al.'s MSR study of Qt, VTK and ITK found that review coverage and participation share a significant link with software quality. Components where changes land with little or no review tended to carry more post-release defects.

A review culture for some people

Pull your merged PRs from the last quarter and segment the unreviewed ones two ways. The clusters you'll find are the diagnosis:

By author. Somewhere in your org is a senior whose PRs merge untouched, not because they demanded it but because a social gradient formed: who reviews the principal's code? This is how a trusted fast lane becomes a fact nobody decided. Both readings deserve the table. Maybe their solo areas are genuinely theirs by design and the org accepts the trade, or maybe you've built a knowledge silo with excellent throughput, unreadable by anyone else, one resignation away from being an orphaned area. What settles the fork is whether anyone else could meaningfully review that code if they tried. Skill was never the question.

By area. Deploy scripts, CI config, migrations, the gnarly subsystem with one owner. Unreviewed merges concentrate where review supply is zero: nobody but the author is competent to review, so asking feels like ceremony, so nobody asks. Note what this means: exhortation won't fix it. "Please review more" does nothing when one person is the entire safety net for an area. The unreviewed cluster is a map of where you need to grow a second reviewer, which is the same move as dismantling the silo. Microsoft's research found review's real outcomes lean toward knowledge transfer and awareness rather than defect-catching. The self-merged area is skipping the one mechanism that would, as a side effect of normal work, create the second competent human it lacks.

One honesty note before the numbers: coverage counts any non-author review, so a 40-second rubber-stamp LGTM counts. Coverage is a floor: it detects absence, not depth. An org can pass coverage and still have a reading problem; you need both checks, and they fail in opposite directions.

The free diagnosis: three numbers, one exception list

  1. Coverage share. Of PRs merged last quarter, what share had at least one non-author review? Compute it from what actually merged, not from your branch-protection settings. Bypasses, exempt repos and bot merges make the two disagree, and the gap is your real number.
  2. Self-merge share, segmented. The complement, split by repo and by author. Org-wide averages hide everything; the finding is always a cluster. Three self-merged lockfile bumps are noise. Forty unreviewed merges into deploy scripts by the same two people is a silo forming in real time.
  3. Reviews per merged PR. Total reviews divided by merged PRs, as a companion trend. A healthy number rides near or above one (Google's median: one approver; one reader is the whole bar). Sliding toward zero while latency "improves" is the survivorship signature. LinearB's benchmarks across 8.1M+ PRs band the speed metrics, but band them after you know how much of your merge volume they even describe.
  4. Write the exception list. Bots, lockfiles, generated code, the emergency hotfix reviewed after the fact. Written down, it's policy; unwritten, it's drift. Everything outside the list gets a reader. If review is too slow to wait for, fix the queue instead of routing around the reading. The craft side of making that sustainable is the code review best practices playbook; the coverage check is what makes the playbook apply to all of your code instead of most of it.

Then the real fix, in the areas the clusters exposed: pair the only-competent author with an apprentice reviewer for a few weeks, route the low-risk PRs in that area to them deliberately, and keep PRs small enough to actually read. None of that is new process. It grows review supply exactly where it's zero.

The delivery-stats view breaking each pull request into pickup, review, merge, and deploy time.The delivery-stats view breaking each pull request into pickup, review, merge, and deploy time.
The cycle-time breakdown - where each PR spends its lifeLive product · fictional demo org

How you'd actually see this in Busfactor

The quarterly audit is a great meeting that happens once. Busfactor computes the coverage side continuously from your GitHub data: merged PRs with non-author review, its complement merged with no non-author review, and reviews per merged PR sit in the judged stat grid - each graded healthy/watch/bad against expert bands for your org's size, with cited industry reference bands beside them, and trackable per team on the team scoreboard. The clustering question - whose code and which areas skip review - is what the review network draws: who reviews whom, load, breadth, reciprocity, the one-way streets, and the areas where a single reviewer is the whole safety net. That's the map that turns "coverage is 81" into "these two areas have no second competent reviewer, and here are the PRs that shipped there unread."

The honest limits: coverage counts any non-author review, so a rubber stamp inflates it here too, which is exactly why the network view and the review-friction taxonomy sit next to the number instead of letting it stand alone. Busfactor sees the events GitHub sees. The review that happened over a screen-share or in a DM is invisible, and orgs with heavy out-of-band review will look worse on coverage than they are; the numbers say so rather than pretend otherwise. And a self-merge cluster is not automatically a dysfunction: a deliberate, documented fast lane for a trusted solo area is a choice some orgs defensibly make. The tool shows the cluster, what it costs in second readers, and both interpretations. The verdict stays yours.

The door

Run the coverage query this week - one afternoon against your git host's API, three numbers out. The honest sentence you're buying is one you currently can't say: "this share of the code we shipped last quarter was read by a second person, and here's where the rest concentrates." If the number embarrasses you, you've found the cheapest review improvement that exists: not faster review, not deeper review, just review, in the two areas that currently have none. And if you'd rather the survivorship bias never creep back, get your org's free read - coverage, self-merge clusters and the review network drawn from your real merged PRs, receipts attached.

Frequently asked

How do I find PRs merged without review?

Query your git host for PRs merged in a window and check each for at least one review by someone other than the author. Branch-protection settings are not the answer to this question: admin bypasses, exempt repos, direct pushes and bot merges all leak past the rule. Count what actually merged, then segment by repo and author, because unreviewed merges cluster, and the cluster is the finding.

Why does review latency look fine when many PRs skip review?

Survivorship bias. Pickup time and review time are computed over reviews that happened: a PR merged with no review contributes no pickup timestamp and no review duration, so it exits the dataset silently. The more PRs skip review entirely, the fewer slow data points your averages contain. A team can drift toward barely reviewing at all while its latency dashboard steadily improves.

Is it ever OK to merge a PR without review?

Yes, with a short written exception list: automated dependency bumps, lockfiles, generated code, and the genuine emergency hotfix that gets its review after the fact (provided the post-hoc review actually happens). The difference between policy and drift is whether the list is written down. Unwritten exceptions grow silently until the exception is the culture.

Does a 40-second LGTM count as review coverage?

Mechanically, yes: coverage counts any non-author review, so a rubber stamp inflates it. That makes coverage a floor rather than proof of reading. It tells you a second person was present, not that they engaged. Pair it with reviews per merged PR and with reading-depth signals like comment rate and time-to-approve on large diffs to tell presence apart from engagement.

Receipts

Keep reading