BT

Facilitating the Spread of Knowledge and Innovation in Professional Software Development

Write for InfoQ

Topics

Choose your language

InfoQ Homepage Articles Pragmatic Technical Debt Management

Pragmatic Technical Debt Management

Bookmarks

An overview of technical debt

Technical Debt is a metaphor coined by Ward Cunningham in a 1992 report [1] and is defined as the debt that accrues when we knowingly or unknowingly make wrong or non-optimal technical decisions [2]. It is very similar to financial debt. A person incurs debt when he takes a loan. If he is making regular repayments, then the created debt is acceptable and does not introduce further problems. However, if the person does not repay, a penalty in the form of interest is applicable and it mounts every time he misses the payment. In case the person is not able to make any payment for a long time, then accrued interest makes it even more difficult to clear the debt. In the extreme case, the person has to declare himself as bankrupt.

In the same way, when a person adopts an un-optimal or sub-optimal technical decision, he introduces technical debt. If it is not corrected soon enough, the decision impacts other related technical decisions and the debt starts mounting. In the case of non-payment of the accrued technical debt for a long time, the software increasingly becomes harder to change and in the extreme case, the software product becomes technically bankrupt (i.e., it is not feasible to introduce a change reliably in the prescribed time). Such situation often leads to project closure.

Why is it important for a software practitioner to be aware of technical debt and why must he try to avoid incurring it? To understand this, let us first understand the components of technical debt. Technical debt is a result of principal (the original hack, or shortcut), and accumulated interest incurred when the principal is not addressed on time. The interest component is compounding in nature: the more development teams ignore it or postpone it, the bigger the debt becomes over time. Thus, it is the interest component that makes technical debt a significant problem.

Large technical debt impacts the productivity of the software development team and lowers their morale and motivation. Continuous accrual of technical debt leads to a vicious cycle: large technical debt reduces the productivity and morale of the team; at the same time low productivity attracts management push for more features and postponement of technical debt issues, which in turn further increases the technical debt.

There are multiple dimensions of technical debt. Some of the prominent dimensions of technical debt are:

  • Implementation debt: Examples- code duplication, static tool rules violations, and code smells.
  • Design and architecture debt: Examples - Design smells, design rules violations, and architectural rules violations.
  • Test debt: Examples - Lack of tests, inadequate test coverage, and improper test design.
  • Documentation debt: Examples - No documentation for important concerns, poor documentation, outdated documentation.

Figure 1: Dimensions of technical debt

A type of technical debt defines why and how the technical debt occurs. A well-known classification [3] of technical debt is as follows:

  • Strategic debt – This type of debt is incurred knowingly for strategic gains (such as first to release in market) and intended for long-term.
  • Tactical debt – Such debt instances are incurred knowingly for quick gains and are typically intended for short-term.
  • Inadvertent debt – Inadvertent debt is incurred unknowingly usually due to lack of knowledge and awareness.
  • Incremental debt – Periodic inadvertent debt results in incremental debt.

Managing technical debt

“Debt is inevitable!” In this fast-paced world, software development teams have the responsibility to quickly deliver value to their customers. In this pursuit, there are various occasions when the team has to opt for quick-and-dirty solutions. In these situations, it is important to adopt a diligent and pragmatic approach to handle technical debt issues.

The first aspect to manage technical debt is to “prevent” technical debt from accumulating. It includes increasing awareness within the software development teams about technical debt and introducing relevant processes within the organization. Another aspect to manage technical debt is to “repay” technical debt. Conscious efforts are required to identify, prioritize, and refactor technical debt issues in real-world projects. Let us discuss these aspects in more detail below.

Preventing technical debt

One of the key ways to prevent technical debt is to create awareness about technical debt in development teams. Development teams must know about technical debt, its various dimensions and types, and the impact of debt on their project. They must be well equipped with code quality concepts, clean coding practices, design smells, and ways to refactor them.

The level of understanding and awareness about best practices and above-mentioned concepts could be improved by conducting focused trainings, as well as organizing workshops and conferences.

Employing relevant processes can help a development team prevent accumulation of technical debt. Typical examples of such processes are review processes (such as code, design, architecture, and test reviews) and architecture governance (for instance, to ensure that the code adheres to the intended architecture and design). However, the adopted processes must be pragmatic: rigid and difficult to follow processes deter the team from following them properly and lead them to seek shortcuts while adhering to the processes.

Repaying technical debt

Often, teams work in projects that have accumulated considerable amount of technical debt. In such situations, it is not wise to ignore the debt further since it may lead the project to technical bankruptcy. On the other hand, it is also not feasible and practical to stop developing new features for a few months and instead focus only on repaying technical debt.

A balanced approach is required in these situations to repay the debt steadily and keep progressing as far as features and functionality of the software is concerned. Let us now discuss a few pragmatic strategies for repaying technical debt.

1. Identify, document, and track the debt

The first step towards repaying technical debt is to identify and document existing debt. Numerous tools are available that could be used to identify the concrete debt instances for various technical debt dimensions [4]. Further, experienced developers and architects in the team can also identify debt instances. Once identified, the debt instances must be documented in a suitable form. Such documentation could be performed using simple Excel sheets or with the use of sophisticated tools such as Teamscale [5]. Then, the documented debt instances need to be assessed and their status must be traced (whether the team is going to fix them, and if so, who will fix them and when).

2. Prioritize smells

Not all debts are the same – different types of debt come with different interest rates. Hence, the identified debt instances must be prioritized for refactoring based on factors such as potential impact of the debt instance on the project. It is practically impossible (in fact, not recommended also) to be 100% “debt free” in real-world projects; it is okay to live with some (low priority) debt to maintain the balance between feature development and technical debt repayment.

3. Amortize small debt payment into each iteration

In the financial domain, if one has a large loan (say, a home loan), it is unlikely that the person could repay the whole loan in one instance; however, it is definitely easier for the person to repay the loan by paying EMIs (Equated Monthly Installments). In the same way, it is unlikely for a project team to repay huge technical debt all at once; however, repayment in the form of small installments – ERIs (Equated Release Installments) is quite feasible and practical where a small portion of effort in each iteration is dedicated to refactoring.

4. Motivate and reward people for maintaining quality

“People care about the things that you measure and you reward.” If the manager of a software development team measures the number of features delivered or number of defects fixed by the team as the yardstick for their performance, then the team will only focus on adding features and fixing defects. How well it is done is as important as getting it done. Keeping the motivation high and rewarding people for not only developing working code but also quality code is the key strategy in the battle against high technical debt and deteriorating quality.

5. Follow “Boy’s scout rule”

The Boy’s scout rule i.e., "always leave the campground cleaner than you found it" is applicable for developing software too: “check-in the code better than you checked-out”. Encourage the team members to reduce technical debt actively; for instance, motivate them to refactor whenever they touch a piece of code for feature addition or bug fixes.

6. Look out for possible large-scale debt repayments

Large-scale debt repayment is analogous to making the part-payment of a big home loan upon receiving a bonus from the employer. Keep looking out for opportunities to repay debt on a large-scale, for instance, just after a major release. Large-scale changes such as performing architecture refactoring can contribute to drastic reduction in technical debt. On the flipside, it requires considerable planning and effective communication to reduce the associated risks while performing such large-scale debt repayment.

7. Repay debt horizontally and not vertically

Debt instances belonging to different dimensions impact each other. For example, instances belonging to test and design debt could be related. It is quite possible to change a few design decisions in order to make the code testable (or vice-versa). Hence, instead of trying to completely repay technical debt in one dimension, attempt to repay debt associated with an entity (viz. a class, file, or component) in various dimensions.

8. Don’t repay debt in certain cases

Yes, it is not worth repaying technical debt in certain cases even if the debt is very high. Such cases include technical debt incurred in prototypes, proof of concept implementations, and products that are nearing end-of-life. In addition, if migration to a new technology, platform, or architecture is planned for your legacy project, it is wise not to repay the technical debt in the legacy project, since relevant debt can be addressed during the migration.

References

  1. Ward Cunningham. The WyCash Portfolio Management System, Experience Report, OOPSLA '92.
  2. Girish Suryanarayana, Ganesh Samarthyam, Tushar Sharma. Refactoring for Software Design Smells: Managing Technical Debt, Morgan Kaufmann/Elsevier; 2014.
  3. Edith Tom, AybüKe Aurum, and Richard Vidgen. 2013. An exploration of technical debt. Journal of System and Software 86, 6 (June 2013), 1498-1516.
  4. Tool suite for identifying and addressing technical debt. Available online. Last assessed: 27th July 2015.
  5. Teamscale. Available online. Last assessed: 27th July 2015.

About the Authors

Tushar Sharma is currently a Technical Expert at Research and Technology Center, Siemens Technology and Services Pvt. Ltd. Bangalore, India. His work at Siemens involves researching, providing consultation and trainings on topics related to software design, refactoring, design smells, code and design quality, design patterns, and change impact analysis. He has been pursuing his research interests actively in topics related to software design and refactoring that resulted in several patents, research papers, and tools. He has an MS (by research) degree in Computer Science from the Indian Institute of Technology-Madras (IIT-M), Chennai, India, where he specialized in design patterns and refactoring. He has co-authored two books; his first book "Oracle Certified Professional Java SE 7 Programmer Exams 1Z0-804 and 1Z0-805" published by Apress in February 2013 and the second book "Refactoring for Software Design Smells: Managing Technical Debt" published by Morgan Kaufmann in November 2014. He is an IEEE Senior Member. His twitter handle is @Sharma__Tushar

Ganesh Samarthyam has more than 12 years of experience in the IT industry. He is a consultant with an IT services start-up ZineMind, Bangalore, India. Earlier, he worked for the Software Architecture and Development team in Siemens Corporate Research & Technologies in Bangalore. His work involved providing consultancy to development teams on code and design quality, pursuing applied research in the areas of software design, and conducting trainings on topics related to software design and refactoring and quality-driven development. Prior to Siemens, he worked in Hewlett-Packard's C++ compiler team for 5 years where he also represented HP in the ANSI/ISO C++ standardization committee. He is an IEEE-certified Software Engineering Certified Instructor (SECI) and regularly conducts training for the IEEE SWEBOK Certificate Program (SCP) and IEEE Certified Software Development Associate (CSDA) program. He has also helped contribute course material for the IEEE's SWEBOK Certificate Program (SCP). Ganesh has authored/co-authored several books on programming. His twitter handle is @GSamarthyam

Girish Suryanarayana is currently a Senior Research Scientist at Research and Technology Center, Siemens Technology and Services Pvt. Ltd. Bangalore, India. At Siemens, he is involved in providing architectural guidance to software development teams, pursuing research in topics related to software architecture and security, and conducting internal software design and architecture training. Girish is a member of the IEEE Software Advisory Board. He actively contributes to software engineering conferences. He was the General Chair for the IEEE Software Experts Summit 2014 conference which was held in Bangalore, India for the first time. In 2013, he was on the program committee for the Software Engineering In Practice (SEIP) track at the 35th International Conference on Software Engineering (ICSE). Girish received a PhD in Information and Computer Science from the University of California, Irvine, in 2007. His twitter handle is @girish_sur

Rate this Article

Adoption
Style

Educational Content

BT