How do you prioritize technical debt vs. new features
Treat it as a portfolio: features deliver visible value; debt delivers velocity. Make debt visible (a backlog of cards with cost and impact, not abstract grumbling); attach debt to feature work when possible ('paying down to ship the new thing'); allocate a steady fraction of capacity (~20%) as ongoing maintenance; escalate when debt actively harms users or shipping speed (the 'unable to deploy on Fridays' moment).
Tech debt vs features isn't a debate to win — it's a portfolio management problem. Treat it that way and you stop arguing in abstractions.
1. Make debt visible
Most "we have so much tech debt" conversations are vague. The fix: convert debt into tickets with explicit cost, impact, and effort.
- "Build pipeline is flaky — 1 in 5 PRs needs a re-run" → ticket with the failure rate, dev-hours lost weekly.
- "Auth context re-renders the whole app on token refresh" → ticket with the rendering profile and INP impact.
- "Three different date utilities in the codebase" → ticket with the bug history caused by inconsistencies.
Vague grumbling has no priority. A ticket with numbers can be ranked against a feature.
2. Attach debt to features
The most efficient time to pay down debt is when you'd touch the code anyway. "Adding the new dashboard widget needs us to factor out the chart wrapper" — fine, that's part of the feature, not separate.
This avoids the "debt sprint that gets cut for the feature deadline" trap.
3. Allocate a steady fraction
Pure feature work without ongoing maintenance compounds debt until velocity collapses. Allocate ~20% of capacity to ongoing tech work:
- Test-coverage gaps for recently shipped features.
- Lint/CI/build fixes.
- Refactors that pay off mid-term.
A steady tax is much cheaper than periodic "debt sprints" — and the team's velocity stays predictable.
4. Escalate when debt harms users or shipping
Some debt isn't just slowing you down — it's causing user pain or shipping failures:
- Incidents recur on the same surface.
- Engineers refuse to deploy on Fridays because the system is fragile.
- A class of bugs keeps hitting users despite repeated patches.
When debt graduates from "annoying" to "actively damaging," it's no longer a tradeoff — it's an emergency. Escalate with the impact data.
5. Frame in terms PMs/leadership care about
- Time saved — "this refactor cuts the average PR review cycle from 2 days to 1."
- Risk reduced — "this rewrite eliminates the class of bug that's hit prod three times this quarter."
- Velocity unblocked — "we can't ship feature X without paying down Y."
- User impact — "fixing this saves users 3s of LCP on mobile."
Avoid the engineer-internal pitch ("the code is ugly"). It rarely resonates.
6. Distinguish debt categories
Not all debt is equal:
- Velocity debt — slows new work down. Pay down opportunistically.
- Risk debt — could cause an outage. Prioritize aggressively.
- User-facing debt — perf, accessibility, UX inconsistency. Treat as a quality feature.
- Aesthetic debt — code style, naming. Lowest priority — usually fix in passing.
7. The "ship blocker" argument
When a feature literally can't ship without resolving debt — say so plainly. "We can't add per-user theming on top of the current CSS architecture; here are three options and their estimates." That's not arguing for debt, it's specifying the work.
8. Avoid the failure modes
- Big-bang rewrite proposals — almost always lose to incremental work that ships value sooner.
- Debt sprint that gets cut — when the deadline tightens.
- "Just a refactor" PR with no clear outcome — a refactor without a measurable goal is hard to defend.
- Hoarding cleanup tasks for "later" — later never comes.
Interview framing
"I treat it as portfolio management, not a debate. First, make debt visible — convert it from grumbling into tickets with cost and impact (dev hours lost weekly, INP regressions, incidents on this surface). Second, attach debt work to feature work when possible — the cheapest time to refactor is when you'd touch the code anyway. Third, allocate a steady fraction of capacity to ongoing maintenance — ~20% — so debt doesn't compound. Fourth, escalate when debt actively harms users or blocks shipping — that's no longer a tradeoff. The pitch always lands better in business terms: time saved, risk reduced, velocity unblocked, user impact. Big-bang rewrites and 'debt sprints' usually lose; incremental, opportunistic work that ships value alongside cleanup wins."
Follow-up questions
- •Give an example of debt you successfully prioritized and how you sold it.
- •How do you avoid the 'debt sprint that gets cut for the deadline' trap?
- •When do you say 'no' to a feature because of debt?
- •How do you measure tech debt?
Common mistakes
- •Vague 'we have tech debt' without specifics.
- •Pitching to leadership in code-quality terms instead of business terms.
- •Big-bang rewrite proposals.
- •Hoarding cleanup for 'later'.
- •Letting debt sprints be the first thing cut under deadline pressure.
Performance considerations
- •N/A — process question.
Edge cases
- •Product/engineering disagree on whether something IS debt.
- •External deadline that makes pause-for-cleanup impossible.
- •Legacy system maintained by a different team.
Real-world examples
- •20% time policies (Google, others).
- •'Fix-it Fridays' or rotating debt-paydown rotations.
- •Quality KPIs in OKRs (perf, accessibility scores).