
Code generation is no longer the bottleneck. An agent delivers more changes in a morning than a team reviews carefully in a day β and responsibility for the result stays entirely with the humans. The constraint has moved from producing code to judging it. This guide describes what a robust review process for agent output looks like, and which checks turn a prototype into a deliverable that can actually be signed off.
This article is an in-depth expert contribution from our content cluster. Discover the complete overview on our main page:Modern Web Development & Software Engineering →
- The bottleneck has changed sides: Writing code is no longer scarce; the ability to judge it is. Teams that adopt agents without planning review capacity are not saving work, they are moving it to the phase where mistakes cost the most.
- Review without intent: Reviewing your own code means comparing execution against intent. With agent output that intent is not in the reviewer's head. Familiar review habits stop working, and a dedicated mechanic is needed instead.
- Verifiability is a contractual question: A prototype without a defined set of checks cannot be signed off, because nobody can say when it is finished. Quality gates are therefore not a technical detail but the basis of every clean fixed-price acceptance.
The question before the merge
An agent opens a branch with four hundred changed lines. Tests are green, the build passes, the description sounds plausible. Nobody on the team wrote a single one of those lines. Who decides, by what method, whether this gets merged β that is the central quality question of software development in 2026.
1. The Reviewer Bottleneck
One number rarely appears in discussions about developer productivity, although it decides everything: how much code a human can review carefully in a day. Experience from review practice puts it at a few hundred lines before attention measurably declines β and that number has stayed stable for decades, because it depends on human concentration rather than on tooling.
On the other side stands an AI coding assistant that produces this volume in minutes. That makes the arithmetic behind most productivity claims incomplete. It measures production and quietly omits judgement. Add both together and the picture changes: the bottleneck has not disappeared, it has moved.
This is not a criticism of the tools. Agents such as Cursor, Claude Code or Antigravity are remarkable at producing code, and we covered the architecture behind them in our article on multi-agent systems in software development. It is a criticism of the balance sheet drawn from them, because three things remain unchanged:
Liability does not transfer
Whoever ships the software answers for it. No customer, auditor or court cares which tool produced a defective line. Responsibility stays entirely with the delivering company β the producer never assumed it.
Review fatigue is real
Anyone working through twenty plausible-looking branches in a row reviews the twenty-first differently from the first. Plausibility is precisely what generated code is best at β and precisely what lowers human vigilance.
Deferred cost is higher cost
A defect caught in review costs minutes. The same defect in production costs analysis, a hotfix, communication and trust. Unreviewed agent output saves nothing; it shifts effort into the most expensive phase β a pattern long familiar from the debate around technical debt.
What has genuinely been solved β and this is the real progress of the past two years β is the syntactic layer. Whether the code compiles, whether types line up, whether formatting rules hold: tooling checks that more reliably than any human, and it is no longer a sensible subject for review. What remains is the layer on which tools fundamentally cannot judge: whether the code does the right thing.
2. Why Foreign Code Is Reviewed Differently
When developers reread their own code, they do something quite specific without noticing: they compare what is written against an intent they themselves hold. They know which problem they set out to solve, which three approaches they discarded, and why one place deliberately contains an inelegant solution. The text on screen is only half the information; the other half sits in their head.
That half is exactly what is missing when reviewing agent output. The reviewer has the code but not the intent behind it β and while the producer can describe that intent plausibly on request, it cannot stand behind it. An agent justifies every decision convincingly, including a wrong one. That is the real difference, and it implies a different posture.
In classic peer review the question is: did my colleague miss what I can see? In agent review it is: have I understood what actually happens here β and did I want that?
Classic Peer Review vs. Agent Review
- Starting point: A colleague whose thinking and strengths are known.
- Failure mode: Carelessness, knowledge gaps, time pressure β usually local and explainable.
- Follow-up question: Produces a reliable rationale; the author answers for the statement.
- Size: Grows with the author's effort and is therefore naturally limited.
- Style: A personal signature against which deviations stand out.
- Starting point: A producer with no memory of the project's unwritten rules.
- Failure mode: A plausible misreading of the task β global, consistently applied and therefore hard to see.
- Follow-up question: Produces a convincing narrative that carries no guarantee.
- Size: Arbitrarily large, with size saying nothing about difficulty.
- Style: Uniform and conventional β anomalies disappear into the average.
Three questions follow that every review of agent output has to answer. The order is deliberate, because the first decides whether the other two are worth asking:
-
Does this change solve the stated problem?
Not: is the code good? But: was the task understood correctly? The most common failure class in agent output is a clean, well-structured, fully executed solution to a slightly different problem than the one posed. This check requires no look at the implementation, only a comparison between the brief and the observable behaviour.
-
What else does it change?
Agents optimise the stated task and have no sense of which side effect is expensive. A signature changed along the way, a helper function "tidied up", an extra database call inside a loop: technically correct, wrong in context. This check is about scope of effect, not about the diff.
-
Why exactly this way?
Wherever the code makes a non-obvious decision β caching, a retry, a bespoke implementation instead of an existing function β a human must be able to follow and own that decision. Where that fails, the answer is to simplify rather than to debate.
3. The Review Mechanic
The three questions set the posture. To survive daily practice they need a mechanic β a fixed sequence of moves that still works at the end of a long day. The following five are tool-independent and can be introduced in any team, whichever agent is in use.
One agent run, one reviewable unit
The single most effective measure is also the least popular: cut the brief small enough that the result stays reviewable in one sitting. An agent can handle three tasks at once β but a human cannot judge three intermingled tasks cleanly. The limit is set by reviewability, not by the capability of the tool.
Blast radius before line count
Review depth follows the blast radius, not the volume of changes. Two hundred lines in an isolated component are less dangerous than three lines in a shared helper, an authentication path or a migration. Read in order of scope of effect, not in the order the diff presents.
Data and migrations first
Presentation defects are repairable; defects in the data often are not. Schema changes, delete operations, permission logic and anything touching money or personal data are read before the rest β regardless of how small the section is.
Justify every new dependency
Language models invent package names that do not exist β and attackers register exactly those names, a pattern known as slopsquatting. Every newly added package is therefore checked individually: does it really exist, who maintains it, and does the project need it at all? The security side of this question is covered in our guide to securing AI agents in development environments.
The fifth move is the most effective and the cheapest: the counter-check. Before a branch is merged, a human explains in their own words what it does β the reviewer, not the agent. Two or three sentences are enough. Anyone unable to formulate them has not understood the code, and at that point the size of the diff is irrelevant.
Expert tip: the rationale belongs in the commit, not the chat
The most valuable part of an agent run is the reasoning for why a solution looks the way it does β and that part usually stays behind in the chat window and is lost within a week. Moving it into the commit message makes the decision traceable for every later reader. It is the same reason architecture decisions get documented: the code is not the hard part to reconstruct, the discarded alternative is.
4. Tests as Specification, Not Self-Confirmation
Agents write tests readily and quickly. The result looks like quality assurance but has a structural flaw: those tests check the code against the very interpretation of the task from which the code emerged. If the agent misread the task, implementation and test are wrong together β and the suite is still green.
That does not make generated tests worthless. As a regression net they are useful: they record how the system behaves today and fire when a later change breaks that behaviour. What they do not answer is whether the recorded behaviour is correct. This distinction determines which tests you delegate.
Humans write the acceptance cases
What must hold in business terms is formulated independently of the agent β ideally before it is briefed. That turns the test into a specification rather than an echo. This is the layer at which a business department can and must have a say.
The agent writes breadth of coverage
Edge cases, null values, empty lists, error paths: here the machine's freedom from fatigue is a genuine advantage, and the cost of a missed case is low. These tests are a supplement, never a proof.
Mutation testing checks the checkers
Mutation testing injects small faults deliberately and observes whether the suite reacts. It answers the question a green indicator leaves open: whether anything is being measured at all. An occasional run across the critical modules is enough to expose false confidence.
The pyramid still holds
Many fast unit tests, fewer integration tests, a handful of end-to-end tests on the paths that carry revenue or trust. Agents tend to serve every layer at once β the result is a slow, brittle suite nobody waits for.
A word on reliability: a flaky test is more dangerous here than in classic projects. A team used to answering red runs with a retry loses exactly the warning function on which the entire review structure rests. An unstable test is therefore fixed or removed β but never ignored. How to keep end-to-end tests with Playwright stable is covered in detail in our article on website monitoring with GitHub Actions and Playwright.
5. The Second Agent as Reviewer
The obvious answer to too much agent output is another agent that reviews it. This works better than sceptics expect β and worse than tool vendors suggest. Both halves matter, because the limit is not set by model quality but by the kind of defect.
An automated reviewer is tireless, consistent and broad. It finds missing error handling, unused variables, absent permission checks and deviations from project conventions β reliably, even in the twentieth branch of the day. As a pre-filter that concentrates human attention on what remains, it is genuinely valuable.
What it cannot do has nothing to do with its capability:
Reviewer and producer share training data and therefore systematic tendencies. A pattern one considers correct, the other rarely considers wrong. It is the same effect that makes LLM-as-a-Judge setups require calibration against human judgement.
Whether a discount is commercially sound, a deadline legally permissible, or a data field collectable at all is not in the repository. That is exactly where the expensive mistakes live.
Code presented for review tends to be confirmed rather than rejected, especially when it looks clean. A review that almost never finds anything is not a good sign β it is a reason to question the setup.
Approval by a model is not approval. It is a hint. The signature stays with a human, and with it the duty to have understood what is being released.
The resulting division of labour is simple and holds up in practice: the agent filters, the human decides. Anything that changes data, moves money or is visible to the outside world requires human release β by someone who has actually answered the three questions from chapter 2. Everything else may be pre-sorted by a tool.
6. Quality Gates as a Sequence, Not a Collection
Most teams already own their checking tools: linters, type checks, tests, security scans, audits. What is often missing is the order β and order determines the value. A quality gate should catch the class of defect it catches most cheaply, and it should do so before more expensive stages consume compute and waiting time.
Static analysis. Formatting, linting, type checking β seconds, no debate, no human attention required. Anything caught here should never reach a review.
Fast tests. Unit level, a few minutes. The goal is not completeness but an early, reliable signal that the core logic is still intact.
Build and preview environment. Only after a build does something reviewable exist. A preview environment per change is the difference between "looks fine in the diff" and "works".
End-to-end against the preview. The paths whose failure hurts β login, form submission, checkout. Few, stable, meaningful tests instead of a broad and brittle suite.
Human release. Only here, once everything mechanical is green, is it worth spending the scarcest resource: human attention on the three questions no machine answers.
Shipping with a way back. A deploy without a rehearsed rollback is a bet. The way back need not be elegant, but it must work under pressure β and somebody must have walked it before.
This website follows exactly that pattern, without commercial tooling. A push to the main branch triggers a GitHub Actions workflow that builds the project, transfers the result to the target server and then purges the CDN cache. On top of that, automated checks run inside the build itself β for instance one that detects literal Markdown syntax in the rendered HTML and aborts the build, added after precisely that defect once became visible across several pages. A weekly technical audit of the published pages completes the picture. The tooling layer behind it β Playwright scripts, YAML workflows, performance budgets β is described at length in our article on website monitoring with GitHub Actions and is not repeated here.
The point of the example is a different one: no single gate in it is remarkable. What is remarkable is that each one grew out of a concrete defect that had slipped through once. That is how a robust set of checks emerges β not by being complete on day one, but by letting every incident leave behind exactly one gate.
7. From Quality Gate to Acceptance Criterion
Everything so far has been an internal matter. The more interesting part starts when software is built for someone else β because then the review question becomes a contractual question. A prototype an agent produced in a few days is impressive. It becomes acceptable only when both sides know in advance how they will recognise that it is finished.
In the classic world a requirements specification answered that. Its problem is well known: it is written at the point when nobody yet knows the system it describes. We therefore work with a functioning prototype of the core workflows instead of a document. For that approach to hold contractually, a verifiable condition has to take the place of the lengthy description β a definition of done that does not depend on who or what wrote the code.
The question "did a human type this?" is irrelevant to acceptance. The question "which checks did it pass, and who stands behind them?" is the only one that counts.
For a fixed-price engagement a short, hard list works best β not a statement of intent, but conditions whose fulfilment can be demonstrated:
Quick check: what belongs in the acceptance
The last item is the most unusual and, in practice, the most important. A prototype whose limits are stated explicitly protects both sides: the client makes the next investment decision on a solid basis, and the supplier is not measured against expectations that were never part of the agreement. Anyone wanting to apply this to AI systems rather than classic applications will find the matching metrics in our article on evals and quality assurance for AI output; the pipeline stays the same, only the metric changes. An overview of our fixed-price work is on the services page.
Conclusion
The development tools of 2026 have made an old truth visible rather than abolishing it: software does not become good because it is written, but because someone stands behind it. As long as writing was expensive, that distinction could be ignored β the author was there anyway and knew the code. Now that writing has become cheap, it is out in the open.
The consequence is not a return to handcraft. It is to treat review capacity as seriously as production capacity: cut briefs small enough to remain judgeable. Formulate tests independently of what they are meant to check. Order quality gates by the cost of the defects they catch. And leave release with a human who can justify it in their own words.
Teams that do this can use agents to the fullest without giving up control. Teams that do not will ship faster β but nobody among them will be able to say what the system actually does. The difference does not show in the first week. It shows the moment something breaks.
Questions about quality assurance for AI-generated code?
Book a free initial consultationOur Regional Expertise
We are your digital partner β regionally anchored and successfully scaling across borders.
Have a vision?
Let's check together how we can make your idea take flight.
Book your free strategy call nowExtended Specialized Glossary
Blast Radius
The scope of effect of a change β everything it can touch, not just what visibly changed. When reviewing agent output it is the key prioritisation measure: one line in a shared helper deserves more attention than a hundred lines in an isolated component.
Mutation Testing
A technique that deliberately injects small faults into production code and observes whether the test suite reacts. It answers the question a green suite leaves open: whether the tests measure anything at all or merely run alongside.
Quality Gate
An automated threshold in the delivery chain that lets a change pass only when defined conditions are met. Order is what matters: each gate should catch the class of defect it can catch most cheaply.
Flaky Test
A test that passes sometimes and fails other times on unchanged code, usually because of timing dependencies or shared state. Flaky tests are more dangerous than missing tests, because they teach a team to ignore red runs.
Slopsquatting
Registering package names that language models frequently invent, in order to distribute malicious code through hallucinated dependencies. The attack exploits a repeatable model error rather than a developer's typo.
Definition of Done
An agreed list of conditions that must be satisfied before work counts as finished. In projects involving AI it replaces the question of who wrote the code with the question of which checks it passed.


