Technical debt isn’t what you think it is.
Kellan Elliott-McCrea wrote up an excellent commentary on tech debt back in January ’16. He makes some fantastic points that help clarify what tech debt is and isn’t, but I’ve still been feeling like something is missing in his definition. I think I’m starting to get a handle on it.
What Is Technical Debt?
Kellan tells us that technical debt as “… the choices we made in our code, intentionally, to speed up development today, knowing we’d have to change them later” is rare. I definitely agree with his sentiment. He goes on to identify five types of things that we usually mean when we talk about technical debt:
- Maintenance work
- Features of the codebase that resist change
- Operability choices that resist change
- Code choices that suck the will to live
- Dependencies that resist upgrading
This is a great classification, but I think fundamentally, he’s talking about outputs, not inputs. I’d like to get one level closer to a root cause. Based on his taxonomy, I’d say that technical debt is “the accumulated inertia from conscious trade-offs.”
Technical Debt Is Not an Accident
I use the term “trade-off” very intentionally here: I am purposely not saying “shortcut.” In my experience, I agree with Kellan–tech debt as “shortcuts that are going to bite us later” are quite rare. However, trade-offs that make thing A simple and thing B more difficult are quite common and not always avoidable.
For example, when you add an index to a database column, you’re making a trade-off. You’re saying read performance is more important than write performance or space efficiency. Most development includes trade-offs like this, because we value one or two of these things:
- Performance – faster for the user
- Comprehensibility – easier for a developer to understand
- Development time or cost – easier to write
- Ease of deployment
- Testability – easier to test
- “Hipness” – (also known as “that’s just not how things are done anymore”)–the one point on this list that most often ends up being the wrong thing to value
The items we don’t focus on are then necessarily deprioritized.
Technical Debt Is Not a Mistake
The developer who came before us isn’t a bad person for leaving some tech debt behind. He or she didn’t make a mistake. It was almost certainly a calculated, careful decision made with incomplete information (and the information is always incomplete.) In all likelihood, the original author carefully considered the trade-offs and decided to emphasize one of the items from the list above over the others. And today, the factors that he or she considered have changed.
We should not let our stakeholders see tech debt as a mess we’ve left behind because we’re moving too fast to clean up. We aren’t bad people for having left some debt behind, and it’s not a screw-up. Rather, it is almost always that we made a good decision earlier, at the point of maximum ignorance, and we know better now.
Moving Past Technical Debt
We need to stop beating ourselves up over knowing better today than we did yesterday. Stop taking a sprint to “deal with tech debt,” and start taking time to “implement the lessons we’ve learned over the past X sprints.” When technical debt is just “work” and we can discuss it on its merits and without emotion, we’ll be able to prioritize the things that matter, keep velocity up, and improve quality. But you can’t do that if you’re throwing blame around, hiding embarrassed, or glossing over a “mistake.”
There’s no such thing as technical debt—just technical work.