Why Your Next Codebase Should Be a Markdown File
Programming has climbed from punch cards to assembly to TypeScript. The next rung is annotated prose—a spec that compiles into full-stack apps.
At a Glance
- The pattern: Every 10-20 years, programming moves up one level of abstraction—punch cards → assembly → C → Python/TypeScript.
- The driver: Each new layer lets you express more intent in fewer symbols, trading manual control for higher-level reasoning.
- The next step: Annotated prose. A markdown document with embedded precision (types, schemas, edge cases) that compiles into a full-stack application.
- Who’s doing it: Remy compiles MSFM (MindStudio-Flavored Markdown) into TypeScript backends, React frontends, SQL databases, auth, and deployment.
- Why it matters: The spec becomes the source of truth. Code is a derived artifact. When models improve, you recompile—you don’t rewrite.
- The shift: Non-engineers can describe applications. Engineers can work at the architecture layer. The compiler handles the rest.
Programming didn’t start with TypeScript. It started with punch cards—physical pieces of cardboard fed into room-sized machines. Then assembly language gave us mnemonics instead of binary opcodes. Then C gave us functions and types. Then Python and JavaScript gave us garbage collection and async/await. Each step traded manual control for expressive power. Each step let you say more with less.
The next step is already here. It’s annotated prose.
What Is the Abstraction Ladder?
The abstraction ladder is the history of programming told as a climb. Each rung represents a new source language—a new way to express what you want the computer to do. The lower rungs are closer to the machine. The higher rungs are closer to human intent.
Punch cards (1950s): You physically encoded instructions on cardboard. One card per line of code. Drop the deck and your program is scrambled.
Assembly language (1950s-60s): Mnemonics replaced binary opcodes. MOV instead of 10110000. Still one instruction per line, but at least you could read it.
C (1970s): Functions, types, pointers. You could express algorithms without thinking about registers. The compiler handled the translation to assembly.
Python, JavaScript, Ruby (1990s-2000s): Garbage collection, dynamic typing, first-class functions. You stopped managing memory by hand. The runtime handled it.
TypeScript, Rust, Go (2010s): Type safety without sacrificing expressiveness. The compiler caught entire classes of bugs before runtime.
Each transition followed the same pattern: the new layer absorbed complexity the old layer made you handle manually. C absorbed register allocation. Python absorbed memory management. TypeScript absorbed runtime type errors.
The question isn’t whether there’s a next rung. The question is what it looks like.
Why Annotated Prose Is the Next Rung
The next rung is a spec that compiles into an application.
Not a design doc that a human reads and then implements. Not a prompt that an AI interprets and generates code from once. A structured document—readable as prose, precise as code—that is the source of truth for the application. The code is compiled output.
This is annotated prose. It looks like markdown. It reads like a product spec. But it has embedded annotations that carry precision: data types, validation rules, edge cases, interface contracts. A human can read the whole thing in ten minutes. A compiler can turn it into a working application.
Here’s why this is the natural next step:
1. It separates intent from implementation
C separated algorithms from assembly. Python separated logic from memory management. Annotated prose separates what the application does from how the code implements it.
You describe the application: “Users can create projects. Each project has a name, a list of tasks, and an owner. Only the owner can delete the project.” The compiler generates the database schema, the API methods, the auth checks, the frontend forms.
When you need to change the rule—“actually, admins can also delete projects”—you update the spec. The compiler regenerates the code. You don’t hunt through controllers and middleware and UI components.
2. It makes the source of truth readable by non-engineers
TypeScript is precise, but a PM can’t read a codebase and understand the product. A markdown spec with annotations is different. The prose layer is the product description. The annotations are the precision. Both are in the same document.
This isn’t “documentation that stays in sync with the code.” The spec is the code. There’s nothing to drift out of sync with.
3. It lets better models improve your application automatically
When you write TypeScript, you’re locked to that TypeScript. If a better compiler comes out, you still have the same code.
Seven tools to build an app. Or just Remy.
Editor, preview, AI agents, deploy — all in one tab. Nothing to install.
When the source of truth is a spec, better models produce better compiled output. You recompile the same spec with a smarter compiler and get faster code, better error handling, cleaner architecture—without rewriting anything. This is similar to how GPT-5.5 vs Claude Opus 4.7 real-world coding performance shows different model capabilities—but instead of generating new code each time, you’re recompiling the same source of truth.
4. It compresses the iteration loop
Changing a TypeScript application means editing files, running tests, deploying, monitoring for regressions. Changing a spec means editing one document and recompiling. The distance between “I want to change this” and “the change is live” collapses.
This is what every abstraction ladder climb has done. C made it faster to express algorithms than assembly. Python made it faster to prototype than C. Annotated prose makes it faster to define applications than TypeScript.
How Does Annotated Prose Actually Work?
The cleanest example is MSFM (MindStudio-Flavored Markdown), the format Remy compiles.
An MSFM spec is a markdown document. The prose describes what the application does. The annotations—embedded in the markdown as structured blocks—carry the precision the compiler needs.
Here’s a fragment:
# Task Manager
Users can create projects and add tasks to them. Each task has a title, a status (todo, in progress, done), and an optional due date.
## Data Model
```table:projects
id: uuid (primary key)
name: string
owner_id: uuid (references users.id)
created_at: timestamp
id: uuid (primary key)
project_id: uuid (references projects.id)
title: string
status: enum(todo, in_progress, done)
due_date: date (optional)
Methods
createProject(name: string) → Project
Creates a new project owned by the current user.
addTask(project_id: uuid, title: string, due_date?: date) → Task
Adds a task to the specified project. Only the project owner can add tasks.
That's the spec. A human can read it in 30 seconds. The compiler turns it into:
- A SQL database with two tables, foreign keys, and indexes
- TypeScript methods with type signatures and auth checks
- A React frontend with forms, validation, and state management
- API endpoints with request/response schemas
- Auth middleware that enforces "only the owner can add tasks"
- Deployment config, environment variables, and monitoring hooks
The spec is 20 lines. The compiled output is 2,000 lines of TypeScript, SQL, and React. You never touch the 2,000 lines. You edit the spec and recompile.
## What This Means for Who Writes Software
Every abstraction ladder climb changed who could program.
Assembly meant you didn't need to memorize opcodes. C meant you didn't need to think in registers. Python meant you didn't need to manage memory. Each step opened programming to people who couldn't (or didn't want to) work at the lower level.
Annotated prose does the same thing. If the source of truth is a readable spec, you don't need to be fluent in TypeScript to define an application. You need to be able to describe what it does and annotate the precision.
That's a different skill. It's closer to product thinking than to coding. A PM who can write a clear product spec can write an MSFM spec. An operator who understands their workflow can describe it in enough detail for a compiler to generate the app.
This doesn't mean engineers disappear. It means engineers work at a different layer. Instead of writing CRUD boilerplate, they work on the compiler, the runtime, the abstractions the spec compiles against. The same way most engineers today don't write assembly—but someone still maintains LLVM.
## Why Now?
The abstraction ladder has always climbed when two things converged:
1. **The lower layer became too complex to manage by hand.** Assembly was unmanageable at scale. C codebases became unmanageable without garbage collection. TypeScript applications are unmanageable without better separation between intent and implementation.
2. **A new compiler became good enough to handle the translation.** You couldn't have C without a C compiler that produced decent assembly. You couldn't have Python without a runtime that handled memory well enough. You can't have annotated prose without a compiler that generates production-grade code.
We're at that point now. LLMs are good enough to compile structured specs into working applications. Not perfect—no compiler ever is—but good enough that the compiled output is deployable, maintainable, and correct most of the time. Understanding [real benchmark results comparing GPT-5.4 vs Claude Opus 4.6 vs Gemini 3.1 Pro](/blog/gpt-54-vs-claude-opus-46-vs-gemini-31-pro-benchmarks) helps explain why this inflection point is happening now.
Remy is the first production system doing this at scale. It compiles MSFM specs into full-stack TypeScript applications: backend methods, SQL databases, React frontends, auth flows, deployment pipelines. The specs are readable. The output is real code you can edit, extend, and deploy.
This is the same inflection point C hit in the 1970s. The question then wasn't "will we stop writing assembly?" It was "when?" The question now isn't "will we stop writing TypeScript as the source of truth?" It's "when?"
## What About the Code?
The compiled code still exists. It's still TypeScript (or Python, or whatever the target language is). You can read it. You can edit it. You can extend it with hand-written code when the spec isn't expressive enough.
But it's not the source of truth anymore. The spec is.
This is the same relationship assembly has to C. The assembly is still there. LLVM still generates it. But you don't write it by hand unless you're optimizing a hot loop or writing a kernel driver. For everything else, you write C and let the compiler handle the translation.
Same here. For most applications, you write the spec and let the compiler generate the TypeScript. For the 5% of cases where you need manual control—performance-critical paths, unusual integrations, legacy system bridges—you drop down and edit the compiled code directly.
The difference is: when you edit the compiled code, you're working against the grain. The spec is the reset point. If you recompile, your hand edits get overwritten unless you've also updated the spec to reflect them.
This is by design. It keeps the spec and the code in sync. It prevents drift. It makes the spec the authoritative source of truth, not just documentation that falls out of date.
## The Objection: "Natural Language Is Too Ambiguous"
The most common objection to annotated prose as a programming language is that natural language is ambiguous. "Create a project" could mean a dozen different things. How does the compiler know what you meant?
The answer is: **annotated prose isn't pure natural language.** It's structured. The annotations carry the precision.
When you write `createProject(name: string) → Project`, that's not ambiguous. It's a typed function signature embedded in prose. When you write a table schema with column types and foreign keys, that's not ambiguous. It's a structured data model.
The prose layer is for human readability. The annotation layer is for compiler precision. Both are in the same document. The compiler reads both.
This is the same way C works. `int x = 5;` is partly natural language ("x") and partly structured syntax ("int", "=", "5", ";"). The natural language part is for humans. The structured part is for the compiler.
Annotated prose just shifts the ratio. More of the document is readable prose. The structured parts are embedded as annotations instead of dominating the syntax.
## Where This Goes
If annotated prose is the next rung, what comes after?
Probably conversational intent. You describe what you want in a conversation. The system asks clarifying questions. It generates a spec. You approve it. The spec compiles into an application.
At that point, the "programming" is the conversation. The spec is an intermediate artifact the system maintains. You never see the code at all unless you choose to.
We're not there yet. But the path is clear. Conversational intent requires annotated prose as the intermediate layer. You can't compile a conversation directly into code—there's too much ambiguity, too much context, too much implicit knowledge. You need a structured artifact in between. That artifact is the spec.
Remy is building that intermediate layer now. The conversation happens (you describe the app to the agent). The agent generates the spec. The spec compiles into the application. The spec stays in sync as the application evolves.
That's the foundation. Once it's solid, the conversation layer can get better without the compilation layer breaking.
## FAQ
**Is this just "AI writes code for you"?**
No. AI-generated code is still code-as-source-of-truth. You prompt an AI, it writes TypeScript, you edit the TypeScript, the TypeScript is your application. Annotated prose is different: the spec is the source of truth, the code is compiled output. When you want to change the application, you change the spec and recompile. The code is downstream.
**Can I still write code if I want to?**
Yes. The compiled code is editable. You can extend it, optimize it, integrate it with systems the spec doesn't cover. But the spec is the reset point. If you recompile, hand edits get overwritten unless you've updated the spec to match.
**What if the compiler generates bad code?**
Same answer as "what if the C compiler generates slow assembly?" You profile it, you optimize the hot paths by hand, or you wait for the compiler to get better. Most of the time, the compiled output is good enough. When it's not, you drop down to the code layer and fix it manually.
**Does this mean non-engineers can build applications now?**
It means the skill shifts. You don't need to be fluent in TypeScript to write a spec. You need to be able to describe what the application does and annotate the precision (types, constraints, edge cases). That's closer to product thinking than to coding. Some non-engineers will be great at it. Some won't. Same as coding.
**Why would I use this instead of just writing TypeScript?**
For the same reason you write TypeScript instead of assembly. It's a higher level of abstraction. You express intent, the compiler handles implementation. If you're building a CRUD app, a workflow tool, an internal dashboard—anything where the architecture is standard and the complexity is in the domain logic—the spec layer is faster and more maintainable than writing TypeScript by hand.
**What about performance?**
Compiled code is usually fast enough. When it's not, you optimize by hand. Same as every other abstraction layer. Python is slower than C, but most applications don't need C-level performance. Annotated prose will produce slower code than hand-optimized TypeScript, but most applications don't need hand-optimized TypeScript.
**Is Remy the only system doing this?**
Remy is the first production system compiling annotated prose (MSFM) into full-stack applications at scale. Other tools generate code from prompts, but the code is the source of truth. Remy's spec is the source of truth. That's the structural difference.
**How does Remy stay useful as AI models improve?**
The spec is the source of truth; recompile and the app upgrades. When better models become available, you run the same spec through the improved compiler and get better code, better architecture, better performance—without changing the spec. This is fundamentally different from [how to run Claude Code for free using Ollama and Open Router](/blog/how-to-run-claude-code-free-ollama-open-router) where you're still generating code as the end artifact.
**Where can I try this?**
Remy is in open alpha. You can try it at [goremy.ai](https://goremy.ai). Describe an application, watch the agent generate the spec, compile it into a working app, and deploy it. The whole process takes 10-30 minutes depending on complexity.
## What Is Remy?
Remy is a product agent that compiles annotated markdown into a full-stack app—backend, database, frontend, auth, tests, and deployment—in a single step. The spec is the source of truth. The code is compiled output. When models improve, you recompile the same spec and get better code automatically. See [goremy.ai](https://goremy.ai).
---
Programming has always moved up in abstraction. Punch cards to assembly to C to TypeScript. Each step let you express more intent in less code. Annotated prose is the next step. The spec becomes the application. The code is what the compiler generates.
If you're still writing TypeScript by hand for every new application, you're working at the wrong layer. The future is already here. It's just a markdown file.
<a href="https://goremy.ai" data-cta="try-remy" data-cta-location="closing">Start building with Remy →</a> 