# Keep Tech Debt Below 10% Is Easy — Here’s How

Technical debt eats 40% of IT budgets ($85B globally, Forrester 2025), slowing delivery and threatening entire businesses. In Java’s Spring-heavy ecosystem, where logic sprawls across services, even minor changes become high-risk operations. Yet keeping debt below 10% is not only possible — it’s straightforward with richly modeled object-oriented (OO) development.

Unlike recipe-driven frameworks like Spring Boot, where technology defines structure, rich OO puts *understanding first*. It captures business intent in objects, making code readable, evolvable, and safe to change. Over decades of work on 50+ to 200+ entity systems, I’ve consistently kept technical debt between **2–4%**, proving that low debt isn’t luck — it’s design.

---

### **Recipe-Driven Development: Tech-First, Revolution by Default**

Spring Boot (used in 62% of Java projects, JetBrains 2025) is the poster child of *recipe-driven* development. It encourages developers to wire services, sprinkle annotations, and “get something running” within days. For small CRUD-style apps (0–20 entities — think users, products, orders), this works brilliantly. A medior team can deliver 80% of the needed functionality six times faster than a hand-crafted model (Gartner 2025).

But the tradeoff is structural: logic lives in scattered services. A simple rule — say, applying a TTL to S3 storage — ends up spread across StorageService, ConfigService, and Scheduler. No single class owns the behavior. Technology dictates the flow; business logic becomes fragmented and invisible.

At first, it feels productive — everything compiles, tests pass, dashboards are green. But every new feature or version upgrade becomes a **revolution**: multiple files, ripple effects, regression risks. Upgrading to Spring 3.0 breaks 25% of projects, requiring 2–4 weeks of rework (JetBrains 2025). What started as “fast delivery” slowly turns into “permanent firefighting.”

This is the trap: recipe-driven development optimizes for *starting fast*, not *staying fast*. The cost of every future change rises with time.

---

### **Richly Modeled OO: Business-First, Evolution by Design**

Rich OO reverses the premise. Instead of asking, “How do I wire this up?” it starts with “What does this object *mean*?”

Take the same S3 example from my earlier article. Rather than sprinkling TTL logic in services, you design a ProcessBucket object. It knows how to store() and remove() items, encapsulating its own lifecycle rules. Technology (the AWS SDK) becomes an internal detail. The *what* and *why* are clear: this object exists to manage transient storage.

When you later add encryption, you evolve the ProcessBucket—no revolutions, no regressions. The design grows naturally. This is *evolutionary change*: self-contained, predictable, low-risk.

Rich models make the domain explicit. The code mirrors the business: Order.fulfill() calls Inventory.reserve(). Everyone—developers, testers, analysts—can read and reason about it. Mistakes become harder, maintenance cheaper.

---

### **The Evolutionary Advantage: Understanding Before Implementing**

Recipe-driven teams tend to start coding as soon as a feature is described. OO teams start by *understanding* — by modeling. This up-front clarity feels slower but pays back immediately: cleaner boundaries, simpler changes, and faster onboarding.

In complex domains (30–100+ entities), this difference explodes. A 3-person OO team often outpaces 10 mediors in long-term delivery. Not because they type faster, but because they *retype less.* Their systems evolve rather than break. Over time, the “slow” team becomes exponentially faster.

It’s a quiet revolution of its own: **evolution replaces rework.**

---

### **The Twist: When Simplicity Stops Scaling**

For simple applications, recipe-driven development remains practical. Small systems don’t justify the modeling overhead, and mediors can produce results quickly. But as complexity grows, the lack of clear ownership in code turns every change into a rewrite.

At around **20–30 entities**, complexity reaches a tipping point. The OO approach — explicit modeling, clear responsibility, minimal layers — becomes cheaper and faster *in total cost of ownership*.

A small, experienced OO team can maintain and extend systems with 2–4% debt, while larger recipe-driven teams sink into 30–40%. Over a few years, the compounding cost of rework makes the “cheap” approach the most expensive one in the building.

---

### **Conclusion: Evolve, Don’t Revolve**

Keeping technical debt below 10% isn’t about heroic discipline. It’s about designing systems that *want* to stay clean.

Recipe-driven development produces revolutionary change — frequent, painful, and expensive. Rich OO models evolve: small, continuous improvements that preserve clarity and intent.

The key is understanding before implementing. Model the business, not the framework. Start with one object — define its responsibility, make it own its logic, and let that principle scale.

Do that consistently, and tech debt drops to 2–4% naturally. The codebase becomes self-healing, maintainable, and simple to grow. That’s not just sustainable speed — it’s sustainable sanity.
