Do We Still Need Code Reviews in the Age of Coding Agents?
DEV Community

Do We Still Need Code Reviews in the Age of Coding Agents?

For most of my career, code review has been a fairly simple idea. One engineer writes some code, opens a pull request, and another engineer reviews it before it gets merged. The second engineer looks for bugs, questions design decisions, suggests improvements, and ultimately gives the team another level of confidence that the change is safe to ship. It is such a normal part of software development that we rarely stop to question the assumptions behind it. One of those assumptions is that another engineer wrote the code. That assumption is becoming less reliable. Today, a coding agent can implement an entire feature, run the tests, fix failures, refactor the implementation, and prepare a pull request. The engineer who opens that pull request may have spent most of their time reviewing and directing the agent rather than writing the code themselves. This makes me wonder whether our traditional code review process still makes sense. Not because I think code review is obsolete. I think the opposite is true: we need verification more than ever. But I think we need to change how we think about code review. What was code review actually for? Before we decide what should happen to code review, it is worth asking what problem it was solving in the first place. When one engineer writes a change and another engineer reviews it, we get a second set of eyes. The reviewer might catch a bug the author missed, notice that an abstraction is wrong, identify an edge case, question an architectural decision, or simply ask why something was implemented in a particular way. There is also a social dimension to code review. It creates shared ownership and knowledge across a team. The code does not belong exclusively to the person who wrote it. All of that remains valuable. But not every part of the traditional process is equally valuable when the author is an AI agent. I have started thinking about coding agents as something like flawed peers. Imagine that you are a seasoned engineer and you have a very fast colleague who is capable of producing an enormous amount of code. They can work tirelessly, know an impressive amount about software development, and solve many problems very well. At the same time, they are inexperienced in your particular system and can occasionally make mistakes that seem obvious in hindsight. You would not blindly merge their work. You would review it. You would give them clear constraints. You would run automated checks. You might ask another specialist to look at particularly important changes. That sounds quite a lot like the agentic development workflow we are building now. The engineer opening the PR is already a reviewer This is where I think our traditional PR rules start to become interesting. Suppose a team has historically required one human review for every pull request. The traditional workflow looks something like this: Engineer A writes the code → Engineer B reviews the code → merge. Now consider an agentic workflow: Agent writes the code → Engineer A reviews the code → Engineer A opens the PR → merge. If Engineer A has genuinely reviewed the implementation, understands the change, and is willing to take ownership of it, what exactly are we gaining from requiring another human to perform a second generic review? The PR being opened does not magically make the code more trustworthy. The meaningful event happened before that: an engineer examined the work and decided that they were prepared to own it. This is why I think we should be careful about treating approval counts as a proxy for quality. If your previous process required one review, I think there is a reasonable argument that an agent-generated change which has been thoroughly reviewed by the engineer opening the PR may not need another generic human approval. If your process required two human reviews, then perhaps the agent-generated change gets one human review by the owner and one additional human review after the PR is opened. The exact policy will depend on the risk of the system and the kind of change being made. The important part is the principle: The number of approval buttons pressed is not the same thing as the amount of verification performed. Trust the engineer, get ownership in return There is also a cultural issue here. If an experienced engineer reviews an agent-generated change, opens the PR, and says "I am happy to own this", I think we should take that statement seriously. We often say that we want engineers to have ownership. But ownership without trust is difficult to achieve. If we tell engineers that they are responsible for the code but then require another person to validate every decision they make, we are creating a system where responsibility and authority do not quite match. I would rather move toward a model where we say: You reviewed it. You understand it. You own it. In return, we should expect engineers to take that responsibility seriously. This does not mean trusting every change equally. A production database migration, authentication change, or financial transaction workflow deserves a different verification strategy from a small UI change. It means that our process should respond to risk and uncertainty, rather than blindly applying the same number of reviewers to every pull request. The bigger problem is code volume There is another problem that I think is even more important. Coding agents make producing code dramatically cheaper. That is fantastic. It also creates a problem. If generating code becomes cheap enough, the amount of code produced can increase much faster than the amount of human attention available to review it. We cannot solve that problem simply by adding more reviewers. If an agent produces ten times more code and our answer is to have humans manually inspect ten times more code, we have simply moved the bottleneck from writing software to verifying software. Human attention is scarce. So we need to become much more selective about where we spend it. Don't review what you can make unrepresentable This is where architecture becomes a much more important part of code review. There are many classes of bugs where I would rather not depend on a reviewer noticing the problem. I would rather design the system so that the incorrect implementation is difficult or impossible to represent. Consider a database schema. If the database requires a value to satisfy a particular constraint, we don't need to rely entirely on every application developer remembering to validate that constraint correctly. The database can enforce it. Or consider a business workflow. If a process can only move from Pending to Approved or Rejected , we can represent those states explicitly rather than allowing arbitrary strings and hoping that every piece of application code handles them correctly. Finite state machines are a good example of this approach. The architecture itself describes which transitions are valid and which are not. The same idea applies to types, contracts, API boundaries, validation, generated code, static analysis, automated tests, and many other forms of explicitness. The goal is not to make developers more careful. The goal is to make certain mistakes impossible. That changes the economics of code review. Instead of asking a human to inspect every line and think about every possible failure mode, we can move some classes of verification into the system itself. The reviewer can then spend their limited cognitive capacity on the things that actually require human judgment. Verification becomes a layered system This suggests a different model for reviewing agent-generated code. At the bottom, we have constraints and architecture that prevent entire classes of incorrect implementations. Above that, we have automated verification: type checking, tests, static analysis, security scanners, contract tests, database constraints, CI checks, and whatever else is appropriate for the system. Then we have the engineer who reviews the change and takes ownership. And for changes where we want additional confidence, we can add another layer. Adversarial agents. What if the reviewers were agents too? We don't necessarily have to choose between one human review and three human reviews. We can introduce specialized agents whose job is not to approve the code, but to try to find reasons why we should not trust it. Imagine an agent whose only responsibility is security. It reviews the change and asks questions such as: "Can this input be manipulated? Did we introduce an authorization bypass? Are there new injection opportunities? Did this change expose something that should remain private?" Another agent might specialize in performance. It could look for expensive queries, unnecessary allocations, N+1 database access, contention, excessive network calls, or other performance problems. We could have agents specializing in reliability, backwards compatibility, API design, testing, accessibility, architecture, or whatever concerns are particularly important to a given system. The important part is that these agents have specialized responsibilities. I don't want ten generic agents saying "LGTM." I want adversarial agents trying to break my confidence in the implementation. The security agent should be trying to find a security problem. The performance agent should be trying to find a performance problem. The architecture agent should be trying to find an architectural violation. And, just like the coding agent, we should remember that these are flawed peers. A security agent does not prove that our application is secure. A performance agent does not prove that the system is fast. They provide another independent attempt to find problems. That can still be extremely valuable. More verification without a longer delivery cycle This gives us an interesting alternative to the traditional approach. Today, if a change is considered important, we might respond by adding more human reviewers. That increases the amount of human at

Read on DEV Community ↗ ← Back to News

Comments

No comments yet. Start the discussion.