Code Review

A Checklist vs Freeform Comments on a Pull Request

Two pull requests sit open on the same team's board. One has a neat row of checkboxes at the bottom of its description: tests added, docs updated, changelog entry, no console logs left behind. The other has a paragraph of loose prose written at the end of a long day, half question and half apology, ending with the sentence "I think this is probably fine but someone should look at the retry logic." Both get merged. Only one of them leaves a trail that a stranger can follow six months later, and it is rarely the one with the checkboxes.

The checklist and the freeform comment are the two dominant ways engineers frame a change for review, and they are usually described as a question of rigor versus honesty. The checklist is the disciplined one, the template that catches what memory misses. Freeform is the sloppy one, the ramble that happens when nobody enforces a format. That framing gets the tradeoff backwards. The checklist is a compliance instrument, and compliance is cheap to fake. Freeform prose is where a reviewer finds out whether the author actually understands what they changed.

What a ticked box actually asserts

Consider what happens when a reviewer sees "tests added" checked. That is a claim, not evidence. The author checked it because the box was there and an unchecked box looks like unfinished work, so the box gets checked, and the tests in question are three shallow assertions that exercise the happy path and nothing else. The reviewer, who is tired and has eleven more pull requests in the queue, reads the tick and moves on. The checkbox did its job, which was to make the review faster. It did not do the job the reviewer imagines it did, which was to make the review safer.

This is the quiet corruption of every template. The field gets filled because the field exists. A description that asks for a summary gets a summary that restates the diff titles. A description that asks for a testing plan gets "ran the tests locally." The structure rewards completion, and completion is a low bar. Nothing in a checklist can distinguish between a box ticked by someone who thought hard and a box ticked by someone who wanted the form to go away.

The retry logic problem

Go back to that loose paragraph about the retry logic. It is doing something a checklist cannot. The author is telling the reviewer where the doubt lives. That sentence costs something to write, because it admits uncertainty in public, and it points a reviewer at the exact function that deserves the next ten minutes of attention. A checklist would have said "error handling reviewed" and the reviewer would have looked at the diff, seen a try/catch, and felt satisfied.

Reviewers do not have infinite attention. The whole economics of code review is about directing scarce attention to the places where it will find something. A checklist distributes attention evenly across categories that were decided in advance, by someone who was not looking at this specific change. Freeform prose lets the author say "the risk is here." That is worth more than a dozen ticked boxes, because it is a signal that only the person who wrote the code can produce.

When the checklist earns its keep

None of this makes the checklist useless. There is a category of change where the boxes are the whole point: the mechanical, repetitive, low-judgment edits that happen across a large codebase. Renaming a config key. Bumping a dependency. Applying the same migration pattern to forty files. In those cases nobody needs the author's inner monologue, because there is no inner monologue. The checklist exists to confirm the obvious steps were not skipped, and for obvious steps, a tick is the correct instrument.

The checklist also earns its place on teams where the reviewer and author do not know each other well. Freeform prose depends on trust. A reader who does not know the author cannot tell whether "I think this is fine" is a careful person being modest or a careless person being careless. The fixed fields at least guarantee certain information exists, even if it is thin. On a large open-source project with drive-by contributors, the template is the only thing standing between a reviewer and a wall of silence.

The template that ate the description

The trouble arrives when the checklist outgrows its purpose and swallows the whole description. This happens gradually. A team adds a box after an incident. Then another box after a different incident. Then a required field for the ticket number and a required field for the rollback plan. Within a year the description is a form with nine mandatory fields, and the pull request body is a stack of brackets waiting to be filled. The freeform comment, the one place where an author could have said something true, is squeezed out.

Engineers respond to this the way anyone responds to a form that has grown too large. They fill it with the minimum that passes. The boxes get ticked in a batch, the fields get filled with "N/A" where the field does not apply, and the actual thinking, if any happened, stays in the author's head. The form has become a tax on submitting work rather than a tool for reviewing it.

A description that carries a claim

The freeform comment has its own failure mode, and it is worth naming because it is what checklist defenders are actually reacting to. A comment that says "minor changes, please review" tells the reviewer nothing. A comment that says "fixed the bug" is a claim with no location attached. Freeform prose only works when the author writes something the reviewer could disagree with, something specific enough to be wrong. "I moved the retry count from three to five because the downstream service was timing out on cold starts" is freeform done well. It states a decision, a number, and a reason.

That kind of sentence is harder to write than any checkbox. It requires the author to have actually formed a view about the change, which is the real reason templates spread. A template lets a person submit work without deciding what matters about it. Prose forces the decision. The checklist is popular partly because it is easier, and the ease is mistaken for rigor.

What a reviewer can do with a sentence of doubt

A reviewer reading a checklist scans for gaps. A reviewer reading prose reads for the thing the author is worried about. Those are different cognitive tasks, and the second one produces better outcomes. When an author writes "this is probably fine but the cache invalidation worries me," a good reviewer opens the cache invalidation code first. The sentence is a map. A checklist is a border crossing: it confirms arrival without describing the terrain.

There is also a social effect. Writing a specific doubt invites a specific response. The reviewer replies "your cache invalidation looks right, but the retry loop can spin forever if the status code is a 502." That exchange is the review doing its actual work. A checklist produces a different exchange: "LGTM, all boxes checked." Nothing was learned. The pull request was approved by two people who both did less thinking than the process implied.

Keeping the boxes small and the prose honest

The workable arrangement is not to abolish the checklist or to romanticize the ramble. It is to keep the boxes few and the prose mandatory. Two or three checkboxes for the genuinely mechanical confirmations, the ones where a tick is the right instrument, and then a block of open space where the author is expected to say what they changed and where they are unsure. The open space should be small enough that it is not a form and large enough that it is not a formality.

The test of a good pull request description is simple: could a reviewer read it and know where to spend the next fifteen minutes? A wall of ticked boxes fails that test, because it distributes attention nowhere in particular. A single honest paragraph passes it, because it points. The format that looks less rigorous is often the one that carries more information, and the format that looks disciplined is often just a faster way to stop thinking.

Leave a Reply

Your email address will not be published. Required fields are marked *

Back to top button