Picture a small shop you love. The checkout already knows one kindness. Buy ten things or more, and the price drops by ten percent.
One morning a new request arrives. Five dollars off, as long as the cart is not empty. A little welcome gift.
A helper can draft that change in a minute. Sometimes the helper copies the whole checkout into a second file. Sometimes it squeezes another rule into the middle of the old one. Both versions can look finished. Only one of them keeps the shop tidy for the next kindness.
That is the whole article, really. In 2026 a person can type less of a change by hand. The shop around that change still grows more drafts, more review, and more ways to bruise a design that already works. So here is the idea to carry with you. When a design already exists, and someone can still explain it, start by extending it. If the request is the same job and the shape is awkward, tidy the shape first, then extend it. A different job gets a small new piece beside the old one. And you replace a piece only when you can say why.
This order is my conclusion, stated as mine. I did not find a paper that says, in those words, that extend-and-improve is the job now. The older rules below come from sources. Ranking them into a default is my judgment.
Two earlier notes on this site sit next door. Blueprint Over Bytes is about specifying and reviewing, once typing stops being the center of the work. When Code Gets Cheap, Complexity Moves is about estimates and planning. This one is the choice those notes leave open. You already have a living system. Do you extend it, tidy it, add a small new piece, or replace it?

Four moves, and the one to try first
A change walks in the door. You do not start by writing. You start by asking where it belongs.
A few words first, so the table stays friendly. A commit is a saved snapshot of the work. A pull request is a note that says, “please accept this change.” An agent, or coding helper, is a program that drafts code when you ask. A seam is a plug-in point the design already has. A refactor is a tidy-up of the inside. What the customer sees stays the same.
| Move | Choose it when | What "done" looks like |
|---|---|---|
| Buy or call | A product the team already trusts, and does not need to own, already does this job | You use that product. You do not build a twin |
| Extend | Someone can explain how the new behavior maps onto the current design, and a seam already exists | New behavior behind the existing front door. Callers of the stable part stay still |
| Improve | The behavior belongs here, and the current shape would force a special case, a copy, or a messy edit across the file | A tidy-up that keeps today's answers, then the small extension. Old checks still pass |
| Compose | Fitting the change inside the old program would make that program worse at its current job | A new small piece. Its output feeds the old one, or the other way around |
| Replace | Nobody still holds the story of this part, or another local tweak costs more than a bounded new design | A new design for that part, grown beside the old path while the old path still has users |
Try them in this order. Buy, if a maintained product already fits. Otherwise extend, then improve, then compose, then replace. Stop at the first move that fits, and write down why you skipped one.
Two little checks keep you honest.
Can someone still tell the story? Somebody on the team should be able to say why this part is shaped this way, and where a new case belongs. Peter Naur called that story the theory. It lives with people. A file can hint at it, but the file cannot hold it alone. If a teammate has the story, learn it before you touch anything. If nobody has it, you are patching, in Naur’s sense, and a fresh design for that part is allowed.
Is the next change easier? After you extend or improve, the design should be easier to change again. Lehman’s second law says complexity rises unless someone works to hold it down. An extension that needs a warning like “do not use this with the other mode” is a tidy-up you postponed. Compose and replace are exits. Do not drag them back into the loop.
One more line, and it is my judgment, not a study result. Helpers are fluent once the plug-in point is obvious. They are just as fluent at inventing a second copy when that point is hidden. Your job is to choose the move before the helper fills the page. Review then asks a smaller question. Does this change match the move we chose?
flowchart TD
Start["A change is requested"] --> Owned{"Does a maintained product already do this job?"}
Owned -- "Yes" --> Buy["Buy or call it"]
Owned -- "No" --> Theory{"Does someone still hold the theory?"}
Theory -- "Yes, you do" --> Fit{"How does the change fit?"}
Theory -- "A teammate does" --> Learn["Learn the theory, then continue"]
Learn --> Fit
Theory -- "Nobody does" --> Replace["Replace this part"]
Fit -- "Existing seam" --> Extend["Extend"]
Fit -- "Same job, awkward shape" --> Improve["Improve, then extend"]
Fit -- "Different job" --> Compose["Compose a new small piece"]
Fit -- "Another increment costs more" --> Replace
Extend --> Easier{"Is this design easier to change again?"}
Improve --> Easier
Easier -- "Yes" --> Ship["Ship"]
Easier -- "No, same job" --> Improve
Compose --> Ship
Replace --> Ship
Buy --> Ship
Most of the work was always change
Meir M. Lehman spent years watching software that stays in use. In a September 1980 paper he treats maintenance as every change after the first installation, a much wider bucket than bug fixes. He mentions a “generally accepted” split of 1977 U.S. programming spending, about 70 percent maintenance and 30 percent new development. That is a community estimate from that period, not a survey he ran. Leave it in 1977. It is a poor stand-in for costs today.
The argument around it is the keeper. Changing, deleting, and extending a living program is not a distraction from the job. It is the job. Two of his laws still matter on an ordinary Tuesday. Programs that model real human activity must keep adapting, or they go stale. And their complexity rises unless someone works to hold it down.
Shipping the first version starts the work. Every later change fits the design, improves it, or makes the next change harder. Helpers did not invent that fork. They just made it easier to skip the middle path and drop a second design beside the first.
More drafts, fewer finished parcels
A fast draft of the welcome gift tells you how quickly the words appeared. It says nothing about which shelf the gift belongs on. The studies split in exactly that place. Some text got cheaper. The care around it stayed. Longer walks live in When Code Gets Cheap and Is AI Generating a World of Code Slop?.
On one fresh exercise, the draft really did get faster. With GitHub Copilot, people built a sample web server 55.8 percent faster (Microsoft Research, February 2023; arXiv:2302.06590). The paper measures that speed. Whether those servers were easier to extend later sits outside it.
On familiar code, in one early snapshot, the opposite happened. METR’s trial (arXiv:2507.09089, reported 10 July 2025) asked 16 experienced developers to finish 246 real issues on repositories they knew well. With AI allowed, the tasks took 19 percent longer. The authors call it a snapshot of early-2025 tools. Other teams, other editors, and later models sit outside the claim.
Then the big funnel. The September 2026 revision of NBER Working Paper 35275, Writing Code vs. Shipping Code, studies more than 500,000 GitHub developers. It is a working paper, shared for discussion, not peer-reviewed. Extra saved changes add up to about 240 percent with autonomous agents, but that shrinks to about 80 percent more projects and only about 30 percent more shipped releases. More new apps appeared, with no increase in total usage. The authors call it a weak link. Coding speeds up. Human work later still sets the pace. (On 26 September 2026 the public landing page still showed an older summary. These numbers are from the September 2026 PDF.)
The funnel narrows: saved changes vs. what shipped
NBER Working Paper 35275, September 2026 revision. The plain reading: cheaper typing fills the top of the funnel. Review, fitting, and release decide what comes out.
Trust lagged behind the activity. DORA’s 2025 annual survey of nearly 5,000 professionals (fielded 13 June–21 July 2025) says 90 percent use AI at work and more than 80 percent feel more productive, yet 30 percent have little or no trust in the generated code. Adoption lines up with higher throughput and lower stability. Those are survey patterns. (An earlier 2025 DORA note reported worse delivery, including a likely throughput drop. The estimation article cites that one. This article uses the annual report.) Stack Overflow’s 2025 survey (49,009 responses, 29 May–23 June 2025) rhymes: 84 percent using or planning to use AI tools, 51 percent of professionals daily, and more distrusting accuracy (46 percent) than trusting it (33 percent).
Simon Willison puts the practitioner version in one line. New code is almost free; good code is not (Writing code is cheap now, read 26 September 2026). Addy Osmani’s 4 December 2024 note on the “70 percent problem” is a field observation of the same split. Both are judgment. Andrej Karpathy, on 2 February 2025, named the far end of the habit. Accept the changes, skip the diffs, let the code grow past what you understand. He called that not too bad for throwaway weekend projects, and not really coding. The hedge is his.
A cheaper input can raise total use. That picture is an analogy from William Stanley Jevons, The Coal Question (1865). The software evidence is the NBER paper above. The scarce work is review, fitting the pieces together, and choosing where the new behavior belongs. That care is the “do more” half of the idea.
You can skip a line. You should still be able to read it.
Two futures get told as if they were one. They end in different shops.
In the first, people stop reading the notes. The text is a leftover, like machine instructions most of us never open. Karpathy’s February 2025 note is that future, already tried: “forget that the code even exists.” Accept the diff. Let the program grow past comprehension. Simon Willison, on 19 March 2025, keeps the name. Vibe coding means building with a model and skipping review of what it writes. For software he would commit, his test flips. He will not commit what he could not explain exactly to somebody else.
In the second future, you can still read the notes, and a full pass is often unnecessary. The shape tells you what to ignore. The 1985 preface to Structure and Interpretation of Computer Programs already wanted that reader. Programs, it says, must be written for people to read, and only incidentally for machines to run. A good reader knows what not to read, and how to change the program while keeping its spirit and style.
Both futures are available now. Saved changes are up. Trust is limited. The NBER paper counts commits, projects, releases, and usage. It stays silent on how carefully anyone read a diff. Skipping the read is an inference, and it matches how Karpathy described his own weekend practice. Comprehension debt is this site’s name for merged changes nobody can explain. That is the first future winning.
The future I would build is the second one. You skip lines because the shape is honest, and you can still read when the shortcut leaks. One named place for discounts means one rule to change. A tidy-up before the feature keeps that skip list true. A second copy of the checkout rules fails the test. Now you read both, and neither one says which design is real.
Forecasts about losing the ability to read, or reading falling to zero, sit outside these studies. What they show is more notes being produced. Readability is still a choice, and it is still yours.
Older shoulders, in short
Each of these people argues for one move. Each one also stops short of the cartoon.
Extend, while someone still holds the story. In 1985 Peter Naur wrote that the real asset is the programmers’ theory of how the program meets the world. The text is only a trace. In his compiler story, a second team had the source and the notes, and still proposed changes that ignored structure already there. When the theory has died, he says, solve the problem afresh. That is the replace exit.
Improve, and leave what people see alone. On 6 April 2000, Joel Spolsky called a from-scratch rewrite of a working product the worst strategic mistake a software company can make. Repair the mess inside while the behavior people depend on stays. Kent Beck’s line, quoted by Martin Fowler in 2015, gives the step in one sentence. Make the change easy, then make the easy change. A refactoring changes the inside so the software is cheaper to modify, while what users see stays the same.
Add at a seam. Bertrand Meyer’s 1988 principle says a module can be open for extension and closed at the same time. Closed means others may rely on a stable description. Robert C. Martin’s 1996 column draws the working line. Meet a new requirement by adding, rather than by editing what already works. Jeremy Miller’s 2008 damper: treat it as a direction, not a goal, or you will invent plug-in points for changes that never come.
Compose, when the job is actually new. Eric Raymond’s extensibility rule asks you to leave room for later functions without scrapping the architecture, and refuses features nobody needs yet. Doug McIlroy supplies the exit. “To do a new job, build afresh rather than complicate old programs by adding new features.” Same job, extend. Different job, a small new program.
Buy, grow, and replace only what must go. Fred Brooks puts buying first. The most radical way to construct software is to skip the construction. Grow from a running skeleton, so each new function comes out of what already runs. Dan McKinley (2015) says the same about tools. Add one when it changes your chance of solving the problem. When a part really should leave, Martin Fowler’s strangler fig grows the new behavior at the edge until the old path can go. And Jeff Atwood (2007) is the reluctance under every move. Every line you keep has to be read and supported. A second copy of the shop’s rules is not a gift.
Keep the shop you have
It leaves room to add. The welcome gift is still something new. The discipline is where it sits. It leaves room to start something new, too. A problem with no story yet is supposed to grow a design, one running skeleton at a time.
It leaves future plug-in points unbuilt until a real change feels awkward. And it leaves you able to read the rules. Karpathy’s weekend habit is a choice to read less, on purpose, for throwaway work. Treating that skip as the new default, without a shape that makes it safe, is the expensive version.
So extend the designs that already exist. Improve them when an extension would only be a patch. Compose a new piece when the old program would have to change jobs. Replace a part when the story is gone. And keep everything readable enough that a full read is often unnecessary.
The studies say something smaller than the slogans. One bounded task got faster. One familiar-code snapshot got slower. Saved changes rose by more than releases did. The design rules are what you do with that gap.
Sources
Accessed 26 September 2026 unless noted. Working-paper and survey figures are dated because they move.
- Lehman, M. M. “Programs, Life Cycles, and Laws of Software Evolution.” Proceedings of the IEEE 68(9), September 1980. Maintenance as all post-installation change; the “generally accepted” 1977 70/30 expenditure split; laws as statistical abstractions.
- Lehman, M. M. “Laws of Software Evolution Revisited.” 1996 restatement. Continuing change and increasing complexity, for E-type systems.
- Naur, P. “Programming as Theory Building.” Microprocessing and Microprogramming 15, 1985, pp. 253–261.
- Spolsky, J. “Things You Should Never Do, Part I.” 6 April 2000.
- Fowler, M. “An example of preparatory refactoring.” 5 January 2015. Beck’s “make the change easy, then make the easy change.”
- Fowler, M. “Definition of Refactoring.” 1 September 2004.
- Fowler, M. “Original StranglerFigApplication.” Includes “writing tomorrow’s legacy software today.” Current pattern page: “Strangler Fig Application.”
- Martin, R. C. “The Open-Closed Principle.” C++ Report, January 1996, quoting Meyer, Object-Oriented Software Construction, 1988.
- Miller, J. “Patterns in Practice: The Open Closed Principle.” MSDN Magazine, June 2008.
- Raymond, E. S. “Basics of the Unix Philosophy.” The Art of Unix Programming, chapter 1.6. Extensibility, and McIlroy on building afresh rather than complicating an old program.
- Brooks, F. P. “No Silver Bullet: Essence and Accidents of Software Engineering.” UNC technical report 86-020, 1986. Buy versus build; grow, don’t build.
- Brooks, F. P. The Mythical Man-Month, chapter 4. Conceptual integrity as the central design constraint. I am not linking a full-text copy.
- McKinley, D. “Choose Boring Technology.” 30 March 2015.
- Atwood, J. “The Best Code is No Code At All.” 30 May 2007.
- Jevons, W. S. The Coal Question, 1865. Analogy only. The software evidence is the NBER paper below.
- Peng, S., Kalliamvakou, E., Cihon, P., and Demirer, M. “The Impact of AI on Developer Productivity: Evidence from GitHub Copilot.” Microsoft Research, February 2023. Preprint: arXiv:2302.06590. 55.8 percent faster on one JavaScript HTTP-server task.
- Becker, J., Rush, N., Barnes, E., and Rein, D. “Measuring the Impact of Early-2025 AI on Experienced Open-Source Developer Productivity.” METR, 10 July 2025. Paper: arXiv:2507.09089, revised 25 July 2025.
- Demirer, M., Musolff, L., and Yang, L. “Writing Code vs. Shipping Code.” NBER Working Paper 35275, May 2026, revised September 2026. Not peer-reviewed. Landing page, which still showed an earlier abstract on the access date: nber.org/papers/w35275.
- GitHub. “Octoverse: A new developer joins GitHub every second as AI leads TypeScript to #1.” Published 28 October 2025, updated 28 February 2026. Reporting window 1 September 2024–31 August 2025.
- DORA. State of AI-assisted Software Development (2025). Survey 13 June–21 July 2025. Announcement: Google Cloud blog. The earlier analysis cited by the estimation article is Impact of Generative AI in Software Development.
- Stack Overflow. “2025 Developer Survey: AI.” Fielded 29 May–23 June 2025.
- Willison, S. “Writing code is cheap now.” Living guide, read 26 September 2026. Practitioner judgment.
- Osmani, A. “The 70% problem: Hard truths about AI-assisted coding.” 4 December 2024. Field observation.
- Abelson, H., and Sussman, G. J., with Sussman, J. Preface to the first edition, Structure and Interpretation of Computer Programs. MIT Press, 1985. Readable HTML of that preface: sarabander.github.io/sicp. Programs are written for people to read; a competent reader knows what not to read and can still modify the program in its original spirit.
- Willison, S. “Not all AI-assisted programming is vibe coding (but vibe coding rocks).” 19 March 2025. Vibe coding means not reviewing the generated code. His production rule is that he can explain exactly what it does to somebody else.
- Karpathy, A. Vibe-coding post, 2 February 2025. Status on X. Quoted on Willison’s site, 6 February 2025.