Lessons From Six Software Rewrite Stories (medium.com)
A new take on the age-old question: Should you rewrite your application from scratch, or is that "the single worst strategic mistake that any software company can make"? Turns out there are more than two options for dealing with a mature codebase. Herb Caudill: Almost two decades ago, Joel Spolsky excoriated Netscape for rewriting their codebase in his landmark essay Things You Should Never Do . He concluded that a functioning application should never, ever be rewritten from the ground up. His argument turned on two points: The crufty-looking parts of the application's codebase often embed hard-earned knowledge about corner cases and weird bugs. A rewrite is a lengthy undertaking that keeps you from improving on your existing product, during which time the competition is gaining on you.
For many, Joel's conclusion became an article of faith; I know it had a big effect on my thinking at the time. In the following years, I read a few contrarian takes arguing that, under certain circumstances, it made a lot of sense to rewrite from scratch. For example: Sometimes the legacy codebase really is messed up beyond repair, such that even simple changes require a cascade of changes to other parts of the code. The original technology choices might be preventing you from making necessary improvements. Or, the original technology might be obsolete, making it hard (or expensive) to recruit quality developers.
The correct answer, of course, is that it depends a lot on the circumstances. Yes, sometimes it makes more sense to gradually refactor your legacy code. And yes, sometimes it makes sense to throw it all out and start over. But those aren't the only choices. Let's take a quick look at six stories, and see what lessons we can draw.
For many, Joel's conclusion became an article of faith; I know it had a big effect on my thinking at the time. In the following years, I read a few contrarian takes arguing that, under certain circumstances, it made a lot of sense to rewrite from scratch. For example: Sometimes the legacy codebase really is messed up beyond repair, such that even simple changes require a cascade of changes to other parts of the code. The original technology choices might be preventing you from making necessary improvements. Or, the original technology might be obsolete, making it hard (or expensive) to recruit quality developers.
The correct answer, of course, is that it depends a lot on the circumstances. Yes, sometimes it makes more sense to gradually refactor your legacy code. And yes, sometimes it makes sense to throw it all out and start over. But those aren't the only choices. Let's take a quick look at six stories, and see what lessons we can draw.
Nowhere in this article is any flaw in Joel's pronouncement to never rewrite found. The only of the six stories that was a rewrite of an existing product is Netscape and that was a disaster. The fact that Firefox came out years later doesn't make it any less of a disaster.
In the rest of the cases, no one is re-writing their existing product and letting the competition catch up. No, what they are doing it making a new product and moving users over if possible. That makes sense and that is what I learned from Joel's original article.
Making this seem like some kind of intriguing rethink of rewriting legacy code is false and click-baity.
I disagree with your disagreement. Rewriting a working application is juggling with a loaded gun. You say "if you carefully learn from past mistakes" but this is almost impossible in any organization I've ever seen. All those snippets and dirty patches are not documented properly. If there are comments, they may (or may not) be out of date. Maybe there is a reason they chose a weird data structure but that guy retired 15 years ago. So you do something "proper" and find it is 10X slower. Oops.
If I've learned anything, I've learned you gotta let sleeping dogs lie. More patients are killed by doctors in this business than anything.
Sometime you need to disconnect your software from your ego.
A lot of full rewrites are primarily due to the fact the developer wants to be the Hero, toss out the old broken code, and make a new superior on in their own image. (Which then over times becomes old and broken)
Also trying to keep bad code on life support, because you had invested so much into it over your time there, is just as bad, as the application barely meets the business needs anymore, and every fix is getting increasingly more complex.
Sometimes what the code really needs, is just some reorganization. (Move your function and methods in more logical locations in your code so you visualize the problems more easier. Beautify your code, make white spaces consistent. ) Create a script to see where each function is called and where, Delete unused functions. Identify duplicate logic and merge them, or make a parametrized function of of them. It is actually amazing how a little cleanup work can turn a mess into a manageable application for decades.
Also if designing software really try to split Logic and Interface/System call into separate portions. The routine that checks the required field, should be straight logic. Not generating HTML or Form boxes, giving the errors. Despite what your bosses say, assume the platform it is running on will be retired in 5 years, and try to plan to port the application over.
Finally, really try to use basic core components as much as possible, avoid 3rd party tools as much as you can (this includes semi official repositories such as with pip or cargo). Don't be a Hero and make a ground breaking new interface, just use normal component.
If something is so important that you feel the need to post it on the internet... It probably isn't that important.
Technical debt is a thing...
Best place I ever worked knew that, and worked to quantify it. That helps a lot when you're trying to figure out whether or not to refactor. In a couple cases, it became apparent that a partial refactor was going to accomplish something like 90% of a full one, with 10% of the effort.
Quantifying your pain-points with even back-of-the-envelope calculations can really help you make good decisions about how to move forward.
Velociraptor = Distiraptor / Timeraptor