Productivity2023-10-04

Low Quality Code: The #6 Developer Productivity Killer

Discover how low quality code silently erodes developer productivity. Learn best practices to supercharge code quality. Explore now!
How poor code quality kills developer productivity

There's nothing that impacts your bottom line as severely as poorly written code. With $3 trillion GDP loss stemming from workflow inefficiencies, and millions of dollars drained away in patching software vulnerabilities, engineering teams are only just beginning to realize the impact of low quality code.

Poorly executed code can drain the productivity of the engineering team, and even the usability of software. Moreover, low code quality also reflects ineffective team communication, poor team collaboration, and is the starting point of incurring humongous technical debt.

I am not surprised promoting code quality is the first step software engineering teams can take towards improving developer productivity, and the overall bottom line of an enterprise.

In this article, let's talk about the importance of code quality, impacts on engineering productivity, and then zero in on actionable ways to improve it.

The Anatomy of Bad Code

On the development front, code quality translates to creating a reusable, and maintainable codebase. A reusable code might be used just once, but is read a thousand times– to fix bugs, discover patterns, add next functionality, or remember how the product works.

Now think about losing all these benefits just because you underestimated code quality, or put it in the backseat of your engineering efforts. Code quality is subjective, and sometimes harder to define, but here are some common patterns across engineering teams that show how a low quality code looks like:

  • Presence of code smells that usually stem from lack of readability. A readable code is performant, and saves time so no developer has to build a codebase from scratch (always). 
  • Long methods that make your code stretch from 200 LoCs to a mile– Hard to read, and harder to maintain. 
  • Non-idiomatic code written without syntax, indentation, and full of backtracking. 
  • Absence of meaningful, specific, and contextual variable names to make things easier for a developer reading, and reviewing your code. Using “fn” over “employeeName’’ provides no insight, or context into the purpose. Moreover, shifting between different naming conventions within the same codebase is another metric to measure your code quality. Using camel case in your 1st line, and underscore case in the middle is a sin. 
  • Low quality code and high cyclomatic complexity are directly related. Cyclomatic complexity communicates higher decision points, loops, and branches, making it harder to maintain the code, or to understand, and debug it.
  • Breaking existing functionality everytime a new change is added.
  • Unintelligible flow, tight coupling, and low cohesion
  • Overuse of design patterns makes the code look more bloated, and harder to maintain.

Decoding the Culprits: Top Causes of Low Quality Code

Dealing with low code quality repeatedly? Here are your culprits:

1. Coding Without Planning, and Standards 

One of the primary culprits behind low-quality code is a rush to start coding without caring for planning and design. Skipping or giving short shrift to requirement analysis and system design can set the stage for code riddled with issues. This happens when teams either over architecture, or follow bad-design principles.

Without a clear architecture, teams resort to shortcuts, creating a tightly coupled, tangled, and spaghetti-like code that's tough to understand and maintain. Besides, moving without planning often creates code that doesn't scale well. As the project grows, so does the complexity of maintaining and extending it.

Another issue plaguing your code is a blatant disobey of coding standards. Most devs are overworked- they keep lights on, have to manage incidents irrespective of work hours, and code under tumultuous pressure of uneven demands, and tight-packed deadlines. In such a case, ignoring coding standards to deliver on time becomes a way of life for most devs.

Ignoring coding standards is like driving in the Wild West of code. When every developer follows their own style, the codebase becomes confusing, and inconsistent, causes readability issues, and maintenance nightmares.

2. Lack of Tech- Business Alignment

Nothing holds your engineering team back than lack of alignment. Competing vision, frequent scope creep, and rushed development can often put devs on the edge; even coercing them to change the way they build, and code.

As the business side revises its requirements or priorities, development teams have the pressure to continually adapt. The other times, we overstretch ourselves after looking out for future requirements even when customers are not asking for it. And when things don’t pan out, teams often end up building products that were neither needed nor desired in the first place.

All of these factors put devs on spots, and impact the code they write– often adding inconsistencies, complexity, and lack of shared ownership of the codebase.

3. Unrealistic Deadlines, and Over pressured Devs 

Deadlines are not antithetic to software development; rather they are crucial to manage production costs, and help engineering teams achieve their goals. However, these deadlines start killing productivity of your team when they come with clogged calendars, back-to-back meetings, and less active coding time for devs– which is just 1 hour a day as of now.

Managing engineering deadlines is a make-or-break point for most dev teams. And 40% of devs agree with it. They ignore quality checks, resort to quick fixes and hacks to just deliver on time, and achieve their timelines. This rushed development then spirals into low quality and poorly executed code.

4. The "Works-for-Me" Mindset

Imagine you're working on a group project, and someone casually quips, "It's working like a charm for me; the issue must be something of yours." Pretty frustrating, right? Well, this mindset is the perfect recipe for disaster for engineering teams.

Devs, under pressure of deliverables, and an overworked schedule sometimes overlook the fact that different environments exist. Their code might run seamlessly on their own setup but stumble elsewhere.

This nonchalant approach often leads to compatibility issues and persistent bugs that just won't go away, often creating a loose feedback cycle and low quality code. 

5. Accumulating Enough Technical Debt For a Lifetime 

Technical debt isn’t interest-free. It charges humongous interest in the form of complex code– It's not just complex; it's "how-did-this-even-work-in-the-first-place" complex.

Moreover, the “fix it later” approach often comes at the expense of documentation, frequent bugs, and even high software development costs to rise in the long run. The longer it lingers, the more resources, and code integrity it siphons away, leading to timeline nightmares, and exhausted developers, and a compromised codebase.

It also distorts the active coding time for devs. As of now, they are focusing 42% of their time in resolving technical debt– a blatant wastage of resources, and even loss of ability to code on parts of developers.

Unpacking the Price of Low Quality Code– The Toll on Engineering Teams and Bottom Line

Subpar software has cost organizations more than $2.8 trillion in the States alone. Here are a few more shocking impacts of low quality code on developer productivity, and the financial health of an enterprise:

1. Engineering Woes, and A Never Ending Developer Toil 

It’s no rocket science to decode how a dev’s mental state can hinder their ability to code, and vice versa. Sufficient rest, no burnout, low stress levels, and happiness– all of these impact how a dev delivers code, and build software.

A poorly written code adds to the miseries of already overworked developers. The daily grind creates a vicious cycle of debugging- maintenance nightmares- technical debt for developers, even propagating the ‘always on’ culture, and longer work hours.

We know a lot of devs who code even when they are tired, long past the office hours, and then discovering later that the work was discarded, because either it was not enough, or had to be undone. The “net-negative work” actually creates, and stems from low quality code all at once– even expanding the amount of work to be done, and sometimes starting from scratch.

Demotivated developers are less likely to invest their best efforts in a project. Nothing can compensate for this developer toil– neither sabbaticals, nor a well-brewed beer, nor micro-napping.

2. Less Active Code Time 

A dev's overall productivity takes a hit when they are dealing with low quality code. They now have to put deciphering code and fixing issues than on actual development work.

Didn’t we just mention how devs have only an hour a day to code, while they have to spend 42% of their time fighting bugs, and resolving technical debt. Besides, lack of validated and reviewed code creates strong regressions while devs rework the codebase. The need to address regressions consumes active coding time that could have been spent on building features.

What could have been a straightforward task becomes a marathon of tracing, testing, and fixing. Moreover, code that lacks readability and structure is a ticking time bomb. It demands frequent maintenance as requirements change or as new features are added. All of this interrupts devs flow state, where they are unable to concentrate, and deliver beautiful, and strong code.

3. Frequent Speed Bumps Derailing Engineering Velocity

For long term projects, extending beyond 2 weeks, code quality is a major deciding factor for optimal development speed.

With a badly executed code as your sidekick, it becomes hard to answer questions like– how frequently your team ships? Or, what is the failure rate?

It’s not that devs don’t work hard enough. The stigma is far from real. Rather they are too overwhelmed with bugs, to work on the roadmap.

Poorly documented or convoluted code creates knowledge silos, where only a few team members understand how it works, while most ICs settle with tribal knowledge. This reliance on a select few experts slows down engineering velocity and blocks developers in doing their core work.

Besides, ill-designed and tightly coupled code modules are less reusable. In such cases, teams have to reinvent the wheel instead of building upon existing, reusable components, making engineering super hard to scale.

4. The Crisis of High Software Development 

Let’s talk numbers here– the language every business irrevocably understands:

  • According to Stripe, the toll from 'bad code' has already reached staggering losses of up to $85 billion annually.
  • Vulnerabilities sneak in when code quality is compromised. Based on Contrast Security's research running checks on 8 billion lines of code, a typical modern application has 79% library code and just 21% custom code. Predictably, 76% of these applications harbor at least one vulnerability, while 34% have ‘very high’ chances of breach.

PS: Interested in knowing more about high development costs and its intricacies? Check out our latest post on Linkedin.

These numbers are independent of shipping costs of bad code, or being defeated to market by your rivals– they too are worth considering; howsoever hidden they are. No matter how competent your product vision seems, it WILL struggle when prone to bugs, and hacks.

Do we need anymore proofs into how low quality code can severely impact your bottom line, and even kill your business.

Conquering Low Quality Code: Strategies That Work in Both Letter and Spirits

Consistently delivering good code requires investment, and commitment of resources- a developer’s coding abilities, money, easing deadlines, and development time

But, the good news is– Building software that stands the test of time doesn’t require teams to cease their other engineering activities. Rather, the refactoring is about taking subtle, but consistent steps. Here we are discussing the strategies that are evergreen, yet underrated in building high-quality code: 

  • Streamline your developer’s workload using engineering analytics. Visualize your IC’s workday in terms of efforts distributed: bugs vs roadmap vs technical debt. The best way forward is to work with them in optimizing their schedule so they can have active coding time, and deliver real value.
  • Generally, engineering managers can redistribute work based on the 80:20 rule– with 80% time reserved for building features, or fixing bugs, while 20% is kept for refactoring, so teams can also tackle technical debt head-on.
  • The second point of action is pair programming and effective code reviews. Going solo might be a regular devs way to get work done, but studies have shown how working together on a single codebase can improve its vitality, and overall productivity of everyone involved. Code reviews are the last leg to finally ship your code to production, also it's the last opportunity to catch any quality errors that can later damage your product. 
    Engineering teams can find the real-value out of their tight review cycles by using Hatica’s collaboration dashboard.
Review collaboration dashboard from Hatica

With all review progress at a single, centralized pane, teams can collaborate in real-time, remove blockers that might have caused the code to rot, and effectively deliver high-quality code together.

Moreover, the dashboard also offers visibility into PR hygiene, including size, and number of unreviewed PRs that are merged and currently wreaking havoc on the overall software quality.

By tracking PR changes, engineering teams can rework, and review hassle-free. Also, ensure the PRs passes some build tests before you merge them to the master branch.

  • The next practice is the dark horse of building high-quality software, and often the simplest one too. As Martin Fowler says, “Good programmers write code that humans can understand.” Readable code is not some secret sauce to exceptional products; rather it should serve as a solid, and compulsory foundation to all crafted software products.
  • Write code with clear intent, and follow the single responsibility principle. Mark classes, variables, and methods carefully so someone reading your code for the first time can exactly tell what the method does just by calling out its name.
  • Follow the "Don't Repeat Yourself" principle. Reuse code through functions or classes instead of duplicating it.
  • Add comments that explain why you are doing something, not just what you are doing. This helps others (and your future self) grasp your thought process.

Improving code quality doesn’t have to be painful. Rather it is an opportunity for engineering teams to resolve their differences, and come together in building a solid foundation to the overall development process, even altering the way they function, and deliver products.

The real quality improvement comes when teams are proud of code they generate, and they believe in creating something with solid structural integrity.

Final Thoughts: Escape the Grip of Low-Quality Code 

Historically, businesses have focused on speed as a marker for project success– The faster the delivery, better the outcomes, with satisfied customers. However, times are changing. Engineering teams are realizing the shortfalls of velocity as the success metric, and how it impacts engineering efforts in the long-term.

High code quality is the quickest way to value delivery today.

Well-executed code protects your software from downtime, crashes, and bugs that might have otherwise derailed the overall customer experience. In the long-term, your software quality also protects the overall brand equity of a product. You know what they say- one crash, and years of good work is lost!

Prioritizing a healthy codebase means prioritizing your customers, your engineers, and even protecting your bottom line. Investing time in writing high quality code will pay huge dividends in the long-run, even till the code itself reaches the end stages.

Subscribe to the Hatica blog to stay updated with more engineering insights!

Subscribe to Hatica's blog

Get bi-weekly insights straight to your inbox

Share this article:
Table of Contents
  • The Anatomy of Bad Code
  • Decoding the Culprits: Top Causes of Low Quality Code
  • 1. Coding Without Planning, and Standards 
  • 2. Lack of Tech- Business Alignment
  • 3. Unrealistic Deadlines, and Over pressured Devs 
  • 4. The "Works-for-Me" Mindset
  • 5. Accumulating Enough Technical Debt For a Lifetime 
  • Unpacking the Price of Low Quality Code– The Toll on Engineering Teams and Bottom Line
  • 1. Engineering Woes, and A Never Ending Developer Toil 
  • 2. Less Active Code Time 
  • 3. Frequent Speed Bumps Derailing Engineering Velocity
  • 4. The Crisis of High Software Development 
  • Conquering Low Quality Code: Strategies That Work in Both Letter and Spirits
  • Final Thoughts: Escape the Grip of Low-Quality Code 

Ready to dive in? Start your free trial today

Overview dashboard from Hatica