Software systems are prone to the build up of cruft - deficiencies in internal quality that make it harder than it would ideally be to modify and extend the system further. Technical Debt is a metaphor, coined by Ward Cunningham, that frames how to think about dealing with this cruft, thinking of it like a financial debt. The extra effort that it takes to add new features is the interest paid on the debt. Thinking of this as paying interest versus paying of principal can help decide which cruft to tackle. If I have a terrible area of the code base, one that's a nightmare to change, it's not a problem if I don't have to modify it. I only trigger an interest payment when I have to work with that part of the software (this is a place where the metaphor breaks down, since financial interest payments are triggered by the passage of time). So crufty but stable areas of code can be left alone. In contrast, areas of high activity need a zero-tolerance attitude to cruft, because the interest payments are cripplingly high. This is especially important since cruft accumulates where developers make changes without paying attention to internal quality - the more changes, the greater risk of cruft building up.
Ward Cunningham, one of the authors of the Agile Manifesto, once said that some problems with code are like financial debt. It’s OK to borrow against the future, as long as you pay it off.
Since Ward first used this metaphor, which he called “Technical Debt”, it has gained momentum. While people still disagree about the exact definition of technical debt, the core concept identifies a serious problem that many software teams are struggling to manage.
Ward used it the first time when he was developing a financial application in Smalltalk. He wanted to justify to his boss the refactoring they were doing, so he used a financial analogy:
If we failed to make our program align with what we then understood to be the proper way to think about our financial objects, then we were going to continue to stumble on that disagreement which is like paying interest on a loan.
Later, in 1992, at the OOPSLA conference, Ward provided additional details (slightly paraphrased here based on feedback from Ward):
Shipping first-time code is like going into debt. A little debt speeds development so long as it is paid back promptly with refactoring. The danger occurs when the debt is not repaid. Every minute spent on code that is not quite right for the programming task of the moment counts as interest on that debt. Entire engineering organizations can be brought to a stand-still under the debt load of an unfactored implementation, object-oriented or otherwise.
Don’t Start Up With Hidden Debt: Understanding and Managing Technical Debt
The metaphor of debt is sometimes used to justify neglecting internal quality. The argument is that it takes time and effort to stop cruft from building up. If there new features that are needed urgently, then perhaps it's best to take on the debt, accepting that this debt will have to be managed in the future. To my mind, the question of whether a design flaw is or isn't debt is the wrong question. Technical Debt is a metaphor, so the real question is whether or not the debt metaphor is helpful about thinking about how to deal with design problems, and how to communicate that thinking. A particular benefit of the debt metaphor is that it's very handy for communicating to non-technical people.
Technical dept is also related to software updates. If platform is using an old framework there are performance and security limits attached to this. Although they are typically small and free, software updates play important roles often related to solving or preventing a problem:
- Protect against new-found security risks
- Introduce new features in your software
- Improve battery depletion rate or performance speed
- Extend your equipment's usable life by allowing its maximum productivity
- Fix bugs in the software and improve functionality
Technical debt (also known as design debt or code debt) is a concept in software development that reflects the implied cost of additional rework caused by choosing an easy or limited solution now instead of using a better approach that would take longer. If team productivity is hard to figure out, it's even harder to measure the contribution of individuals on that team. You can get a rough sense of a team's output by looking at how many features they deliver per iteration. It's a crude sense, but you can get a sense of whether a team's speeding up, or a rough sense if one team is more productive than another. But individual contributions are much harder to assess. While some people may be responsible for implementing features, others may play a supporting role - helping others to implement their features. Their contribution is that they are raising the whole team's productivity - but it's very hard to get a sense of their individual output unless you are a developer on that team.
With borrowed money you can do something sooner than you might otherwise, but then until you pay back that money you'll be paying interest. I thought borrowing money was a good idea, I thought that rushing software out the door to get some experience with it was a good idea, but that of course, you would eventually go back and as you learned things about that software you would repay that loan by refactoring the program to reflect your experience as you acquired it.
I think that there were plenty of cases where people would rush software out the door and learn things but never put that learning back into the program, and that by analogy was borrowing money thinking that you never had to pay it back. Of course, if you do that, you know, say with your credit card, eventually all your income goes to interest and your purchasing power goes to zero. By the same token, if you develop a program for a long period of time by only adding features and never reorganizing it to reflect your understanding of those features, then eventually that program simply does not contain any understanding and all efforts to work on it take longer and longer. In other words, the interest is total -- you'll make zero progress.
Ward Cunningham reflects on the history, motivation and common misunderstanding of the "debt metaphor" as motivation for refactoring. Technical debt is a metaphor developed by Ward Cunningham (developer of the first Wiki and pioneer in patterns and XP) to frame the problem of the inevitable trade-offs made between rushing to capture market vs. the longer term viability of code and infrastructure. As a startup, these trade-off decisions will never be more constant and far reaching. While technical debt may be unavoidable, understanding and managing technical debt from the beginning is crucial to a startup’s ability to grow and scale.
Are there other types of debt?
Not all software projects issues are Technical Debt:
- Identified defects are not Technical Debt. They are Quality Debt.
- Lack of process or poor process is not Technical Debt. It is Process Debt. An example is Configuration Management Debt.
- Wrong or delayed features are not Technical Debt. They are Feature Debt.
- Inconsistent or poor user experience is not Technical Debt. It is User Experience Debt.
- Lack of skills is not Technical Debt. It is Skill Debt.
The Technical Debt concept is quite simple. When looking into details, it appears that they are many aspects to consider for analyzing and managing the situation.