Skip to main content

Retrospective: The Rewrite That Didn't Ship

1 min read

The context

A legacy API built on Express.js, 15k LOC, lots of tech debt. The team was frustrated with the codebase and convinced a rewrite was the only way forward.

What happened

  • Month 1: Planning the new architecture
  • Month 2: Building the foundation
  • Month 3: Feature parity — discovered 23 undocumented behaviors
  • Month 4: Bug fixing and scope creep
  • End of Month 4: Canceled. Too far behind, too many unknowns.

What we should have done

Strangler Fig pattern: Replace pieces incrementally. Route new features to new code, gradually migrate old routes. No big bang.

Cost of delay analysis: The rewrite had an 8-month break-even. Legacy was slow but working. The math didn’t support it.

What I learned

The only good reason to rewrite code is if the current architecture prevents you from shipping a specific, valuable feature. “It’s messy” is not a reason. “We can’t add real-time collaboration without a fundamentally different data model” is.