Skip to content
October 23, 2026 Practical guides on software, AI and security

Search Shartech Blogs

Software Development

“A Sufficiently Detailed Spec Is Code”: What the Debate Means for AI-Assisted Development

Table of Contents

“A sufficiently detailed spec is code” is one of those lines programmers have repeated for years, usually as a joke at the expense of anyone who thinks they can skip programming by writing a better requirements document. In March 2026 it became the title of an essay by Gabriella Gonzalez on her blog Haskell for all, and it set off one of the more useful debates about AI coding tools this year.

The argument matters because a lot of current advice about AI coding goes like this: stop writing code, write a detailed spec instead, and let an agent do the rest. Gonzalez’s essay is a direct challenge to that idea. A response from Hillel Wayne, who writes and teaches about formal methods, then added an important correction. Read together, they give a clearer picture of where specs actually help and where they don’t.

What the phrase really means

The saying isn’t a prediction that specs will replace code. It’s a warning. If you keep adding detail to a specification until it pins down exactly what the software must do in every case, including edge cases, error handling, data formats and timing, you end up writing something as precise, and as long, as the program itself. At that point you’ve written code, just in a worse language.

That’s the point Gonzalez makes. It’s the opposite of the “the spec is the new code, so programming is over” reading that sometimes gets attached to the phrase.

Gonzalez’s argument: two misconceptions

The essay targets two assumptions behind spec-driven agentic coding.

Misconception 1: specs are simpler than code

The pitch for spec-driven development is that a spec is easier to write and review than code. Gonzalez argues that once a spec is precise enough for an agent to generate a reliable implementation, it has usually been contorted into code anyway: pseudocode, schemas, reference algorithms and step-by-step instructions written in prose. She draws on Edsger Dijkstra’s old point that precise, formal notation exists because natural language is too ambiguous for this kind of work. You can’t escape the narrow interface that engineering requires. You can only move it.

Her main example is OpenAI’s Symphony project, which was presented as software generated from a specification. Looking at its SPEC.md, she found database schemas written out in prose, pseudocode sections, explicit reference algorithms and “cheat sheets” apparently there to steer the model. In other words, much of the spec was already code, just not in a compilable form.

Misconception 2: spec work is naturally more thoughtful

The second assumption is that writing a spec forces careful thinking in a way coding doesn’t. Gonzalez’s response is that this depends entirely on why you’re writing the spec. If the goal is to ship faster, the same pressure that produces rushed code produces rushed specs, and now those specs are often generated by AI too. A vague spec doesn’t get clearer because an agent reads it. Garbage in, garbage out still applies.

She also reports trying it herself: asking Claude to implement Symphony from the spec in Haskell. The result needed several bug fixes and, on her test tasks, the agent eventually stalled without making progress. That’s one experiment, not a benchmark, but it’s a useful reality check on the claim that a good spec is all you need.

Her conclusion is measured. Specs are valuable for thinking through a problem. They’re not a reliable shortcut: if you’re optimising purely for delivery time, she argues, you’re often better off writing the code directly.

Wayne’s correction: a spec describes a set of programs

Hillel Wayne’s reply, “A sufficiently comprehensive spec is not (necessarily) code”, agrees with much of the practical conclusion but disputes the framing. His key point is that a specification and an implementation are different kinds of thing:

  • Code is one specific implementation.
  • A spec describes a set of acceptable implementations.

A good spec doesn’t need to narrow that set down to a single program. It needs to be sufficient: any reasonable implementation that meets it should satisfy the person who wrote it. More detailed specs refine vaguer ones by ruling out more implementations, but they don’t have to go all the way to code to be useful.

His example is a miles-to-kilometres converter. “Build me a converter” leaves open the language, interface, rounding and precision. Each added requirement narrows the options. At some point you’ve said everything you care about, and whatever is left over genuinely doesn’t matter to you. That’s a sufficient spec, and it’s much shorter than the code.

Wayne also points out that formal specs written in languages like TLA+, and test suites written in programming languages, are still specs. They describe properties the software must have, not the software itself. And he notes that even if code generation from specs became fully automatic, someone would still need the skills to write those specs precisely, and that has historically been a programmer’s job.

So who’s right?

Both, about different things. Gonzalez is right about the practice she’s criticising: specs written so an agent can produce a specific implementation tend to turn into code-shaped prose, and they don’t save as much effort as advertised. Wayne is right about the concept: a spec that captures only the properties you actually care about is a different, and often more valuable, artefact than code.

The useful question isn’t “should I write specs or code?” It’s “what am I trying to pin down, and what’s the best notation for it?”

What this means if you use AI coding tools

If you work with tools like Claude Code, Cursor or GitHub Copilot, a few practical lessons fall out of this debate:

  1. Specify behaviour, not steps. Tell the agent what must be true: inputs, outputs, constraints, error cases. If you find yourself writing pseudocode, consider writing the actual code for that part instead.
  2. Use executable specs where you can. Tests are the most practical form of specification most teams have. A failing test is a precise, checkable statement of what you want, and agents work much better when they can run it.
  3. Keep specs short and layered. Following Wayne’s idea of refinement, start with the few properties that really matter, then add detail only where the agent’s output shows ambiguity.
  4. Review the output as code. A spec doesn’t transfer responsibility. Whatever the agent writes still has to be read, tested and understood by someone.
  5. Don’t use specs to avoid thinking. The value of a spec is in the thinking it forces. A long, AI-generated spec that nobody has thought hard about is worse than no spec.

Where formal specs still shine

None of this is an argument against specifications in general. For concurrent systems, distributed protocols and anything safety-critical, formal specification languages like TLA+ let engineers check designs for problems like race conditions and deadlocks before writing implementation code. That’s exactly Wayne’s point: the spec describes properties at a higher level than any one implementation, and that’s what makes it worth having.

The mistake is treating “write a spec” as a way to skip the hard part. The hard part of software has always been deciding precisely what should happen. Whether you express that in English, a test suite, TLA+ or Python, someone still has to do it.

Related reading

Sources: Gabriella Gonzalez, “A sufficiently detailed spec is code”, Hillel Wayne, “A sufficiently comprehensive spec is not (necessarily) code”, TLA+ home page.

Did you find this article helpful?

Written by

Malik Shamir

Malik Shamir is the founder and lead tech writer at SharTech, a modern technology platform focused on artificial intelligence, software development, cloud computing, cybersecurity, and emerging digital trends. With hands-on experience in full-stack development and AI systems, Shamir creates clear, practical, and research-based content that helps readers understand complex technologies in simple terms. His mission is to make advanced tech knowledge accessible, reliable, and useful for developers, entrepreneurs, and digital learners worldwide.

54 Articles Website
Previous Article Android's "Advanced Flow" for Sideloading: The 24-Hour Wait Explained Next Article The Future of Version Control: Git 3.0, Jujutsu and What's Actually Changing

Leave a Comment

Your email address will not be published. Required fields are marked *

Stay Updated with Shartech

Get smart tech insights, tutorials, and the latest in AI & programming directly in your inbox. No spam, ever.

We respect your privacy. Unsubscribe at any time.