Ipek Ozkaya gives a typical, representative example of a Technical Debt accumulation case in “Does principal really exist in technical debt?”: a project development team selects a particular application framework at the start of the project and while going deep into the implementation phase realizes the framework does not fit part of the project needs and/or causes redundant work to mitigate framework related risks or compensate of its deficiencies. The question arises: should the framework be replaced or kept in place given the amount of work to replace it including functionality rework, integration, learning efforts, risks introduced by the new framework selection, etc.
Let us look at the possible root causes of the technical debt at hand located at the early stage of the project when the framework selection is originally done:
- Functionality to be developed on top of the framework is not sufficiently defined by the analyst, product owner, UX designer.
- Relevant quality attributes such as maintainability, performance, interoperability, maturity, and other ones important for framework selection are not well understood.
- Important constraints such as familiarity of the framework to the team or overall level of competence/ability to work within provided features, patterns, and paradigms, and others are not accounted for.
- The framework is selected without proper consideration of the above architectural drivers, or driver prioritization is not done right, or drivers contradict to each other too much. Frequently, simple prototyping or even involvement of a knowledgable expert might have prevented a poor choice.
- Even if the above drivers are collected, analyzed, and the best effort is made to select the most fitting framework the market state does not allow to choose the framework accommodating all of the high priority drivers. Such a framework might not exist or have prohibitive licensing terms, etc.
- Finally, the nature of software development business might cause requirement changes in such a way the framework cannot properly address anymore. For instance, the approach to UX is changed so much it does not match patterns supported by the framework anymore.
In practice, some or all of the items in this range might happen and critically affect the framework choice. Retrospective analysis can often reveal which of them had a place in reality. The main point here is that poor framework selection is an objective event and at the same time calculation of the attached Principal is conditional. What should it include:
- Reluctance to allocate a business analyst for two weeks to analyze system requirements?
- Decision to save money on the licensing fees for the optimal choice and to go with the suboptimal open source candidate?
- 2 days unspent on the deeper verification of the framework candidates and prototyping for them?
- Incompetence of the involved architect who selected the framework based on “Coolness” instead of “Maturity”?
- One of a thousand of other possible reasons to make a bad decision?
Next, development starts and technical debt starts invisibly mounting with each new piece of code developed on top of the selected framework. The further the dev team goes into work the more apparent the issues grow and the more effort it would potentially take to re-make the decision did the team decide to do so. When does the “first responsible moment” happen, the moment when the evidence of the poor choice becomes visible and the amount of technical debt is not too high to pay it in full?
Lastly, at a certain point of development timeline the decision maker is faced with two strategical options:
- Replace the framework and refactor the system implementation accordingly.
- Keep the framework and learn to work around its deficiencies based on the already acquired practical knowledge of its internals and peculiarities.
In the first case we would obviously include into technical debt estimation much of the effort spent on the original implementation and all the effort to reimplement it for the framework replacement. One additional contributor is higher risks associated with making a new ground breaking architectural decision so late into the development and close to the release.
In the second case we do not include the second type of effort and should be more careful with the first part. Likely we would only count extra effort we have not had spent on implementation if we had chosen a different (reference) framework from the very beginning. We would also pay this debt differently from the first case.
Hopefully, this discussion shows we can hardly speak of Principal and Interest associated with technical debt as single values or simple time-dependent formulas. They are rather complex functions of multiple variables, some of them being subjective.
In this context I see the technical debt framework, most significantly, as a decision support toolset which allows estimating and comparing technical debt variants based on the combinations from space of the variables like above.