Each developer wants to have a clean code, easily readable and maintainable and with a few issues and bugs. And there’s no magic solution to achieve this goal. Each company has its own best practices and coding rules and try to define a process to keep the code very clean.
It’s not an easy task to measure the code quality of a project, many tools provide their algorithms to evaluate it depending on many factors:
- Issues detected by the static analysis tools.
- Code coverage.
- Code duplication.
- Lack of design.
There’s a metric that gives us an estimated value to have an approximative whole view of our code base quality. It’s the technical debt metric.
From wikipedia we can discover a brief explanation of the technical debt:
Technical debt (also known as design debt or code debt) is “a concept in programming that reflects the extra development work that arises when code that is easy to implement in the short run is used instead of applying the best overall solution”.
Technical debt can be compared to monetary debt. If technical debt is not repaid, it can accumulate ‘interest’, making it harder to implement changes later on. Unaddressed technical debt increases software entropy. Technical debt is not necessarily a bad thing, and sometimes (e.g., as a proof-of-concept) technical debt is required to move projects forward. On the other hand, some experts claim that the “technical debt” metaphor tends to minimize the impact, which results in insufficient prioritization of the necessary work to correct it.
In theory, it’s very promising to deal with the technical debt to improve the software quality, but in practice, it’s not easy to use it, indeed the big challenge is how to evaluate the technical debt?
And whatever the tool or the method used to evaluate it, it must be flexible and easy to customize. The company must have the possibility to calibrate its algorithm depending on its context. Indeed one team could tolerate a method with more than 50 lines of code and another could choose 30 as a maximum.
An agile algorithm to the rescue
There are two options to make the debt calculation flexible:
- Define a specific algorithm and give the possibility to change its parameters depending on the development team context.
- Not define a specific algorithm and give to the user a way to customize its calculation formulas.
With CppDepend we choose to make the algorithm flexible and it could be changed for each rule depending of the project context.
For example here’s a formula for the debt introduced by too big types:
And here’s another formula for a cppcheck issue
This way each team could configure their debt calculation depending on the project context and they have the possibility to reduce the estimation errors of the debt calculation.
The comparison with a baseline
It’s very difficult to evaluate the technical debt, each algorithm used will introduce many estimation errors and we do not have much time to calibrate it, it depends on many factors.
However, if we compare the technical debt of two iterations of a codebase we can have a good idea about the evolution of its code quality.
The difference between the debt metrics of two versions will minimize the estimation errors and give more accurate debt metric.
Trends to track the evolution
Concepts like technical debt help quite a bit. But nothing hits home like a visual.
For instance, you might want to look at average cyclomatic complexity and lines of code per method. Generally speaking, you would expect these figures to remain relatively flat (and low) in a codebase. You could use a trend chart to confirm this and keep tabs.
Does the trend line stay pretty much flat, with a little uptick or downtick here and there? Or does it trend slowly but steadily upward? Observing a trend like this can help you catch an issue much earlier than you otherwise might. Whenever I see a codebase with heinous method complexity, I understand that nobody went in and made it that way in an afternoon. It took years of not noticing a general, gradual trend.
The technical debt metric is a powerful way to control the code base quality. However, the user must have an easy way to calibrate it and reduce the estimation errors. And it’s more interesting to rely on the technical debt evolution than the debt itself.