Author here. No analogy is perfect, but this is how working with code has felt for me for a while, so I wanted to write down my thoughts about it.
I wrote this a couple of months ago, and everything moves so fast nowadays that the concept of factories is already being blurred as harnesses get better and require less tooling around them. I still think that the distinction between wanting to be in the loop vs automated out from it holds up, though.
There are other interesting aspects of malleable code that I don't explore in the article, for example:
- Ownership. People feel less attached to their code, which has both good and bad consequences (e.g. fewer ego battles but less accountability).
- Malleable software that adapt to users. Huge topic, many interesting questions to explore.
- Assets in code. Things like (some) 3D graphics and animations can now be done entirely in code. Before they were tedious to code and very difficult to tweak (malleability changes that).
> When the mold is done, you let the agent pour in the code in any format you like.
Exactly. And the mold could be a spec, an MVP or even one of the implementations (e.g. the Swift one) acting as the source of truth for the other versions.
> "just" give them Claude and teach them to describe what they want and iterate to get something that maybe resembles an MVP but in more cases is just an interactive UI spec
That's a great example of what malleable code unlocks. You let the client to create the mold themselves, refine it and then use it to build it properly.
> What it boils down to is that the future of coding is more about creating the mold where the code is poured in and knowing how exact of a mold is "good enough" for the problem at hand.
> When the mold is done, you let the agent pour in the code in any format you like. It can create a Swift version, Rust version and a web assembly version in "half a soda" as you put it =)
Unless you use code, that mold is at best a formless bag.
The reason people use software is because there's a need to manipulate some data/information, transfer it, and interact with it (input or output). All those actions needs to be done correctly, and if not possible the error should be reported. To get to that level of correctness, we need to be formal with how we express the process, which means essentially going from a non-zero amount of ambiguity (natural language) to zero (programming language).
Using AI to translate specs/prompt to code is just asking it to randomly resolve any ambiguity found in the specs. And as any experienced dev knows, some of those are just tradeoffs where there no right or wrong answers, just contextual ones that evolves over time and space.
> Before I had to dig specs of an application out of a client's mind and try to form them into software with a full-ass team. Now we can pretty much "just" give them Claude and teach them to describe what they want and iterate to get something that maybe resembles an MVP
I wonder if there's actually been conversation with the client before? Where you use some prototyping tools like RAD or Sketch to resolve UI issues, get in touch with the actual domain experts,... or was it just a telephone game full of politics?
> They can be TLA+ definitions, linters, cyclomatic complexity checkers, unit tests, integration tests, end to end tests etc.
That’s even more work than just writing the code, at least the latter is immediately useful. The reason we create complicated machinery is mostly because of industrial scale. Molds and factories help create thousand of pieces and the total value of the latter is way more than the cost of the former.
The reason we don’t write specs and other kind of docs extensively is usually that the time taken is way more than just writing the code. Yes, code do require formal thinking, and a training in syntax. But a lot of jobs require understanding some concepts and training in the jargon and techniques.
> No program will ever be perfect[0], but you need to get it good enough for the problem at hand.
The nicest thing about software is that some subproblems are nearly eternal. That’s why we reuse code and utilities. Also while some problems do evolve, it’s usually done slowly and in a way, predictably (as in how, not when). Taking care to solve it once well, usually is better, rather than solving it again and again.
It’s more important to worry about the solution to a specific problem (in terms of concept), than to worry about code. Coding was not, and will never be the primary problem. Any experienced developer knows this, which is why most will says they spend very little time thinking about code and writing it.
> Before I had to dig specs of an application out of a client's mind and try to form them into software with a full-ass team. Now we can pretty much "just" give them Claude and teach them to describe what they want and iterate to get something that maybe resembles an MVP but in more cases is just an interactive UI spec we can use as a reference to build the actual tool.
What are they paying you for if you’re just having your clients vibe code their own apps?
Vibe coding the "feel" and flows of the app - if they know how to do it and what they want.
These are for highly specific stuff like a tool to help a copywriter work on game dialogue for example.
It's a fuckton faster for the actual expert in the field to do it than me first learning enough of their craft to know the terms and how they work to get there eventually.
The actual code that does anything meaningful is made by Actual Programmers. As well as everything beyond that, where it's run the CI pipelines, tests, infrastructure to run it etc.
It's like an architect asking a client to draw and describe their dream home and using it as a basis for the final product.
The mold analogy falls apart under even cursory examination: why create a mold in ambiguous uncheckable human languages? Just create a reference implementation.
Nobody said the mold has to be done in a human language. It _can_ be a part of it for the fuzzy bits.
But it's just writing the hard limits on the outside, in code. Define that when A goes in B must come out. Enforce hard linting rules and other code-level checks on the output etc.
This analogy is apt for working with LLMs. Were you aware, tho, that it has repeatedly been used to describe Lisp?
I think Lisp is an ideal language to use with an LLM, because it is essentially a notation for a logical assembly code, and I expect there to be compound benefits in using it with AI.
Lisp [...] made me aware that software could be close to executable mathematics.
— ACM Fellow Profile of L. Peter Deutsch.
APL is like a diamond. It has a beautiful crystal structure; all of its parts are related in a uniform and elegant way. But if you try to extend this structure in any way — even by adding another diamond — you get an ugly kludge. LISP, on the other hand, is like a ball of mud. You can add any amount of mud to it [...] and it still looks like a ball of mud!
— R1RS (1978) page 29, paraphrasing remarks attributed to Joel Moses.
Part of the beauty of the ball-of-mud quote is that there really does seem to be a causal connection between Lisp's use of generic, unencapsulated, largely un-type-checked data structures and its extensibility. The converse implication is that we should expect specialization, encapsulation, and aggressive type-checking of data structures — all strategies extensively pursued in various combinations in modern language paradigms — each to retard language extension.
Each of these three characteristics of Lisp serves to remove some kind of automated restriction on program form, leaving the programmer more responsible for judging what is appropriate — and thereby shifting things away from close conversation with the machine, enabling (though perhaps not actively encouraging) more human engagement. The downside of this is likely obvious to programming veterans: it leaves things more open to human fallibility. Lisp has a reputation as a language for good programmers. (As a remark attributed to Dino Dai Zovi puts it, "We all know that Lisp is the best language around, but in the hands of most it becomes like that scene in Fantasia when Mickey Mouse gets the wand.")
LISP is extensible in two ways. First, there is the simple ability to define new functions; these are used in a way that is both syntactically and semantically identical to built-in primitive functions like CAR. This is in contrast to “algebraic” programming languages, which either make an arbitrary syntactic distinction between addition, say, and a user function, or wander into the quagmire of extensible parsers. Second, there is a uniform macro facility for transforming one syntactic form into another; this facility is based on internal data structures rather than external character-string syntax.
One of the links here is somewhat buried and I want to underscore it. Note the "WriteOnlyLanguage", this describes the highest productivity programming language not meant for consumption by other humans -- just the author and the machine.
A language that allows one to easily customize syntax, flow control structures, etc. for the convenience of the author without regard to future readers. It allows one to create their own language or sub-language in their mind's own image without worrying about other readers' preferences or grokkability of the style. Contrast with a CorporateLanguage that assumes or targets masses of mediocre PlugCompatibleInterchangeableEngineers (programmers) where there may be many readers with varying skills. Such a language tends to hard-wire ways of things to reduce variation. One can say that a CorporateLanguage is for the herd of sheep while a HackerLanguage is for the lone wolf. ("Hacker" could be "hobbyist" or "tinkerer" also in this context. It's not meant to only include the devious version of "hacker".)
One can often achieve high personal productivity with a HackerLanguage, but readability may fit a very narrow audience or be questionable. Sometimes derogatorily called a WriteOnlyLanguage.
Code always was, it's supposed to be malleable. It's why it's long been said that code is a liability, not an asset. It's the data you generate with that code that's your asset. You can always rewrite the code.
We, in general, are just very bad at letting code ossify, or for this metaphor, dry out and crumble. AI does not solve this problem and I fully expect to see situations where AI generated code becomes so hard to work with that even LLMs prefer to throw it away and start fresh again.
Code was malleable only to a developer with great code comprehension. In my experience, this is actually very rare.
It seems much more common for a developer to see some code, say it sucks, and rewrite it from scratch, rather than doing a little bit of modification to extend it, even if it was purpose built to be extended. The result being some code that does a small fraction of the original, but is "clean".
And often, it's not the code that is the issue. You understand the code perfectly fine and can edit it easily. The main issue is always finding out the "why" so you do not remove any Chesterton's fence while coding for a new change request.
Thats very true, calling coding craftmansship or considering oneself an amazing coder but only for new projects is obviously wrong.
A great coder loves legacy old projects because theyre challenging, unpredictable, undocumented, and if you figure out, you are like a God.
Starting the perfect greenfield project and writing amazing code the first week is a skill every freshmen student at a CS college has. That's not a problem area, its a solved thing.
But do it for 10 years straight after 5 acquisitions, different infrastructure, different industry, language, culture? You are a RARE BREED.
Or even simpler put, never measure yourself with easy things, only with the hard ones since then the easy things are a joke.
> But do it for 10 years straight after 5 acquisitions, different infrastructure, different industry, language, culture? You are a RARE BREED.
Been there done that, the problem is you will not get rewarded by your superiors. Keeping old shit alive is useful to keep your skills sharp, but it's bad in a culture utterly dominated by "resume driven development".
I romanticized even before, because there is a reason why society's view of developers shifted from geek losers to rich in the past 15 years. I remember when 15 years ago a girl told me that I'm different, because I'm not as looser as how she imagined developers.
Did the delivery work functionally as expected? If yes, then they understood what they need to understand to do that work on code. You don't need to understand the whole codebase, just the parts relevant to the work at hand.
Ive worked and work with people who I dont consider super talented but sure as hell they understand the code, maybe just some lines, maybe the method, maybe the class, maybe the module and further.
Unless you worked at the shittiest company in the world, lets try to not bring others down just because they weren't as amazing as we are. They might have other skills weve lacked.
E.g. like a journalist complaining that they colleagues didn't publish books... who cares? Thats not their job, they need to write clear good concluded articles. If they write their articles like books, nobody reads that shit.
Many people here are saying "code was always malleable", "code was always clay". But how many actually do their work in live interactive REPLs, which I'd say is the truer analogy?
The big trick always was to limit your scope. If you can't do that or if your tooling doesn't help you with that then very quickly you will run into the limits of what you can still keep in your head.
We tend to forget in tech-oriented forums that most of us are bound to those who pay our salaries, and for many developers that payment is to be focused on revenue-generating, or client-focused work.
Developing advanced comprehension and being able to use it for long-term system stability are unfortunately not always paired in the daily work.
That sounds a bit extreme, to me, I think code was always malleable simply from good experienced devs. The "developer with great code comprehension" just did it better I guess but it wasn't a skill shared only by the holy Coder chosen by Destiny or something.
Also comprehension is one side, its "Consuming" code, but it doesnt say anything about theyre talent of producing great code.
I disagree. Code can be/was more malleable if it's designed well, with pure FP. People kept on moving away from OOP and more towards this idea of pure functions and composition, creating more robust and malleable software.
Now instead of aiming for robust, malleable code, people are throwing up their hands and saying. "It was always a mess, let's just keep throwing more tokens at it."
Yeah, people said "I'll use javascript and python because it'll help my velocity to forget about types" and then went back and reinvented types and functional programming in both. And now they're so confounded by the pile of confusion that they're yielding to LLMs.
If a dev just followed public trends, then I guess I can see how they came to the conclusion that this is the best way out, because their baseline level of comprehension is so far in the floor. It's like circling around the entrance of a maze for days until finally an AI merchant shows up near the door, and they say "well clearly, the only way to get out of this maze is to pay the merchant for his fancy roomba to carry me out" instead of carefully mapping your way through.
From a selfish perspective, that's fine by me. I've built up skills that I don't think will be replaced in the near-term, and in that same period most people will end up de-skilling. The only downside is that I've had to shrink my circle that I collaborate with even further.
Truly spoken as someone who has never worked with legacy code. You know, the kind that's still running Java 1.something when Java was already doing full numbered releases.
The kind that works, but everyone who knows why has left the company. The whole codebase is written in a way that makes automated testing either impossible or so time-consuming that the client will never pay for the required refactoring.
There is way too much code in the world we never were able to rewrite due to real-world concerns. There were people who had the skill, but a part of that skill came with knowing the risks of doing major refactoring to a money-generating system that is ancient, but still works.
Anecdote: I had to work with a system where the original coder (long gone) had rewritten Linked Lists with their custom solution that worked normally except the first X items were the sum, average and mean of the data. Fun times.
Maybe, but I think one of the points is that the marginal cost of both understanding that legacy code base and safely refactoring it are increasingly trending down thanks to agentic coding tools. It changed the value and risk tradeoff for legacy apps, if deployed properly. There's still a lot of work (too much) to get the harness in place to make high confidence changes to legacy, critical apps. If someone makes that more automated, we'll be in a very different place for legacy refactoring and it will look a lot more like the clay molding the article discusses.
As with anything LLM-related, I feel compelled to ask, is that actually what's happening, or are they just successfully convincing their users that's what's happening? I truly cannot tell.
I'm not using any LLMs directly (my workplace still bans them in-house) and my experience on the receiving end of contractors using them is quite poor. That includes one major, "we'll replace your ancient software with shiny new stuff"... with significantly reduced capability that in turn makes everything far more difficult than it was or ought to be. The UI appears much more user friendly, but really is just broken in multiple ways where the much-patched 1980s software it replaced was user-unfriendly but largely worked.
This all could be the result of poor coding, regardless of LLM use, of course.
I've been able to do relatively big refactors with great success, like porting thousands of lines of data transforms to drastically different data stores practically in one fell swoop. In the background. As I worked on other stuff.
The cost of experimenting is just mind mindbogglingly cheap now, it's really insane. Don't like the abstractions it comes up with, or think it generated a bunch of slop? Go again, who cares? With a little more steering, they'll often produce exactly what you want.
As for contracting firms, many of them were slop shops before AI, I imagine those kinds of firms are even worse slop shops now.
> I've been able to do relatively big refactors with great success, like porting thousands of lines of data transforms to drastically different data stores practically in one fell swoop. In the background. As I worked on other stuff.
This is a great use case, as you have ground truth to compare to. LLMs are phenomenal at this stuff. Where you don't have this is where they are less successful (in my experience).
With this new-found capability, you can use an LLM to plan and execute some long-needed refactors, or use it to pile on new features even faster with no regard for tech debt management.
As others have said... it's a tool. A powerful tool in the hands of a wise and skilled wielder who makes planned, focused changes, or a slop-cannon in the hands of someone who is happy to churn out features with minimal understanding of context or system design.
> The UI appears much more user friendly, but really is just broken in multiple ways where the much-patched 1980s software it replaced was user-unfriendly but largely worked.
LLMs don't magic away the need for careful and extensive testing. Good code still takes a lot of time. But it's also a lot less time than before.
I suspect a lot of problems come from people trying to one-shot entire apps, or from those who do not have the relevant experience or knowledge to understand that close-with-a-nice-modern-GUI is not nearly good enough.
We can fully solve 'code' in the sense we can model every single interaction and then use that specification to produce another program that does the exact same thing, and then based on inputs, it should be possible to cull that tree of possibilities even more.
That is my hope anyway, apart from that, I do think there is an inherent laziness in business to not mess with the machine that makes money.
Yes, well-designed code is malleable to an extent when coding by hand, but even then it's an order of magnitude more rigid than when working with agents (and real-world code often ossifies, as you pointed out). Malleability comes not only from the possibility of change but also from the speed.
> It's the data you generate with that code that's your asset. You can always rewrite the code.
I like that perspective, but "you can always rewrite the code" almost never happens in real life for complex projects, and when it does, it's a huge undertaking that takes many months or even years. Malleable code makes that much more feasible, I'd argue.
Rigid implies you are trying to change something into something else in a controlled way. Eg a refactoring that does nothing but enable for a future feature. Agents does not change code to refactor anything, they write code to solve the new feature directly. And if you are good at prompting they might overwrite code that exist so that the end result looks like a refactoring. But no clay was reshaped.
> Finally, there is the delight of working in such a tractable medium. The programmer, like the poet, works only slightly removed from pure thought-stuff. He builds his castles in the air, from air, creating by the exertion of the imagination. Few media of creation are so flexible, so easy to polish and rework, so readily capable of realizing grand conceptual structures.... https://home.adelphi.edu/sbloch/class/adages/joy.html
The point is that previously, changing code in a major way might take months of refactoring. Large changes were simply not contemplated unless they were justified by similarly large additional profit. Once you designed your architecture, you were pretty much stuck with it.
Now, the kinds of changes that were simply unrealistic before are now entirely realistic. A refactor/migration that would have taken 6 months before, you can now get a working version done in a day, and another few days of QA. That's what this post means -- code is no longer stone, it's clay. You can change it quickly in ways that were previous unimaginable.
This has nothing to do with the concept of code being liability or asset -- that's a totally separate conversation.
I was watching the most recent Rich Hickey talk[0] and at the start, he talks about correctness and the difference between the internal machinery of your software (which can be finely specified) and handling the external world (which will always be messy).
Good Architecture will try to isolate the two. You got the internal logic which is either the business domain abstracted away. And you got the highly volatile part (request from frontend, new integration, new drivers, deps update,....).
If you've done that, migration/refactoring, unless it entails some unlikely core changes, will not take that long. It's just a matter of dropping that part and replacing it (like changing a car's brake pads or steering wheel). But the actual core mechanism will hardly change over the years.
To go with the thread flow: It's a stone core wrapped by clay.
> The point is that previously, changing code in a major way might take months of refactoring.
> Now, the kinds of changes that were simply unrealistic before are now entirely realistic. A refactor/migration that would have taken 6 months before, you can now get a working version done in a day, and another few days of QA.
Significantly changing a system implementation is a function of understanding, not time.
Given a starting solution state being A and a desired functionality state of A', the tooling used to codify the A -> A` delta is largely irrelevant. Specifically, in order to successfully deliver major product realignment requires awareness of what exists currently and understanding of what needs to be.
Code is neither stone nor clay.
When making software, remember that it is a snapshot of
your understanding of the problem. It states to all,
including your future-self, your approach, clarity, and
appropriateness of the solution for the problem at hand.
Choose your statements wisely.
> Significantly changing a system implementation is a function of understanding, not time.
> Specifically, in order to successfully deliver major product realignment requires awareness of what exists currently and understanding of what needs to be.
And this is exactly what agentic coding brings to the table in spades.
Agentic coding does not create understanding in the people tasked with altering a product to provide significantly different functionality.
In order for agentic coding to be a net positive, the instructions given to the AI offering must be from people who understand what a system currently does as well as what functionality a product needs to provide in its future desired state.
Agentic coding does not solve these fundamental concerns.
I don't disagree with wanting people to understand the product they're altering.
But whether or not this is actually needed or not now, I'm not so sure. LLMs are very good at parsing a codebase, discovering what needs to be changed to provide different functionality, suggesting any architecture changes that would be needed to do so, and ultimately implementing those changes within the bounds of an existing test suite.
I sadly suspect that if it's a choice between throwing a person or an LLM on an existing large and complex codebase cold, it's now safer and faster to use an LLM in many instances. Much better still to have someone with knowledge and understanding of the codebase work with an LLM, of course. But we're getting to the point that you can do a lot with little to no human knowledge at all.
(LLMs are also very good at bringing you up to speed with a large and complex codebase. A model can absolutely help create understanding in the person overseeing these changes, provided that person deigns to ask for it.)
> I sadly suspect that if it's a choice between throwing a person or an LLM on an existing large and complex codebase cold ...
You're missing the point. Understanding has nothing to do with code.
"Code" is short for "encode", which is an industry term for "encoding a solution". This implies a solution has been formulated before it is expressed in a programming language.
There is no "codebase" without a person or people who understood what solution to reify in the first place.
> A model can absolutely help create understanding in the person overseeing these changes, provided that person deigns to ask for it.
A model can assist a person to gain understanding, sure, but like you said yourself:
... provided that person deigns to ask for it.
By this statement alone, you have proven my point of:
In order for agentic coding to be a net positive, the
instructions given to the AI offering must be from people
who understand what a system currently does as well as what
functionality a product needs to provide in its future
desired state.
It might depend on your use case. Life threatening bugs in a plane? Your argument holds up.
Letting an llm rewrite your internal todo tool, in another language, better design and up-to-date software stack. Yeah, this is absolutely not a fantasy anymore. We got rid of most SAAS tools in a month. Complete with Keycloak, behind wireguard, pocketbase backend, in our cooperate design with exactly the features we want. It works flawless since day one.
This is outdated news though. It's cope. People are out there telling themselves "well it's insecure". That was true. The AI models are better hackers then humans now though. Red teaming your own code with AI will produce a better penetration test then any developer trying to implement OIDC.
And frankly...have you tried configuring Keycloak? It is a gigantic "do everything app". The idea that it's going to have a narrower attack surface is basically fantasy.
I've been able to execute several highly niche, large scale refactors in a production system in the last 6 months, entirely enabled by AI tooling. The kinds of changes that individually by hand would have taken months and you would never get top down approval to do because it would take paid developer time away from client-focused work.
This has stabilised the system, fleshed out unfinished ideas, expanded testing capability, introduced new developer-experience oriented tools, and refactored sensitive systems to be more flexible for future use. Not to mention addressing the kinds of uber-niche tech debt that would take years to bite and months to fix.
Maybe for absolutely massive refactors? But if you've got a good test suite and a capable LLM, most refactors are ... almost enjoyable, now.
I think this is what TFA was getting at -- what was once hard or impossible, and an absolutely massive headache to conceptualise, is now surprisingly simple and straightforward.
Definitely fantasy esp "6 months to 1 day". That's just impossible physically.
Did they even sit and thought deeply before they wrote this comment or have people really just started putting out slop everywhere due too much usage of AI?
The code that was produced in 6 months before cant be even read in 1 day today so dont get me started on properly functionally producing it.
It's hard to say because no one actually describes what and how they are doing to get AI to successfully refactor or operate in large code bases.
My experience is, slop on slop. Frontier models still can't handle even modest sized refactors without explicit hand holding. I still don't trust models with production scale refactors.
Apparently, everyone has the magic sauce and I'm blind. Or our definition of quality and production grade is very different.
Some misc advice. Your first task with ai is to use it to build constraints and guard rails for the ai.
That probably means a test suite that is at least twice the size of your code base. If you started there, great, but increase it to integration and benchies if you’re mostly holding units. It actually helps a bit if you can use a different language for this too but it depends on project, ymmv.
After that you have to either let go of certain style/idiom things or enforce ruthlessly with deterministic hooks everywhere.. no middle ground there and prompts will never work.
You also need to deliberately channel chain of thought with workflows rather than hoping for the best.. most of the generated product here shouldn’t be committed or preserved at all.. non-public doc flows and ticketing systems help.
Like people, an ai can easily create code that it cant actually maintain. It’s a matter of discipline now, same as before. Always using the smartest model is wrong, but double wrong on “wide” changes like a big refactor.. it leaves you no good options if you get into trouble.
Is this always true? I'm honestly not sure. For unit tests I completely agree with you, for integration tests I'm not so sure—validating permutations does not necessarily couple you to code, and may in fact be good discipline for user expectations.
That is...not at all my experience of Opus 5.5, which has absolutely both spotted weird workarounds, then spotted the underlying bugs which were leading to the workaround, then spotted the race conditions which were masked by the workarounds.
This. Since forever was I told that the term "software" was coined because, contrary to hardware, it was easy to change, adapt, and mold into your needs.
I'm very surprised to hear people in this day and age claim it wasn't.
Working code that people pay to use is of course an asset. If it is a liability then just delete it all an have no source code an you just paid off a debt for free.
An expression that stuck with me from the Domain Driven Design book is "supple design". Achieving supple design (and thus supple code) is a goal, but it doesn't come for free - it requires a lot of work. I'm trying hard to get agents to create supple design - or at least not to make my own designs less supple - but it's not easy, because they have a tendency at overcomplicating and overengineering code.
> Code always was, it's supposed to be malleable. … You can always rewrite the code.
This isn’t capturing the spirit or the essence of the metaphor. chipping away at marble or whittling has this locality to it that’s keen but myopic. Molding with clay isn’t so detail oriented, you can literally close your eyes and focus on shape, same with turning on a lathe although I wouldn’t suggest closing your eyes.
there is such a thing as being precise without being detailed or local. Before LLMs you did this with test suites techniques maybe, and a few automated refactoring tools, CSTs and AST work, sometimes macros and other metaprogramming. Yeah it happened but fair to say it was rare and difficult. Everyone is/can be a sculptor now
It's not just about malleability. It's about specificity. A prototype has to specify certain details to run at all. This is not really true of sculpting in clay (former sculptor here). What the article describes of a sculptor working from big forms to smaller forms and so forth is in contrast to what it feels like to code by hand, which always requires some thought for the details even if the details are going to change dramatically as the program goes from prototype to hardened production software. The programmer always had to have their hands on the details even as they thought about architecture, but that's not the case now. Now we really can work from primary masses to increasingly specific details.
Fun facts, Abrahamic religions that are based on the Bible and Quran both claiming human are made from clay [1],[2].
In Hebrew name Adam, the very first human, comes from the word adamah, which means "ground," "soil," or "red clay".
In Arabic Adam, comes from the word adeem, means the surface of the earth or dust, reflecting the Islamic and Abrahamic tradition that Adam was created from the clay or dust of the ground.
By extension in Hebrew and Arabic the word Adam also means mankind and humanity.
Very cool, thanks for that. I was vaguely aware that clay metaphors were important in old religions, and I thought about looking into it and maybe finding a nice quote for the article, but didn't have the time. I accept suggestions though :)
In Chinese mythology, human beings were also created from clay. The goddess Nüwa first came to an empty river bank and spent much time carefully crafting a set of figures, then got tired, and rushed together a bunch of clay piles using a length of corded rope. The first group of clay figures were the nobility, while the latter were the commoners.
I look forward to the day when the broader industry realizes code was never a bottleneck, and you still have to answer to the market to make money.
This piece, while valid, puts way too much emphasis on code. I don’t want to dismiss the author, but they’ve yet to see how little of a shit the business gives about code. This has been perennial.
Some development houses have always done sketches, proof of concepts or prototypes. Not because code was expensive or inmalleable, but because they didn’t know what would be a success. Even if it did not take forever to build the thing. If I told you what the perfect product was and how to make a boatload of money, you’d be ready with an army of programmers. But life and business rarely work out that way.
So you've NEVER had a sketch, proof of concept or prototype end up being a part of the final product? Now you're stuck with a piece of crap that was implemented expecting to be thrown away, but then because of time and money constraints it's now a load-bearing (heh) part of the application.
It also takes more time for humans to build prototypes and PoCs than doing the same with an agent. Iteration speed and time-to-market matters more and more (case in point: mobile games).
That's a fascinating topic. I'm curious about how do you approach it... like can the user-facing AI change any part of the code? Or is it constrained to a set of predefined components/plugin layer/etc.?
So I have the app deployed to railway with a Postgres database. I give the customer an agent that has the railway skill and basically access to that customers project on railway and they can talk to the agent and it can communicate with app, change the code deploy it again, do migrations.
Agreed, clay/modeling it is a good analogy. I keep trying to describe the level I work at now (if only to myself) and all I could conjure was shaping the product at a higher level with less control overall (unless you want to drop down and do some "detail work") but the ability to make sweeping changes much easier.
I prefer the 'code is legos' metaphor. Well defined interfaces that hurt like hell if you step on them. You get a practically indestructible chunk that is simple by itself but can be composed to extreme complexity. Parts can be used in many different contexts and new parts are constructed when required. I think AI actually increases the need for this kind of construction.
I'm reminded of the software for the Gemini spacecraft. [0] Does it still exist? We don't have any assembly or machine code. But like today in the '60s the designers of the flight software, considered the assembly output to be an intermediate stage - a kind of temporary mapping from the real program. The real program was designed in "Math Flow" - a visual flowchart language for expressing logic. We still have the charts. Arguably the charts are the real software. The handwritten assembly translation a mere ephemeral shadow which could be reconstructed as-needed.
Funnily enough I recently found Claude Opus to be very capable of handling flowchart logic and a translation of the bitmap scans of the flowcharts describing the PDP-8/S processor, into Verilog, was a one-shot prompt.
Everyone is saying this about "the factory." I have seen some successful fix and migrate campaigns for well-defined, local transformations such as retroactive fixes for new lint rules, flaky tests, or library migrations. But so far the attempts to do nontrivial new functionality in this manner have made big messes that take more effort to review and correct than simply hand-feeding 1-3 vanilla Claude Code sessions with my full attention.
Code is more like a garden. You spend a lot of time just watching stuff grow, you don't know what you're going to get, sometimes you have to pull weeds, and you have to be mindful of the weather and soil conditions to ensure stuff grows optimally.
And it is still better to be a coder in a garden, than a gardener in CODE.
Code is clay now, agents have surpassed most human coders, arguably arriving at AGI. Yet the team at Hacker News STILL can't figure out how to make their forum software bump a post without these embarrassing fake time stamps.
I remember explaining software to someone, and I explained that it was like a sandpit, every day - it is cleared, you make shapes, lines, add rocks, toys - surely, at the end of the day, it gets cleared, and starts again new the next day.
What remains are the lessons we learnt, the sand is a medium through which we express ourselves.
To torture the analogy a bit: You didn't sculpt bridges out of clay - critical infrastructure was built from stone. Even if you wanted to use clay, you made bricks, and architected the structure from those units. You couldn't just throw a lump of clay across a stream and vibe-build a bridge...
If we want to use LLMs responsibly, to build substantial pieces of infrastructure, we should be using it to create discreet "bricks" of code, that can be tested, relied upon, and used to implement human-driven architectural decisions.
There's also another sticky, malleable substance that could work for this analogy...
But more seriously: the question, the same as before, is "what are you going to sculpt". Sculpting for the sake of sculpting achieves nothing, and if it's too cheap and too easy, it can cost you time and money than if you had to pause and think beforehand.
I implore you to look at the past several months of vibecoded games and Github projects submitted to HN. It's amazing that you can prototype something in hours. It's bleak when you realize that half of these projects weren't even working properly - we often upvote based on vibes too - and are now abandoned in a half-broken state because the author has no attachment to it whatsoever. It was just some money exchanged for internet points.
There's no doubt that we're going to have more software; I think it's very much an open question whether there's going to be more good software, or more software that can make money.
I agree. My hope is that this half-broken made-in-a-day vibecoded demos getting attention is just a phase. Those things look impressive because they would have been impressive 1-2 years ago, but when people's brains adjust to the new normal they won't be more interesting than the food you cooked for yourself yesterday or your creative writing class assignment.
178 comments
[ 1.3 ms ] story [ 16.7 ms ] threadI wrote this a couple of months ago, and everything moves so fast nowadays that the concept of factories is already being blurred as harnesses get better and require less tooling around them. I still think that the distinction between wanting to be in the loop vs automated out from it holds up, though.
There are other interesting aspects of malleable code that I don't explore in the article, for example:
- Ownership. People feel less attached to their code, which has both good and bad consequences (e.g. fewer ego battles but less accountability). - Malleable software that adapt to users. Huge topic, many interesting questions to explore. - Assets in code. Things like (some) 3D graphics and animations can now be done entirely in code. Before they were tedious to code and very difficult to tweak (malleability changes that).
Exactly. And the mold could be a spec, an MVP or even one of the implementations (e.g. the Swift one) acting as the source of truth for the other versions.
> "just" give them Claude and teach them to describe what they want and iterate to get something that maybe resembles an MVP but in more cases is just an interactive UI spec
That's a great example of what malleable code unlocks. You let the client to create the mold themselves, refine it and then use it to build it properly.
> When the mold is done, you let the agent pour in the code in any format you like. It can create a Swift version, Rust version and a web assembly version in "half a soda" as you put it =)
Unless you use code, that mold is at best a formless bag.
The reason people use software is because there's a need to manipulate some data/information, transfer it, and interact with it (input or output). All those actions needs to be done correctly, and if not possible the error should be reported. To get to that level of correctness, we need to be formal with how we express the process, which means essentially going from a non-zero amount of ambiguity (natural language) to zero (programming language).
Using AI to translate specs/prompt to code is just asking it to randomly resolve any ambiguity found in the specs. And as any experienced dev knows, some of those are just tradeoffs where there no right or wrong answers, just contextual ones that evolves over time and space.
> Before I had to dig specs of an application out of a client's mind and try to form them into software with a full-ass team. Now we can pretty much "just" give them Claude and teach them to describe what they want and iterate to get something that maybe resembles an MVP
I wonder if there's actually been conversation with the client before? Where you use some prototyping tools like RAD or Sketch to resolve UI issues, get in touch with the actual domain experts,... or was it just a telephone game full of politics?
That’s even more work than just writing the code, at least the latter is immediately useful. The reason we create complicated machinery is mostly because of industrial scale. Molds and factories help create thousand of pieces and the total value of the latter is way more than the cost of the former.
The reason we don’t write specs and other kind of docs extensively is usually that the time taken is way more than just writing the code. Yes, code do require formal thinking, and a training in syntax. But a lot of jobs require understanding some concepts and training in the jargon and techniques.
> No program will ever be perfect[0], but you need to get it good enough for the problem at hand.
The nicest thing about software is that some subproblems are nearly eternal. That’s why we reuse code and utilities. Also while some problems do evolve, it’s usually done slowly and in a way, predictably (as in how, not when). Taking care to solve it once well, usually is better, rather than solving it again and again.
It’s more important to worry about the solution to a specific problem (in terms of concept), than to worry about code. Coding was not, and will never be the primary problem. Any experienced developer knows this, which is why most will says they spend very little time thinking about code and writing it.
What are they paying you for if you’re just having your clients vibe code their own apps?
These are for highly specific stuff like a tool to help a copywriter work on game dialogue for example.
It's a fuckton faster for the actual expert in the field to do it than me first learning enough of their craft to know the terms and how they work to get there eventually.
The actual code that does anything meaningful is made by Actual Programmers. As well as everything beyond that, where it's run the CI pipelines, tests, infrastructure to run it etc.
It's like an architect asking a client to draw and describe their dream home and using it as a basis for the final product.
Otherwise, create a "mold" in AST in Lisp.
But it's just writing the hard limits on the outside, in code. Define that when A goes in B must come out. Enforce hard linting rules and other code-level checks on the output etc.
I think Lisp is an ideal language to use with an LLM, because it is essentially a notation for a logical assembly code, and I expect there to be compound benefits in using it with AI.
Lisp [...] made me aware that software could be close to executable mathematics.
— ACM Fellow Profile of L. Peter Deutsch.
APL is like a diamond. It has a beautiful crystal structure; all of its parts are related in a uniform and elegant way. But if you try to extend this structure in any way — even by adding another diamond — you get an ugly kludge. LISP, on the other hand, is like a ball of mud. You can add any amount of mud to it [...] and it still looks like a ball of mud!
— R1RS (1978) page 29, paraphrasing remarks attributed to Joel Moses.
Part of the beauty of the ball-of-mud quote is that there really does seem to be a causal connection between Lisp's use of generic, unencapsulated, largely un-type-checked data structures and its extensibility. The converse implication is that we should expect specialization, encapsulation, and aggressive type-checking of data structures — all strategies extensively pursued in various combinations in modern language paradigms — each to retard language extension.
Each of these three characteristics of Lisp serves to remove some kind of automated restriction on program form, leaving the programmer more responsible for judging what is appropriate — and thereby shifting things away from close conversation with the machine, enabling (though perhaps not actively encouraging) more human engagement. The downside of this is likely obvious to programming veterans: it leaves things more open to human fallibility. Lisp has a reputation as a language for good programmers. (As a remark attributed to Dino Dai Zovi puts it, "We all know that Lisp is the best language around, but in the hands of most it becomes like that scene in Fantasia when Mickey Mouse gets the wand.")
Lisp, Mud, and Wikis
https://fexpr.blogspot.com/2018/10/lisp-mud-and-wikis.html#s...
{LISP Is a Ball of Mud}
LISP is extensible in two ways. First, there is the simple ability to define new functions; these are used in a way that is both syntactically and semantically identical to built-in primitive functions like CAR. This is in contrast to “algebraic” programming languages, which either make an arbitrary syntactic distinction between addition, say, and a user function, or wander into the quagmire of extensible parsers. Second, there is a uniform macro facility for transforming one syntactic form into another; this facility is based on internal data structures rather than external character-string syntax.
The Revised Report on Scheme
https://research.scheme.org/lambda-papers/lambda-papers-revi...
https://wiki.c2.com/?HackerLanguage
Also:
Lisp is Clay: The Power of Composable DSLs (video)
https://archive.fosdem.org/2026/schedule/event/HDE7JZ-lisp-i...
Hacker Language
https://wiki.c2.com/?HackerLanguage
A language that allows one to easily customize syntax, flow control structures, etc. for the convenience of the author without regard to future readers. It allows one to create their own language or sub-language in their mind's own image without worrying about other readers' preferences or grokkability of the style. Contrast with a CorporateLanguage that assumes or targets masses of mediocre PlugCompatibleInterchangeableEngineers (programmers) where there may be many readers with varying skills. Such a language tends to hard-wire ways of things to reduce variation. One can say that a CorporateLanguage is for the herd of sheep while a HackerLanguage is for the lone wolf. ("Hacker" could be "hobbyist" or "tinkerer" also in this context. It's not meant to only include the devious version of "hacker".)
One can often achieve high personal productivity with a HackerLanguage, but readability may fit a very narrow audience or be questionable. Sometimes derogatorily called a WriteOnlyLanguage.
Malleable Systems Collective
https://news.ycombinator.com/item?id=50188437
We, in general, are just very bad at letting code ossify, or for this metaphor, dry out and crumble. AI does not solve this problem and I fully expect to see situations where AI generated code becomes so hard to work with that even LLMs prefer to throw it away and start fresh again.
It seems much more common for a developer to see some code, say it sucks, and rewrite it from scratch, rather than doing a little bit of modification to extend it, even if it was purpose built to be extended. The result being some code that does a small fraction of the original, but is "clean".
This used to be what being a dev was, if I recall. It's been a few years.
A great coder loves legacy old projects because theyre challenging, unpredictable, undocumented, and if you figure out, you are like a God.
Starting the perfect greenfield project and writing amazing code the first week is a skill every freshmen student at a CS college has. That's not a problem area, its a solved thing.
But do it for 10 years straight after 5 acquisitions, different infrastructure, different industry, language, culture? You are a RARE BREED.
Or even simpler put, never measure yourself with easy things, only with the hard ones since then the easy things are a joke.
Been there done that, the problem is you will not get rewarded by your superiors. Keeping old shit alive is useful to keep your skills sharp, but it's bad in a culture utterly dominated by "resume driven development".
Regarding the average developer as an imbecile was a cottage industry from Djikstra to FizzBuzz.
And non-slop parts were maybe some prominent open source projects.
Most bigtech company had an internal joke of "we couldn't ever open source X, not because it can't be done, but it would be too embarrassing"
Unless you worked at the shittiest company in the world, lets try to not bring others down just because they weren't as amazing as we are. They might have other skills weve lacked.
E.g. like a journalist complaining that they colleagues didn't publish books... who cares? Thats not their job, they need to write clear good concluded articles. If they write their articles like books, nobody reads that shit.
I'm not sure your experience is the norm.
LiveCoding in CommonLisp.
https://www.youtube.com/watch?v=xzTH_ZqaFKI
https://news.ycombinator.com/item?id=50205569
We tend to forget in tech-oriented forums that most of us are bound to those who pay our salaries, and for many developers that payment is to be focused on revenue-generating, or client-focused work.
Developing advanced comprehension and being able to use it for long-term system stability are unfortunately not always paired in the daily work.
Also comprehension is one side, its "Consuming" code, but it doesnt say anything about theyre talent of producing great code.
Now instead of aiming for robust, malleable code, people are throwing up their hands and saying. "It was always a mess, let's just keep throwing more tokens at it."
If a dev just followed public trends, then I guess I can see how they came to the conclusion that this is the best way out, because their baseline level of comprehension is so far in the floor. It's like circling around the entrance of a maze for days until finally an AI merchant shows up near the door, and they say "well clearly, the only way to get out of this maze is to pay the merchant for his fancy roomba to carry me out" instead of carefully mapping your way through.
From a selfish perspective, that's fine by me. I've built up skills that I don't think will be replaced in the near-term, and in that same period most people will end up de-skilling. The only downside is that I've had to shrink my circle that I collaborate with even further.
This is a one possible approach/explanation:
https://pragprog.com/titles/swdddf/domain-modeling-made-func...
The kind that works, but everyone who knows why has left the company. The whole codebase is written in a way that makes automated testing either impossible or so time-consuming that the client will never pay for the required refactoring.
There is way too much code in the world we never were able to rewrite due to real-world concerns. There were people who had the skill, but a part of that skill came with knowing the risks of doing major refactoring to a money-generating system that is ancient, but still works.
Anecdote: I had to work with a system where the original coder (long gone) had rewritten Linked Lists with their custom solution that worked normally except the first X items were the sum, average and mean of the data. Fun times.
I'm not using any LLMs directly (my workplace still bans them in-house) and my experience on the receiving end of contractors using them is quite poor. That includes one major, "we'll replace your ancient software with shiny new stuff"... with significantly reduced capability that in turn makes everything far more difficult than it was or ought to be. The UI appears much more user friendly, but really is just broken in multiple ways where the much-patched 1980s software it replaced was user-unfriendly but largely worked.
This all could be the result of poor coding, regardless of LLM use, of course.
The cost of experimenting is just mind mindbogglingly cheap now, it's really insane. Don't like the abstractions it comes up with, or think it generated a bunch of slop? Go again, who cares? With a little more steering, they'll often produce exactly what you want.
As for contracting firms, many of them were slop shops before AI, I imagine those kinds of firms are even worse slop shops now.
This is a great use case, as you have ground truth to compare to. LLMs are phenomenal at this stuff. Where you don't have this is where they are less successful (in my experience).
As others have said... it's a tool. A powerful tool in the hands of a wise and skilled wielder who makes planned, focused changes, or a slop-cannon in the hands of someone who is happy to churn out features with minimal understanding of context or system design.
LLMs don't magic away the need for careful and extensive testing. Good code still takes a lot of time. But it's also a lot less time than before.
I suspect a lot of problems come from people trying to one-shot entire apps, or from those who do not have the relevant experience or knowledge to understand that close-with-a-nice-modern-GUI is not nearly good enough.
That is my hope anyway, apart from that, I do think there is an inherent laziness in business to not mess with the machine that makes money.
Yes, well-designed code is malleable to an extent when coding by hand, but even then it's an order of magnitude more rigid than when working with agents (and real-world code often ossifies, as you pointed out). Malleability comes not only from the possibility of change but also from the speed.
> It's the data you generate with that code that's your asset. You can always rewrite the code.
I like that perspective, but "you can always rewrite the code" almost never happens in real life for complex projects, and when it does, it's a huge undertaking that takes many months or even years. Malleable code makes that much more feasible, I'd argue.
You know, I've never thought about that. It's really interesting to consider, especially since refactoring code is now cheaper than ever.
This is not the case as far as accounting and the law is concerned.
Dependency is a cause of ossification.
The point is that previously, changing code in a major way might take months of refactoring. Large changes were simply not contemplated unless they were justified by similarly large additional profit. Once you designed your architecture, you were pretty much stuck with it.
Now, the kinds of changes that were simply unrealistic before are now entirely realistic. A refactor/migration that would have taken 6 months before, you can now get a working version done in a day, and another few days of QA. That's what this post means -- code is no longer stone, it's clay. You can change it quickly in ways that were previous unimaginable.
This has nothing to do with the concept of code being liability or asset -- that's a totally separate conversation.
Good Architecture will try to isolate the two. You got the internal logic which is either the business domain abstracted away. And you got the highly volatile part (request from frontend, new integration, new drivers, deps update,....).
If you've done that, migration/refactoring, unless it entails some unlikely core changes, will not take that long. It's just a matter of dropping that part and replacing it (like changing a car's brake pads or steering wheel). But the actual core mechanism will hardly change over the years.
To go with the thread flow: It's a stone core wrapped by clay.
[0]: https://www.youtube.com/watch?v=P5eO7BNyJao
> Now, the kinds of changes that were simply unrealistic before are now entirely realistic. A refactor/migration that would have taken 6 months before, you can now get a working version done in a day, and another few days of QA.
Significantly changing a system implementation is a function of understanding, not time.
Given a starting solution state being A and a desired functionality state of A', the tooling used to codify the A -> A` delta is largely irrelevant. Specifically, in order to successfully deliver major product realignment requires awareness of what exists currently and understanding of what needs to be.
Code is neither stone nor clay.
> Specifically, in order to successfully deliver major product realignment requires awareness of what exists currently and understanding of what needs to be.
And this is exactly what agentic coding brings to the table in spades.
In order for agentic coding to be a net positive, the instructions given to the AI offering must be from people who understand what a system currently does as well as what functionality a product needs to provide in its future desired state.
Agentic coding does not solve these fundamental concerns.
But whether or not this is actually needed or not now, I'm not so sure. LLMs are very good at parsing a codebase, discovering what needs to be changed to provide different functionality, suggesting any architecture changes that would be needed to do so, and ultimately implementing those changes within the bounds of an existing test suite.
I sadly suspect that if it's a choice between throwing a person or an LLM on an existing large and complex codebase cold, it's now safer and faster to use an LLM in many instances. Much better still to have someone with knowledge and understanding of the codebase work with an LLM, of course. But we're getting to the point that you can do a lot with little to no human knowledge at all.
(LLMs are also very good at bringing you up to speed with a large and complex codebase. A model can absolutely help create understanding in the person overseeing these changes, provided that person deigns to ask for it.)
You're missing the point. Understanding has nothing to do with code.
"Code" is short for "encode", which is an industry term for "encoding a solution". This implies a solution has been formulated before it is expressed in a programming language.
There is no "codebase" without a person or people who understood what solution to reify in the first place.
> A model can absolutely help create understanding in the person overseeing these changes, provided that person deigns to ask for it.
A model can assist a person to gain understanding, sure, but like you said yourself:
... provided that person deigns to ask for it.
By this statement alone, you have proven my point of:
The reason code takes time to change is not because changing it takes time.
You have to redo all the testing and relearn all the hard fought and underspecified lessons of the previous attempt. That's what takes the time.
Letting an llm rewrite your internal todo tool, in another language, better design and up-to-date software stack. Yeah, this is absolutely not a fantasy anymore. We got rid of most SAAS tools in a month. Complete with Keycloak, behind wireguard, pocketbase backend, in our cooperate design with exactly the features we want. It works flawless since day one.
If you did, please do an urgent meeting with your team and dont tell anybody, just fix it. When shit hits the fan, it really hits hard.
And frankly...have you tried configuring Keycloak? It is a gigantic "do everything app". The idea that it's going to have a narrower attack surface is basically fantasy.
I also wrote about internal tools. Not public facing applications. That would be a bit much for my taste.
This has stabilised the system, fleshed out unfinished ideas, expanded testing capability, introduced new developer-experience oriented tools, and refactored sensitive systems to be more flexible for future use. Not to mention addressing the kinds of uber-niche tech debt that would take years to bite and months to fix.
It's far from fantasy.
I think this is what TFA was getting at -- what was once hard or impossible, and an absolutely massive headache to conceptualise, is now surprisingly simple and straightforward.
Did they even sit and thought deeply before they wrote this comment or have people really just started putting out slop everywhere due too much usage of AI?
The code that was produced in 6 months before cant be even read in 1 day today so dont get me started on properly functionally producing it.
Yes, they really have been. It’s exhausting at work.
That's what truly convinced me programming was over: it writes better tests, more thoroughly, then any developer.
Can you help me understand what domain and language(s) you are using here?
This really does not match my experience so I'd love to understand what the differences may be.
Was there an existing good test suite? Is this an application built before LLMs?
I'd love to get more info so I can figure out how to get Opus to do this for myself, as I really haven't had this experience.
AI absolutely solves that problem. Just about every prompt "fixes" the dried out pieces of the code. And it's only getting better at that every month.
Sometimes I feel like people are experiencing AI so differently that it makes talking about it nearly impossible.
It's hard to say because no one actually describes what and how they are doing to get AI to successfully refactor or operate in large code bases.
My experience is, slop on slop. Frontier models still can't handle even modest sized refactors without explicit hand holding. I still don't trust models with production scale refactors.
Apparently, everyone has the magic sauce and I'm blind. Or our definition of quality and production grade is very different.
Please enlighten me.
That probably means a test suite that is at least twice the size of your code base. If you started there, great, but increase it to integration and benchies if you’re mostly holding units. It actually helps a bit if you can use a different language for this too but it depends on project, ymmv.
After that you have to either let go of certain style/idiom things or enforce ruthlessly with deterministic hooks everywhere.. no middle ground there and prompts will never work.
You also need to deliberately channel chain of thought with workflows rather than hoping for the best.. most of the generated product here shouldn’t be committed or preserved at all.. non-public doc flows and ticketing systems help.
Like people, an ai can easily create code that it cant actually maintain. It’s a matter of discipline now, same as before. Always using the smartest model is wrong, but double wrong on “wide” changes like a big refactor.. it leaves you no good options if you get into trouble.
Not sure what kind of data this refers to?
This. Since forever was I told that the term "software" was coined because, contrary to hardware, it was easy to change, adapt, and mold into your needs.
I'm very surprised to hear people in this day and age claim it wasn't.
This isn’t capturing the spirit or the essence of the metaphor. chipping away at marble or whittling has this locality to it that’s keen but myopic. Molding with clay isn’t so detail oriented, you can literally close your eyes and focus on shape, same with turning on a lathe although I wouldn’t suggest closing your eyes.
there is such a thing as being precise without being detailed or local. Before LLMs you did this with test suites techniques maybe, and a few automated refactoring tools, CSTs and AST work, sometimes macros and other metaprogramming. Yeah it happened but fair to say it was rare and difficult. Everyone is/can be a sculptor now
Akshually, you can never rewrite your code.
Fun facts, Abrahamic religions that are based on the Bible and Quran both claiming human are made from clay [1],[2].
In Hebrew name Adam, the very first human, comes from the word adamah, which means "ground," "soil," or "red clay".
In Arabic Adam, comes from the word adeem, means the surface of the earth or dust, reflecting the Islamic and Abrahamic tradition that Adam was created from the clay or dust of the ground.
By extension in Hebrew and Arabic the word Adam also means mankind and humanity.
[1] Genesis 2:7:
https://www.biblegateway.com/passage/?search=Genesis%202%3A7...
[2] Quran 7:12:
https://quran.com/al-araf/12
https://en.wikipedia.org/wiki/Creation_of_life_from_clay
This piece, while valid, puts way too much emphasis on code. I don’t want to dismiss the author, but they’ve yet to see how little of a shit the business gives about code. This has been perennial.
Some development houses have always done sketches, proof of concepts or prototypes. Not because code was expensive or inmalleable, but because they didn’t know what would be a success. Even if it did not take forever to build the thing. If I told you what the perfect product was and how to make a boatload of money, you’d be ready with an army of programmers. But life and business rarely work out that way.
It also takes more time for humans to build prototypes and PoCs than doing the same with an agent. Iteration speed and time-to-market matters more and more (case in point: mobile games).
Very true.
- only thing I use AI for is to review it
It's literally the Disney Fantasia scene of the Sorcerer's Apprentice: https://www.youtube.com/watch?v=m-W8vUXRfxU
Funnily enough I recently found Claude Opus to be very capable of handling flowchart logic and a translation of the bitmap scans of the flowcharts describing the PDP-8/S processor, into Verilog, was a one-shot prompt.
[0] https://www.ibiblio.org/apollo/Gemini.html#Evolution_of_the_...
In what world this was ever true ? a software or a lib is pretty much never finished
And it is still better to be a coder in a garden, than a gardener in CODE.
What remains are the lessons we learnt, the sand is a medium through which we express ourselves.
If we want to use LLMs responsibly, to build substantial pieces of infrastructure, we should be using it to create discreet "bricks" of code, that can be tested, relied upon, and used to implement human-driven architectural decisions.
But more seriously: the question, the same as before, is "what are you going to sculpt". Sculpting for the sake of sculpting achieves nothing, and if it's too cheap and too easy, it can cost you time and money than if you had to pause and think beforehand.
I implore you to look at the past several months of vibecoded games and Github projects submitted to HN. It's amazing that you can prototype something in hours. It's bleak when you realize that half of these projects weren't even working properly - we often upvote based on vibes too - and are now abandoned in a half-broken state because the author has no attachment to it whatsoever. It was just some money exchanged for internet points.
There's no doubt that we're going to have more software; I think it's very much an open question whether there's going to be more good software, or more software that can make money.