Preamble
Martin Fowler’s Refactoring is a catalog of safe moves—rename, extract, move method—backed by a safety net of tests. I treat code smells as signals, not insults: long methods, feature envy, divergent change, shotgun surgery. May is the month I schedule refactors before the next feature makes the mess existential.
Smells as navigation
Long method often means missing named steps; extracting functions documents intent. Feature envy—a method that cares more about another class’s fields than its own—suggests move method. Divergent change (one class edits for many reasons) hints at splitting responsibilities along use-case lines.
Tests as guardrails
Without tests, refactoring is edit and pray. Characterization tests (Test Doubles at System Boundaries, Feathers-style) lock behavior you do not yet understand fully. With tests, refactoring is mechanical—small steps, green bar, commit.
Layer alignment
Smells often trace to layer violations—Architecture for Evolvable Services After Polyglot Expansion is the adjacent read on boundaries once multiple runtimes share a system. Moving persistence details behind repositories removes “SQL in the service layer” odor at the source.
Conclusion
Refactoring is risk management for the next concurrency or benchmarking experiment—not vanity. Test Doubles at System Boundaries discusses test doubles at those same boundaries.