DEV Community

Cover image for The Spec Is the Fast Path
Efe Genç
Efe Genç

Posted on Originally published at efe-genc-portfolio.vercel.app

The Spec Is the Fast Path

The standard objection to writing the design down is that it is what you give up in exchange for speed. Early-stage companies are meant to be the place where you skip it. No specifications, no plans, build the thing and find out. Documentation gets treated as a tax that mature organisations can afford and small ones cannot.

I have worked the other way round for a while now, and I want to make the argument properly instead of just asserting it.

At Cendra, across a twelve-month tenure as one of two founding engineers, the work produced 255 design specifications, 207 implementation plans and 17 production runbooks. Over the same period there were 377 production releases coordinated across four repositories, and 482 merge commits across those repositories (an all-merges count, broader than the frontend-only first-parent integration figure on the Cendra page), spread over 239 active development days. The release figure works out at roughly one every twenty-two hours.

All of those figures are tenure-scoped and self-measured against private repositories while I held authorised access to them, a caveat I will come back to. The shape is what I care about here. The documents and the shipping happened together, at the same time, by the same person.

What I am not claiming

I cannot prove the specifications caused the cadence. There is no control group. It is entirely possible to imagine a version of that year with no documents and more releases, and I have no way to rule it out.

What I can do is describe precisely what the documents removed from the critical path, and let you judge whether that is worth the hours. The mechanism matters more than the correlation to me, because the mechanism is the part that transfers to your codebase.

The specification is a comprehension test I administer to myself

People assume I write a design down before building it in order to communicate it. Communication is a side effect. Writing it is how I find out whether I actually understand the problem.

There is a specific and reliable experience involved. Somewhere in the second half of a document, I reach a paragraph I cannot write. The words are not the difficulty. The thing I am trying to describe does not resolve. What happens when both of those conditions are true at once? Which side owns this state? What does the system do when the third case arrives, the one I have been mentally filing as "unlikely"?

That paragraph is the design flaw, and it has surfaced while it costs a paragraph. The same flaw would surface on its own eventually, after the schema is written, after two features depend on the shape, after something is in production carrying data. The distance between those two moments is most of what people mean when they say a piece of work took longer than expected.

So the cheapest place for a design to be wrong is in a document, and the second cheapest place is nowhere near as cheap. Everything below is bookkeeping on top of that one observation.

Three artefacts because they answer three different questions

The counts differ (255, 207, 17) because the three documents do different work and are needed at different rates.

A specification says what a thing should do and why, including what it deliberately will not do. That last part earns its place more often than the rest. A written non-goal is the only defence I have found against a feature that grows a third of the way through implementation. "We said explicitly that this was out of scope" is a settled question. "I don't think we should do that" is a conversation.

An implementation plan says in what order, what can break, and what has to land before what. It exists because a design being correct says nothing about a sequence being safe.

A runbook says how the thing reaches production and how it comes back out. There are only seventeen because a runbook describes a recurring operation rather than a change: staged rollout, feature-flagged release, a forty-eight-hour post-merge soak, rollback procedures, cross-repository dependency ordering, smoke matrices, incident response and on-call handover.

The runbooks were the ones I nearly did not write. They turned out to have the clearest payback.

The runbook exists because of a single point of failure that looked like competence

Releases spanned four repositories with real ordering constraints. Backend routes had to land before the frontend that called them. A web deployment and a mobile over-the-air bundle had to activate together, or a native shell would spend an afternoon calling an endpoint that did not exist yet.

That ordering lived in my head, and I was good at it, which was the problem. An engineer who reliably gets a complex sequence right looks the same as a documented process right up until the day they are ill or gone. I had been treating "I know the release order" as a strength. It was a single point of failure that felt like one, and the fact that it felt good is what stopped me fixing it sooner.

Writing it down was the fix. It also made the sequence reviewable, a second-order benefit I did not anticipate. An ordering constraint you can read is one somebody else can find a hole in.

Where the speed actually comes from

Nobody's bottleneck is typing. The expensive things in shipping software are rework and coordination, and specifications attack both.

Rework, because a design flaw found in a document is fixed by editing the document. Coordination, because a written interface is how two people build against each other without a meeting. That second one was concrete for me. Our AI engineer owned the LangGraph services, the agent workflows and the RAG pipelines. I built the product layer those capabilities were surfaced through (agent configuration, the knowledge base, the agentic rule-authoring interface, the in-product assistant) plus the transport between them. I did not architect the orchestration underneath, and the boundary between us is exactly where a specification pays for itself. Two people can build towards a written interface at the same time. They cannot build towards a remembered one.

The third piece is a completion standard rather than a document. Nothing counted as done until I had watched it behave correctly in production logs, in the database, or on a real device. I adopted that after being wrong often enough to stop trusting a passing build. The clearest illustration I have is a mobile feature that passed everything and still had to be removed after I reproduced its behaviour on a physical handset. Specify, implement, then verify in production. That last step is where the specification either turns out to have been true or does not.

What the artefacts turned out to be good for that I did not intend

They are the only part of that work I can still point at. Every repository I have shipped production code into belongs to somebody else, so demonstrating ownership becomes a problem of publishing a method rather than an artefact. Commit shares and blame analysis are self-measured; you are taking my word for the numbers and judging the method. Process artefacts sit differently. They existed in the repositories independently of my description of them, and two co-founders who were there have agreed to act as references and can confirm scope and ownership without me in the room.

I did not write 255 documents in order to have evidence. But a habit that produces its own record turns out to be worth more than a habit that produces only working software, once the working software is behind an NDA.

The same discipline runs in my own projects, at a scale suited to them. The autonomous documentary pipeline carries 25 design specifications committed alongside the code, including a build-versus-buy roadmap with licence analysis per component.

Where I would not write one, and what the counts do not tell you

A specification for a change whose blast radius is smaller than the document is ceremony, and ceremony is what gives specifications their bad reputation. My rule of thumb is to write one when the decision is expensive to reverse, when it crosses a boundary someone else builds against, or when the state it introduces will outlive my memory of why. A copy change or a dependency bump meets none of those. Neither does a contained bug fix.

The counts are counts of artefacts, not of quality. 255 documents is not 255 good documents, and I would rather say so than present a number as evidence of uniform rigour. The only claim a count of this kind can support is that the habit was consistent. The order is not always clean either. Sometimes the honest way to understand a problem is to build a throwaway first and write down what I learned afterwards, and a document produced that way is still worth having even though it arrived out of sequence.

There is one more thing this discipline carries. LLM coding tools are central to how I work, and the specification is what makes that safe rather than fast and hopeful. It is the artefact a tool's output can be checked against, something outside my own memory of what I asked for. Working this way is what lets one engineer cover a large surface, and the specs, the tests and the production verification are the reason it holds.


Ownership evidence and how each figure was measured: Cendra.


This essay first appeared on my site, efe-genc-portfolio.vercel.app, where the rest of the series lives. If you have run a small team with a different ratio of writing to shipping, say so. Disagreement is the most useful comment I can get.

Top comments (0)