The existence of the technical debt in all IT projects is often an open secret that nobody involved wants to admit. The scale of the debt and the speed at which it grows depends on many variables. I’m gonna walk you through a few most important aspects of technical debt (in my opinion of course). With that knowledge, your daily developer work will be easier in the long run. Fewer bugs and the easier introduction of new features will surely be rewarding for the team and make the project itself better.
The first issue on our list is the fast pace of new features introduction. It often goes in combination with skipping some important design and architecture bits. The new feature is just glued into the project without SOLID principles preserved. If it works, it works, I guess it’s good enough, but this is only partially true. If you make these mistakes, they can get back at you in the future and interfere with the development of the project.
The second problem on my list is skipping Unit testing of newly introduced features. If SOLID wise features can be placed between trash and garbage, we need at least add Unit Tests. Those can be reused when the feature will be rewritten or refactored. It is important to ensure that the functionality is redone in 100% and don’t introduce any regression bugs.
The third mistake is forgetting about documentation. Developers' brains don’t store unneeded information. We forget about feature-specific solutions and hacks implemented after a couple of weeks of the project lifespan. Sooner than later the project-specific elements will be overwritten by new features. And when you get back to the feature that you need to refactor it won't be there. And believe me, that time will finally come. You will spend many hours trying to figure out what the author had in mind. That’s embarrassing, especially when you were… the author.
The fourth well-known sin committed by development teams is the lack of proper code review. We accept the code that’s good enough. But in many cases good enough isn’t so good in the last place. Later on, we can’t focus and lose the bigger picture. For example, we concentrate on typos in comments instead of critical code failures and risky code structures.
The code review process is the most important point of your software production. With good code review you will:
mentor junior developers how to code better,
give feedback to experienced developers,
show a better approach (if it is possible) and plan future refactoring if the deadline is tight.
Increase in the quality of software
The fifth issue is the sight of surprise on the developer's face when he finds a technical debt that wasn't addressed before. All the time, each developer should be on a technical debt hunt! When you open a class after a while, and you see the mistakes, don’t procrastinate, address the problem, create a ticket and plan it. Refactor! Fulfill your duty to the project.
The sixth problem: losing track of your debt, each commit, each version you and your team released. All the team members knew that some shortcuts were made. But they didn’t know how far the debt was forced into the project. There is a point of no return and believing it's still far away is irresponsible. Your team needs to act now! Audit the project with a static analysis tool. Establish the desired level of debt in your project. Make a plan to refactor most debt-heavy classes. Introduce in your Continuous Integration a step that will run the static analysis tool, and bring you a detailed report for each commit. That will give the team situational awareness about the debt introduced or the debt reduced with this change. Furthermore, it can make the code review easier, because it can integrate nicely with GitHub or GitLab merge requests.
The Seventh Sin - Unit tests. Yes, we are all guilty of skipping the unit tests! It’s hard to write them when the time is crucial. Skipping these tests is risky in all situations. But when you plan a refactor and the features aren’t covered with tests, it can be a suicidal mission for the team, managers, and the dagger for the project. You need to have the source of truth that will determine if the feature you just refactored is working as intended. Before refactoring, do yourself a favor and test the feature you're gonna work with.
The Eighth, final, and most important problem - in my op
inion - is building a team awareness that with any chosen approach we will always introduce some amount of technical debt into our project, simply because of a need of meeting business needs and given deadlines. But, having this in mind, we also need to be aware of the fact that in the next iteration we're gonna deal with that debt by refactoring the trouble-making solutions.
That awareness is a key to keeping the debt at bay. When you can address the problems you created, prioritize and plan tickets to refactor parts of code that have the heaviest impact on debt and project.
Tips and tricks to avoid the technical debt
Don’t deny the existence of the technical debt in your project. Raise awareness about it among your management. Define weak spots and prioritize tasks. Plan the refactor in your development cycle (time-box the refactor tasks). Write the tests to ensure that refactoring won’t damage anything fragile. Do the refactor itself. Track the progress of the refactor with a static analysis tool. And keep your team sane and they won’t be afraid to work with your well-maintained project.