Skip to content
Back to all field notes vibe · 9 min

Vibe coding debt: what you actually owe and when it's due

The interest on vibe-coded software is real, but it is not one number. It is three separate debts with three different due dates.

field note 9 min

You shipped a working app in a weekend. An agent wrote most of it, you steered, the demo landed. Three weeks later a two-line change takes you a full day, and you are not sure why the app still runs. That day you lost is the interest payment. You just did not see the loan being taken out.

Everybody calls this technical debt. The name is right and it is also hiding something. When Ward Cunningham coined technical debt, the debt was code you understood, written under pressure, that you chose to clean up later. Vibe coding produces a different animal: code you never read, generated at a speed no human review kept up with. Calling it one lump of “debt” tells you it exists. It does not tell you what you owe or when the bill arrives.

So let me split it into the three debts that actually behave differently.

Debt is not one number

The mistake is treating a vibe-coded codebase as a single pile of shortcuts to pay down someday. That framing paralyzes you, because “rewrite it properly” is never the right size of task and never the right week to do it.

The debts that matter accrue interest at different rates and come due on different triggers. If you can name them separately, you can pay the expensive one first and leave the cheap one alone. That is the whole move.

Layer 1: comprehension debt

This is the one nobody prices in. It is the gap between what your software does and what you can explain about it.

When you write code by hand, comprehension comes for free as a side effect. When an agent writes it, comprehension is a separate cost you have either paid or deferred. Most vibe coding defers all of it. The app works, so you move on, and the model of how it works lives nowhere except in a chat transcript that scrolled off the screen.

Comprehension debt is invisible until you need to change something. Then it charges interest at a brutal rate, because every edit starts with an archaeology session. You are reverse-engineering your own product. This is the tax behind the fear of touching your own code: the fear is rational, and it is comprehension debt sending you the bill.

The dangerous part is that it compounds silently. Each new feature the agent adds on top of code you did not understand widens the gap. By month three you are not maintaining an app. You are negotiating with a stranger who happens to share your repo.

Layer 2: test and verification debt

This is the debt you can see, which is exactly why people mistake it for the whole problem.

Vibe-coded apps usually ship with no tests, or with tests the agent wrote to describe what the code already does rather than what it should do. Either way, you have no independent signal that the thing works. You have the fact that it worked when you last clicked around, which is not the same claim.

Verification debt has a specific and unpleasant property: it stays cheap right up until it is catastrophic. As long as nobody changes anything, the absence of tests costs nothing. The moment you or an agent ships a change, the missing tests are the reason a broken feature reaches a user before you notice. This is the mechanism behind every new feature breaking an old one: without a verification layer, there is no gate between “the agent said it works” and production.

There is a version of this that is worse than having no tests, which is having tests that pass without proving anything. An agent that reports “all tests green” when the suite never exercised the changed path has handed you a false receipt. Distinguishing a real pass from a green build that verifies nothing is its own discipline, and it is why a green build is not a correct feature.

Layer 3: architecture debt

This is the slowest and the most expensive, and it is the one the metaphor was originally about.

Architecture debt is structural: duplicated logic that should be one function, a data model that assumed one use case and now serves five, boundaries that were never drawn so everything depends on everything. Agents are very good at producing this, because each prompt is a local optimization. The agent solves the change in front of it well and has no standing model of the system it is changing. The result is code that is locally correct and globally incoherent: every piece defensible, the whole drifting.

Architecture debt charges the highest interest of the three, but it charges it late. You can run on bad architecture for a surprisingly long time. What it steals is your future velocity. The app that took a weekend to build takes a month to extend, and the reason is never one bad file. It is the accumulated cost of a structure nobody designed.

When each one comes due

The debts have due dates, and knowing them is how you stop paying interest by surprise.

Comprehension debt comes due the first time you need to change something non-trivial, which for a real product is usually within the first month. It is the earliest and the most frequent bill.

Verification debt comes due the first time a change ships that breaks something you did not touch. You cannot predict the date, but you can be certain it exists, and it lands harder the more users you have when it does.

Architecture debt comes due when you try to scale the app past its original shape: a new integration, a second customer type, a feature that cuts across three others. That is the 90-day range where vibe-coded apps tend to break, not because of a single failure but because all three debts come due within weeks of each other.

Paying it down without stopping the world

You do not fix this by rewriting. You fix it by paying the debts in the order they charge interest.

Pay comprehension debt first, because it is cheapest to service and everything else depends on it. Before you touch a feature, get the system to explain itself: what this code does, what it assumes, what would break if it changed. You are not documenting for its own sake. You are recovering the model you never built.

Pay verification debt second, and pay it precisely. You do not need full coverage on a weekend prototype. You need tests on the paths that would hurt a user if they broke, written before you change them. That is also the real answer to when to add tests and architecture: not on day one, not never, but at the moment a path becomes load-bearing.

Pay architecture debt last and only where it blocks you. Refactoring code you are not about to change is spending money to reduce a bill that was not charging you interest. Restructure the part you are extending, leave the rest.

The through-line is that all three debts are really one missing thing: a durable record of intent and evidence that lives outside the agent’s context window. When that record does not exist, every change starts from zero. That is the same failure that makes a prototype impossible to promote to a product without a painful reckoning.

Where PaellaDoc fits

The reason vibe coding produces all three debts at once is that the agent’s understanding, the acceptance contract, and the evidence of what passed all evaporate when the session ends. Nothing outlives the chat.

PaellaDoc exists to keep that record alive locally: the intent behind a change, the decisions that shaped it, the code it touched, and the evidence that it worked, connected in one place instead of scattered across transcripts. It does not make the debt disappear. It makes the debt legible, so you can see which layer you owe and pay it deliberately instead of discovering the balance the hard way, on the day a two-line change costs you a week.

FAQ

Is vibe coding technical debt worse than normal technical debt? It is a different shape. Normal debt is usually code you understood and chose to defer cleaning. Vibe coding adds comprehension debt on top: code you never read, so you owe understanding before you can even assess the rest.

Do I have to add tests to a vibe-coded project right away? No. Add them to the paths that would hurt a user if they silently broke, and add them before you change those paths. Full coverage on a throwaway prototype is paying down a debt that is not charging interest.

How do I know which debt to pay first? Pay comprehension debt first because everything depends on it, verification debt next on load-bearing paths, and architecture debt last and only where it blocks the change you actually need to make.