About 1 result (0.09 seconds)
2026-07-12 · 9 min readShort answer: AI coding agents optimize for the check you gave them, not the outcome you wanted. A build passing means the code compiles; it says nothing about whether the page behaves correctly. Validate the rendered output, not the report that says the work is done.
Six failure modes I hit shipping real code with an AI agent — what they looked like, how I caught them, and the discipline that fixes all six.
The agent optimizes for the check you gave it, not the outcome you wanted.
A build passing means the code compiles. It says nothing about whether the page behaves correctly. Lint passing means the code satisfies a set of static rules. It says nothing about whether the form sends, whether the default state is right, whether production matches the repository, or whether the thing you asked to remove was the thing that got removed.
Every failure below looked different. Underneath, they were the same failure.
I asked the agent to collapse six sections into accordions and default a contact form to closed.
It reported complete. Build passed. Lint passed. Its own validation passed.
I opened the deployed preview. All six sections were wide open. The form was expanded.
The root cause was my validation instruction. I had told it to verify that the text was still in the HTML. That check passes whether a <details> element is open or closed. It proved the content still existed. It did not prove the rendered default state was correct.
The fix was to validate the rendered default state: no open attribute on first render. It worked the first time after that.
My bad validation instruction caused the failure. That is the point. The agent did exactly what I asked it to verify.
An email-capture endpoint returned a clean 200 with no provider wired. It was a stub returning success.
A contact form sent from an unverified subdomain, got a 403 on every submission, and swallowed the provider error into a generic "failed to send."
Agents are trained to make things work. A stub that returns success looks like working code. A caught error with a friendly response looks cleaner than a loud provider failure. The interface behaves. The logs stay quiet. The leads disappear.
The fix is to ban fake success in the prompt. Demand loud failure over silent success. If the provider is not configured, fail. If the provider rejects the request, show the real operational state somewhere the operator can see it.
This is the failure that quietly drops leads forever.
I audited a site whose content was invisible in search and found that 12 of its 13 articles did not exist in the repository at all.
They were live on production. They were not in git.
One deploy from an older repository state would have silently deleted the content library.
The fix is to ask, "Is production ahead of my repo?" as an actual question. Do not assume the repository is the source of truth because it is supposed to be. When you find drift, figure out how it happened. A one-time content recovery fixes the immediate danger. Understanding the publishing path keeps it from happening again.
I gave the agent a repository path from memory. It did not exist.
The agent found a different repository, assumed it was the right one, and worked in it. It mentioned the substitution in a footnote at the end.
It happened to be right.
That is not reassuring.
The fix is to start every prompt with an audit step that reports the actual repository path, environment variables involved, and framework before touching anything. That small pause is cheaper than perfectly executed work in the wrong codebase.
A regex in my own free SEO/GEO/AEO checker reported a valid 150-character meta description as "2 characters."
The root cause was precise and embarrassing. The regex rejected both quote characters regardless of which quote opened the attribute. A double-quoted description containing an apostrophe — content="It's a..." — truncated at the apostrophe and captured It.
Two characters.
It had been quietly making good pages score badly.
Google Search Console flagged a "Duplicate without user-selected canonical" error on my homepage. I ran it through my own checker, which said the canonical was fine.
Both were right.
The tag existed. The checker tested presence. The tag was not correct.
Then I found that 51 of 53 pages were emitting the homepage's share metadata instead of their own — a metadata default in a root layout that no page overrode. Post any link in Slack and the preview card advertised the wrong page. The site ran like that for months.
My checker confirmed the tags existed and moved on.
Testing for presence is not testing for correctness.
The checker has since been hardened: canonical correctness including self-reference and host match, Open Graph and Twitter consistency including detection of site-wide default leakage, title and meta length limits, impact tiering, and inline evidence for every finding.
The broader lesson is the same one in Check Your Work: Verification Discipline, From Both Ends: a test is useful only if it can fail when the outcome is wrong.
I asked the agent to prune demo and template pages from a sitemap.
It also swept out 12 real articles that matched the pattern. The sitemap went from 104 URLs to 26. The summary reported success.
The fix is simple: for destructive operations, make the agent print what it removed and what it kept, with counts. Then read both lists.
The summary is not the inventory.
This is also how I approach custom application development: the build is only one part of the work. Verification, operational failure modes, and what happens after deployment are part of the product.
The code was the easy 20%. That is the part everyone posts about.
The other 80% was infrastructure, verification, and the unglamorous work of checking whether the thing that said it was done was actually done.
This is not an argument against agents. I shipped more in two days than I would have shipped in two weeks otherwise.
It is an argument about where you have to stay awake.
Look at the rendered page. Every time.
Gary Corriston runs Corriston Consulting, working with agencies and in-house marketing teams on paid media, SEO, marketing operations, and demand gen infrastructure. He's also building Campaign Budget Optimizer, an AI-native cross-platform budget allocation tool launching May 2026.
Book an intro call →
A passing build proves that the code compiles. It does not prove that the rendered default state is correct, that a form reaches its provider, or that the requested content survived a destructive operation. Validation has to exercise the outcome that matters, not a nearby condition that can pass while the feature is still wrong.
Validate the rendered outcome instead of trusting the completion report. Open the page, inspect its initial HTML and state, submit the form, and confirm the external operation really happened. The check must be capable of failing when the user-visible outcome is wrong.
No. AI coding agents make execution dramatically faster; the article's author shipped more in two days than he otherwise would have shipped in two weeks. The lesson is to keep human judgment in the loop for scope, destructive operations, production state, and deciding which outcomes actually matter.
Test the browser-visible default state and the real operational result. For an accordion, confirm the first render has no `open` attribute. For a form, submit it and verify the provider accepted the message. For metadata, inspect the rendered tags and compare their actual values, hosts, URLs, and lengths instead of checking only that tags exist.
Capture a before-and-after inventory with counts, then review both what was removed and what was retained. A success summary is not enough. If the operation affects pages, data, or files, the retained set is as important as the deleted set.