← Back to Blog
Building in Public

The Great Rebuild: Starting Over When Starting Over Is the Only Option

christian crumlish•
A robot inventor surrounded by sketches and discarded parts, embracing a full restart as the only path forward.
“Back to the drawing board!”

The Great Rebuild: Starting Over When Starting Over Is the Only Option

June 1, 2025

There’s a particular kind of clarity that comes after you close your prototype folder and open a fresh terminal. Not deletion — the old code sits there like a photo album, reminding you how far you’ve come. But you’re not looking back anymore.

One manic week of work. Still there, still kinda broken, but an evolutionary dead end. (Later I’ll write a piece about how I got the proof-of-concept and prototype debugged and saved in demo branches so I can still show them in action when telling this story.)

But you know it felt good? I had learned a ton, stopped myself before running off a cliff and while it was definitely going to take weeks if not months, I was ready to build Piper Morgan the right way.

The diagnosis: successful prototype syndrome

After the scaled-back demo, I spent a weekend doing what any reasonable engineer would do: trying to find a path forward with the prototype. Just refactor this bit. Extract that service. Maybe if I just…

No. Stop.

I had three different architectural assessments open in different tabs. I threw the generated specs from what I was now calling Piper Morgan 0.1.1 at several LLMs and told them “You are a distinguished technical architect. An eager PM and developer have prototyped an intelligent agent and are hyping it but they have not built it in a sound way. Please review these docs and propose an appropriate architecture for this project.”

Each one trying to chart a course from the prototype’s “architecture” (I’m being generous) to something sustainable. The conclusion was unanimous: start fresh with what you’ve learned.

The plans were similar but different. Some got going faster, some were more rigorous and robust. In the end I let Claude Opus (by now my boss at Kind had approved me upgrading my subscription) to adjudicate and we synthesized a “best of” plan.

Claude called it “successful prototype syndrome” — when a prototype works just well enough that you’re tempted to build on it, but not well enough to actually support what you’re building.

Pretending I understand domain-driven design

Sunday morning. Fresh coffee. New directory: piper-morgan-platform/. Time to do this right. (The word “platform” seemed a few generations off and I later changed the project name to piper-morgan-product for the MVP. That change went fine by the way but a later directory-name change on my laptop led to some hilarious shenanigans.)

But where to start? With a question: What are we actually modeling here?

not this:

class GitHubIssue:
title: str
body: str
labels: List[str]

but this:

class WorkItem:
title: str
description: str
acceptance_criteria: List[str]
item_type: WorkItemType # Story, Bug, Task, Spike
priority: Priority

class Product:
name: str
vision: str
features: List[Feature]

class Stakeholder:
name: str
role: str
interests: List[str]

The first is modeling GitHub. The second is modeling product management. GitHub is just one place work items might live.

Starting with intent (and TextEdit)

Yes, TextEdit. I am not a programmer! I’m barely a hacker. When I started I was literally spawning random terminal windows, constantly having to recreate my virtual environment, and opening files from Finder like it was 2003. VS Code? Cursor? Those revelations would come later, each one making me wonder how I’d survived without them.

But even with primitive tools, the design principles were clear. This time, I started with intent categories:

class IntentCategory(Enum):
EXECUTION = "execution" # Create, update, implement
ANALYSIS = "analysis" # Investigate, measure, evaluate
SYNTHESIS = "synthesis" # Summarize, consolidate, report
STRATEGY = "strategy" # Plan, prioritize, decide
LEARNING = "learning" # Improve, adapt, evolve

Everything else would flow from these. Not “what can we build?” but “what do PMs actually need to do?” Is this list exhaustive? Of course not. Is it good enough for now? I think so?

The two-laptop reality check

I develop on two machines:

  • Personal laptop (gaelic word for seagull: faoilean)
  • Work laptop (charming in a different way: kindbook)

I knew I wanted the project on github, part of working in the open and to preserve things and, of course, version control. Even the prototype was (and still is) on github. But also, I work on two laptops. I have one for work and one for play but some things are both.

It’s also a forcing function. If your development environment only works on one special machine with that one special configuration, you haven’t built a system — you’ve built a house of cards.

Of course, in these early days, “development environment” meant “whatever Python was installed” and “hoping I remembered to activate the virtual environment” and “constantly installing and then immediately upgrading Pip.” The proper Docker setup would come later, after enough pain to make it obvious why we needed it.

You know one of the immediate benefits I’ve been getting from all this is more empathy for my engineers. I would never claim to have their chops but I am spending a lot mor time looking at the world through their screens and feeling my hands “on the metal” for the first time since, well, the early days of the Internet, and I think it will make me a better PM.

The beautiful ambition of starting right

Here’s what I knew I wanted, even if I didn’t know how to build it yet:

  • Real domain models, not tool-specific hacks
  • Services that could talk to each other
  • A learning system built in from the start
  • Plugin architecture for integrations
  • Production-grade quality (whatever that meant)

I didn’t have Docker yet. I didn’t have proper development tools. I was making indentation errors that would cost hours of debugging. But I had a vision of what this could become.

Spoiler alert: Every time I have gotten off track (it happens a lot!) I have been able to eventually get back to what I think of as “the right timeline” by reminding Claude and myself that we are using domain-driven design, working from the domain layer down through the database layer, to the orchestration engine and the discerning of intents and on to the workflows.

This has whipped us back into shape already more times than I can count.

The humbling reality of progress

Let’s be honest: rebuilding “the right way” is slow. Painfully slow. Weeks later, I’d still be working toward features that had “worked” in the prototype in days.

But here’s what I was learning: “worked” is a spectrum. The prototype’s version of “working” was like a Rube Goldberg machine — impressive when it succeeded, catastrophic when anything changed. The platform’s version would be boring. Reliable. Extensible.

Some things that took time:

  • Learning to use VS Code (then Cursor) instead of TextEdit
  • Understanding why Docker mattered (after the nth “works on my machine”)
  • Discovering test-driven development (weeks away still)
  • Taming the Cursor Agent when it wanted to rewrite everything
  • Building each service properly instead of just making it work
  • Dealing with regressions and sneaky little flaws that survived just long enough to bite us weeks down the road.

The lessons were already emerging

Even in those first days, with TextEdit and terminal windows scattered across my screen, principles were crystallizing:

  1. Domain models first, integrations second — Model your problem space, not your tools
  2. Two laptops keep you honest — If it doesn’t work on both, it doesn’t work
  3. Intent drives architecture — What users want to do matters more than what’s easy to build
  4. Learning can’t be bolted on — It has to be designed in from the start
  5. Tools matter — But you learn which ones by suffering without them

The unexpected joy of starting fresh

You know what? Starting over isn’t failure. It’s graduation. Every bad decision in the prototype became a good decision in the platform. Every shortcut that bit me became a principle that guided me.

The prototype was a three-week requirements-gathering exercise that happened to produce code. The platform would be built on those requirements.

And that’s why I was smiling as I opened that fresh terminal. I wasn’t throwing away code. I was building on top of everything it had taught me.

What actually happened next

The real story? It would take weeks to match the prototype’s functionality. And that was fine. Because this time:

  • Each feature would be built on solid foundations
  • Services would have clean boundaries
  • The architecture would support the vision, not constrain it
  • I’d learn proper tools and practices along the way

This isn’t about speed anyhow. It was about building something that could evolve without collapsing. Also, it’s really a learning journey. I basically have three goals:

  1. Sandbag: learn a lot (already achieved!)
  2. North star: make something actually useful for me
  3. Stretch goal: make a product others could use or build on

Sometimes the fastest way forward is to slow down and build it right. Measure twice, cut once. Slow is smooth and smooth is fast. A stitch in time… you know the drill.

← Back to BlogAlso available on Medium