Tech debt, or technical debt is pretty much exactly what it sounds like.
When building software, there is a constant trade off between implementing features quickly, and implementing them right.
Ideally, you would always build them right, and in the long term this will also be the quicker route.
When features are implemented with care they are tested and reliable, flexible and well architected. Future developers working on the code will probably not have a lot of trouble understanding the work, and will be able to build on it and modify it with ease.
However, there is an upfront time cost to doing things the right way, and sometimes it can be worth taking on short term ‘tech debt’ in order to get a feature out in time for a specific deadline.
This means that the implementation may cut some corners, and be designed in a less flexible way. Testing coverage may be lower, and the architecture will be less thoroughly planned out.
This ‘debt’ in a healthy system will be paid off as soon as possible after the immediate deadline.
If it is not paid off, and more technical debt is taken on, then the product can begin to suffer.
Changes become harder as poorly architected code, often tightly coupled to other areas of the system, introduces bugs. Fixing these bugs can cause other bugs, and little by little it becomes impossible to add new features, or to amend existing features to match changing business requirements. The development team finds that most of their time is taken up fire fighting bugs, and the product growth grinds to a a halt.
This is a bad situation.
The solution is to only take on tech debt when absolutely necessary, and to pay it off as soon as possible, via constant diligent refactoring of the code base.
An analogy I like is that coding is in many ways like gardening. The job of a developer is to grow and modify various features, such that a product can adapt to meet the changing needs of its users.
Like gardening, there are many factors that affect the ecosystem that the features are growing in, and they must be constantly monitored in order for the product to grow in a healthy and sustainable way.
Technical debt can be thought of as the soil quality. If too many wacky things are done to the soil, it will lose its nutrients, and be unable to support the growth that is needed. If this goes on for too long, it will be unable to support any growth, and the garden will die. Conversely, if the soil is well cared for and ordered, the garden can flourish, and support a far greater amount of growth and change.
Being a good developer is about being a professional, and often this will mean saying no to taking on technical debt. Normally you will be under pressure from managers and clients to turn things around to tight deadlines. Agreeing to cut corners in order to meet these deadlines should be done very sparingly. Another good analogy, courtesy of Uncle Bob is the case of doctors and hand washing.
If a patient or a manager told a surgeon to skip washing their hands, because it was taking too long, and using too much water etc., the doctor would refuse. This is because the doctor is a professional, knows their craft, and knows the cost of not washing their hands.
Likewise, if a developer is a professional, and knows the true cost of incurring tech debt, then they have an obligation to refuse to take it on unnecessarily, even if that means saying no to a manager, or a client.