DEV Community

Cover image for Spec-Driven Development: What Is a Spec Made Of? (Part 2 of 4)
Dirk Mattig
Dirk Mattig

Posted on AI-assisted

Spec-Driven Development: What Is a Spec Made Of? (Part 2 of 4)

In part 1, I collected the most relevant statements about the nature of a spec from the existing SDD definitions and distilled them into five key properties:

  • A spec is written in natural language.
  • A spec defines testable behavior; it is about the "what", not the "how", not the "why".
  • A spec is executable in the sense that an AI coding agent is able to translate it to source code such that the execution of the resulting binary exhibits the specified behavior.
  • A spec prescribes; it does not describe.
  • A spec is long-lived.

In this second part, I will take a closer look at what a spec is made of: its format and its language.

Format

A spec is text-based. Given the above list of key properties, this fact comes as no surprise to anyone. And while it is of course an important formal distinction from images, videos, and audio, it is also not very interesting. So let's quickly formalize this statement (we are engineers, right?) and move on.

A spec is one or more non-empty sequences of Unicode code points, each encoded as binary data using a Unicode character encoding.

Language

A spec is written in natural language and is executable in the sense defined above. This combination marks a radical shift away from practically everything we have ever had in software engineering before. Anything executable had to be written in a programming language. The use of natural language was strictly limited to comments and documentation.

Now that this has changed, I find it somewhat surprising that existing definitions usually end here and do not go into further detail about language usage in specifications. More than one legitimate question immediately comes to mind, so a closer look is warranted.

First of all, the distinction between a natural language and a formal language (and hence practically all programming languages) is at the same time the most radical and the most generic. Everything that counts as natural language is allowed? Absolutely no formal language is allowed? I think what is at play here are implicit assumptions about the nature of technical specifications, so they need to be made explicit.

Wikipedia defines prose as "language that is natural or normal in structure: following the spontaneous flow of conversational speech, without any perfectly regular rhythm [...]" and notes that it "is divided into two main divisions": fiction and nonfiction.

A spec clearly belongs to the second.

A spec is primarily written in nonfiction prose. It is allowed to contain technical syntax (URIs, for example) or formal language (Markdown, DSLs, or pseudocode, for example) as long as this plays a subordinate role and does not call into question the prose nature of the spec.

This definition immediately raises the next question.

Is prose now a programming language?

While it might feel like the answer is "yes", it is not. Prose is natural language, which explicitly excludes all formal languages and with that practically all programming languages. So a spec is executable without being written in a programming language. And while this makes no practical difference in day-to-day project work, it is unfortunate and even feels a bit like a contradiction.

Or could it be that this "contradiction" is a subtle hint that something is missing (a bit like a singularity in physics points to an incomplete theory)?

One question that every author of a spec must have faced at some point is not addressed by any of the SDD definitions I have seen so far: how exactly are we supposed to use nonfiction prose to write a spec? A mainstream programming language answers such questions with ease. It comes with a language specification that has a formal grammar at its core, supplemented by all sorts of conventions, guidelines, and best practices (coding standards and pattern libraries, for example).

And for specs? "American English, please" alone might not even remotely cut it.

I think this is a call to start thinking about language definitions for specs. Since the term specification language already exists and its definition is somewhat too narrow for our purposes, I suggest simply calling these spec languages.

Spec languages

Conceptually, spec languages must bridge the gap between natural and formal languages, and a sweet spot between the two already seems to exist.

According to Wikipedia, a subcategory of formal language is computer language, which in turn contains (among many others) the subcategories modeling language for designing systems and specification language for system behavior.

At the same time, "formal languages are used [...] as the basis for defining the grammars of [...] controlled natural languages," and "controlled natural languages (CNLs) are subsets of natural languages that are constructed by restricting the grammar and vocabulary in order to reduce or eliminate ambiguity and complexity. Traditionally, controlled languages fall into two major types: those that improve readability for human readers (e.g. non-native speakers), and those that enable reliable automatic semantic analysis of the language."

Bingo! This is exactly what we will need.

With this in place, it also makes sense to add spec languages to the existing stack of executable computer languages. This SDD definition already calls natural language the fifth generation; I would narrow that to spec languages. The label itself is older, though: in the 1980s, "fifth-generation" referred to logic-based languages such as Prolog. The resulting stack looks like this:

Generation Languages Examples
First Machine Bits and bytes
Second Assembly Symbolic mnemonics
Third High-level C, Java, Python
Fourth Declarative SQL
Fifth Prescriptive Spec languages

This is where the contradiction dissolves. It only existed as long as natural and formal languages were considered mutually exclusive. A spec language is both: a controlled natural language whose grammar is defined by a formal language. Executability was never reserved for programming languages; it extends to other computer languages as well, and spec languages are simply the newest generation in this stack.

Specify, my attempt at American English coding standards, could serve as a good starting point for a spec language, and I intend to develop it further as part of my own work in this area.

In part 3, I will look at what a spec actually says, how long it lives, and what it means for a spec to drive development.

Top comments (0)