This is a summary of articles and books I have read in the subject over time with some notes from the original sources. Unfortunately I have lost the reference list. If you feel that some pieces of opinions/information stated here belongs to your article or book, please do contact me and I’m happy to update this article with correct references.
Legacy Code is code written as part of a software delivery that creates value for a business and/or users but is difficult for developers to change and maintain going forward. The terms code rot and spaghetti code refer to legacy code that is tangled up in poor quality. Over time, as get it done now is continually favoured over get it done right, the code base decays by avoiding industry best practices. Developers start to deliver tightly coupled, difficult to test and increasingly prone to defects software.
Warnings of Legacy Code
The followings are important signs that can lead even a brand new project into becoming a legacy project and codebase. If you ignore these signs and only focus on the deadline, by the time you deploy the project to production, it will be too late and you should admit that you have just created a legacy software.
Developers seem to be giving considerably large estimates the more project is proceeding towards to end. Every sprint planning could become a negotiation party which frustrates both Project/Product Managers and Developers. This is usually caused by the uncertainty around untestable code, blurry boundaries between contexts and knowing that unknown unknowns will inevitably arise.
This is not only true for big enterprise or tiny startups but this can happen in any organisation size. Having only one developer or certain external short-term contributors assigned and delivered the portion of the code base without Test Driven Development applied in implementation stage or any form of Domain Driven Design lacking in design stage, no one would want to own or touch these parts of the code. Most probably this will also create a dependency and attached cost to these external contributors or certain people in the business.
The following questions are so much easier to capture than previous points. When you throw these questions during any of the retro meetings or even ask anonymously in a spreadsheet to your team, the answers and ratio of yes/no could give you a really clear big picture about your software quality and tendency to create legacy software.
- Do we have increasing number of people leaving the organisation with frustration?
- Do developers repeatedly use phrases like: It was like this when I got here?
- Do changes to fix a defect result in new defects?
- Do developers repeatedly use phrases like: I thought we/I/you/they fixed this before?
- Do you see the tickets for old defects are being reintroduced in every odd sprint?
- Do you have any copy/pasted code?
- Do you have long functions with a lot of logical forks inside?
- Do you have classes that scroll on forever and freeze your IDE?
- Do you have majority of your functions with than 3 parameters unless required by programming language or framework?
- Do you have code pieces that are comment-heavy and actually longer than the lines of code?
- Do developers like to play Jenga with codebase? i.e developers fear breaking everything with a line of code change.
- Do you talk of The Big Rewrite even at non-devs or business/management level?
If majority of your answers are Yes and you do these regularly, you business can be tipped down by a competitor so much easily. It also means you have much more bigger issues on surviving and your software will not really change the world!
Methods to Mitigate Legacy Code
I believe there are a lot of tailored ways of mitigating these problems at organisational and culture level for each company. However, the followings are one of the most impactful ones to start with. They also are the hardest to establish in an existing organisation. One of the tricks that can accelerate this could be hiring people that have done this before. This brings experience with them and improves organisational muscles towards a better stage steadily.
1. Quarantine The Mess
Start place the code base under an automated black box test harness. The initial tests should test what the system currently does, not necessarily what it’s assumed to do so. These tests should be running without changing the codebase and business wise the cost of running these tests should be regarded cheaper when compared to time and money spent on manual testing. Only after these tests are in place, then the requirements can be clarified as to the actual intent of the system. This will also allow to create a safer environment for refactoring the codebase.
2. Refactor Relentlessly
Once the code is under version control and test harnesses are in place, begin refactoring whenever you touch the code. Refactoring embraces the fact that we can’t plan a perfect design upfront and that, given enough time, most architecture will crumble without routine maintenance. Just like your car, your code base needs regular tune ups.
As developers learn more about the business, the code should be refactored to reflect the new knowledge. Every time you are in the code base, leave the code cleaner than you found it. As you refactor more and more, the code base becomes easier and easier to change, and less and less defects will be present.
What You Need to Check Now?
As a manager or individual contributor, please ask the following questions to yourself and your team in order to asses if you have a culture of legacy software creation in place. Sometimes, there is no clear answers or immediate response but keep asking these at least in some retro meetings to do sanity check in your software development culture.
- Do we choose Quality over Deadline/Client Pressure?
- Do we have the notion of Testing or Automation at all?
- Do we encourage Refactoring of production code?
- Do you ask for permission to refactor production code?
- Do you negotiate on dedicated time for refactoring in sprint planning?
- Do you have anyone with enough knowledge sharing best practices between developers to teach importance of Testing and Automation?
- Do you have organisational perception of tests and automation as an internal process of development or instead seeing the, as yet another task in a ticket?
What Actions Can Be Taken?
You would be really struggling to push this individually either as a manager or individual contributor. If you are working for a very early stage startup with founders still coding, you have to be either lucky that they could value this on top of pressure of shipping product early on time or you have to be patient enough to hire people know and love avoiding legacy code creation in later stages (most probably after series A round).
If you have some kind of established organisation and looking for healthy scale up of your engineering organisation, it is better that you should start embracing these from the top to the bottom. It would be really beneficial to create a tailored learning experience for managers to start with. Later, these managers could discuss and plan the development of individual contributors with these preventions and best practices in mind. Also, these managers and team members should seek for new team members that does this and loves doing it.
What do you think?