Reviewing generated code like an owner

Spot the plausible-but-wrong patterns, check the error paths and boundaries, and know when deleting the work is faster than correcting it.

Code you did not write, that looks like code you would write

Generated code is dangerous precisely because it is fluent. It uses your naming, your formatting and a familiar structure, so it reads as reviewed. The review has to be about behaviour, not style - the style is already fine, and that is what makes the mistakes easy to miss.

PatternWhy it is wrongHow to check
Validation that duplicates a schemaDrifts from the real rulesGrep for a second copy of the rule
Error caught and logged, not returnedCallers treat failure as successFollow every catch to its return
Retry without a boundTurns an outage into a stormLook for a max attempt count
Permission checked in the UI onlyThe API is still openTry the request without the token
Off-by-one on a slice or indexSilent data loss at the edgeTest the first and last item
Timezone taken from the machineWrong day near midnightCheck for an explicit zone
💡
Read the error paths first, then the happy path. The happy path was the point of the request and got most of the model's attention; the error handling was an afterthought, and that is where the defects concentrate.

Tracing what it touched

# what did it depend on?
git diff --stat
git diff package.json

# who else calls the function it changed?
grep -rn "applyDiscount" --include=*.ts .

# which tests actually exercise the new branch?
npm test -- --coverage --collectCoverageFrom='src/discount.ts'
  • Every new dependency is a supply-chain decision. Check the package name character by character - typosquats are a real attack against agent-written manifests.
  • Every changed public function needs its callers inspected, not just its tests.
  • Coverage tells you which lines ran, not which were checked; use it to find untouched branches, not as a quality score.
  • A change to a config or CI file deserves more scrutiny than a change to a component, because its blast radius is larger.

When to delete and rewrite

  1. Cause is understood and local: fix it.
  2. Cause is understood but the design is wrong: rewrite that one function or module, keeping the tests.
  3. Cause is not understood: reproduce it first. Rewriting code whose failure you do not understand usually reproduces the same bug.
  4. Two failed corrections on the same defect: restart the task in a fresh session with a tighter spec.
  5. More than about a third of the code needs changing: delete the increment and re-prompt, so you review once rather than twice.
git restore src/discount.ts          # drop just this file
git checkout HEAD -- src/features/   # reset a whole directory
git switch main && git branch -D experiment/x

Deleting feels wasteful and usually is not. A patch on top of a wrong design accumulates explanations, and the next reader inherits all of them. Reverting and re-prompting with what you learned is often the cheaper path - and it keeps the codebase looking like something a person intended.

FAQ

How long should a generated diff take to review?
If you cannot read it carefully in a few minutes, it is too large to have been requested in one go. Split it and review each piece - large diffs get skimmed, and skimming is where an agent's mistakes survive into production.
The code is ugly but works. Should I fix it?
Judge on the cost of the next change, not on taste. If the structure will make the next three features harder, fix it now while the context is fresh. If it is merely unfashionable and nobody needs to change it, leave it and spend the attention on the error handling.

Version control as your safety net Debugging when the agent goes in circles

Last refreshed 2026-09-18.