Skip to content
#software-development
#founders
Security

Technical debt is a security exposure: what to fix first

Technical debt left the sprint queue and became exposure: old code is the first thing an automated scan reads. Three measures before anyone refactors.

Por Victhor Araújo

Founder of Revin. Engineer by training, specialist in software development and digital products.

The file nobody has opened since 2011 still answers anyone calling from outside.

The file nobody has opened since 2011 still answers anyone calling from outside.

Technical debt is a security exposure now: the scan reads your old code before your team does

A colourful dashboard on empty data is the expensive part: you spend months believing you are covered.

A colourful dashboard on empty data is the expensive part: you spend months believing you are covered.

Technical debt left the sprint queue and moved into the company risk register. Until recently, that 2011 file nobody opens was a scheduling problem: it slowed the new screen, annoyed the team, came up in the retro and went back to sleep in the backlog. Today it is the first place an automated scan walks into, and that scan runs in minutes, every day, without getting tired.

The practical answer, before the argument: list the parts of your system the outside world can reach that have barely changed in three years, find out which of those have tests that actually assert something and errors that reach a human who is awake, and only then talk about refactoring. In that order. Refactoring before those two answers is painting over a wall with water coming through the back.

Forty years of debt arrived in the same month

An IEEE Spectrum piece arguing that AI is forcing us to pay off 40 years of technical debt hit 1,309 points and 750 comments on Hacker News. Anyone who reads that site knows those numbers are not routine. That is the volume you get when a lot of people recognise their own system in the description and scroll down to say so.

The mechanism is simple and uncomfortable. What protected your old code was never its quality. It was the cost of looking. Auditing a few hundred thousand lines of a system frozen since 2014 used to burn weeks of expensive people, so nobody looked, neither your team nor anyone trying to get in. That cost now runs on a monthly subscription. The debt did not grow. The price of finding it collapsed.

The measurement question is not new either. On Stack Exchange, the question about quantifying technical debt in a project has passed 20,000 views, and the one about convincing management to deal with it holds 176 points and close to 19,500 reads. Engineering has been asking for over a decade, spreadsheet included. What changed is who asks alongside them: the cyber insurance questionnaire, the enterprise customer who sends a security review before signing, and now a tool that scans on its own and needs nobody's approval.

If you have to take this to a board meeting, put it in three columns: what the business loses if that piece stops for a day, what it costs to fix now, what it costs to fix after an incident. That is the difference between a developer complaint and a number a CFO can act on, and it is also how you measure the bill your coding agents are running up.

Your old debt also degrades your AI

The priority queue comes out of one afternoon looking at the running system, not the repository.

The priority queue comes out of one afternoon looking at the running system, not the repository.

InfoQ reported this week that Google engineers described an effect they call agent distraction. A coding agent dropped into a debt-heavy repository gets derailed: a TODO comment from 2017, a reference to a bug closed years ago, a stale spec that contradicts the code right next to it. The agent reads that as instruction and wanders off on side quests nobody asked for.

Keep that part, because it bills you twice. The same mess that exposes you from the outside eats the return on the tool you bought to go faster on the inside. And plenty of that mess is not in the code at all. It lives in what only two people know, the cognitive debt nobody puts on a board. A stale spec is cognitive debt with an official stamp on it.

"We'll clean it up when a sprint frees up"

I said that sentence in nearly every product meeting at my first company, a marketplace for renting construction equipment. I hired developers without being able to judge their answers, and I treated technical debt as a team preference, something people wanted because they liked tidy code. What I could not see is that the queue never frees up. A sprint frees up exactly zero times. And the thing I kept pushing became the reason a pricing rule change later cost three weeks.

I am on the other side of the counter now, and the same sentence shows up in my inbox, written by founders who are not wrong to believe it. The villain is not the team and not whoever is on call. It is the contract. Fixed price with no continuity built in rewards a vendor for shipping a pretty shell and walking away, because the maintenance bill lands on somebody else's desk. When the incident arrives, the phone that rings is yours. I have written about paying for the same feature three times, which is how that contract usually ends.

Tests that assert nothing, monitoring that instruments nothing

In the rescues we take on after a dev shop walks out, three things show up almost every time: a slow query chained to another slow query, high test coverage with no assertion inside the file, and monitoring that is a health endpoint returning 200 without touching the database, with a colourful dashboard sitting on top of empty data.

That is quality theatre. The metric exists, the guarantee does not. And the expensive part is not the hole itself, it is the months you spend believing you are covered. From what I see, something like 40% of a squad's first month inside a system like that goes purely into learning what it actually does when a user presses the button. I once opened a codebase where the most important process in the business ran on a scheduled job that existed on one person's laptop and not in the repository. Back to the point: before fixing anything, we count how many errors happened yesterday, on which routes, for how many customers. That is also the fastest way to run a 30-minute audit on a vendor.

Three measures before anyone opens an editor

  1. Reachable surface: list every route, form, upload and integration that accepts a call from outside, and match each one against the last modification date of its file. Anything exposed and untouched for three years goes to the front of the queue, even if the code looks harmless.
  2. Real verification: take the three most critical files on that list and break a rule on purpose. If no test turns red, your coverage is a reporting number and you are deciding in the dark.
  3. Owner and alert: next to each item, write a person's name and the channel where the error shows up. Debt with no owner never enters any queue, it just comes back at 3am.

None of that requires buying a tool. It requires one afternoon and someone allowed to look at the running system instead of the repository.

Not every debt is worth paying

A client once asked whether moving MySQL 5 to 8 was the same job as moving to Postgres. Those are two different line items wearing the same clothes. A version jump inside the same engine is usually weeks of work with mapped risk. Swapping the database is a new project, with data migration, rewritten queries and a team learning on the way. If someone gave you one estimate for both lines, someone guessed.

And I almost never approve a rewrite from scratch, for a boring reason: a rewrite hands you back the system you already had, months later, with new bugs and the same business rules nobody ever wrote down. I will admit the limit of that advice. I cannot tell you it holds for a two-person engineering team on a few thousand lines of code. There the maths can land the other way, and I have seen it land there.

The question for Monday's meeting

The scan is already running and it will not wait for your quarterly planning. So ask two questions at the next status meeting: which part of our system serves people outside the company and has not been touched since 2021, and who gets alerted when it fails?

If either answer takes more than a day to arrive, your technical debt has already left the engineering agenda. It is on yours now, and someone else is setting the due date.

Ready to elevate your business

Schedule a meeting
Share
Link de compartilhamento LinkedinLink de compartilhamento XLink de compartilhamento WhatsappLink de compartilhamento Facebook

Newsletter

Every two weeks. The technical decisions we made, and what we learned.