Refactoring
01 / 02

Definition, Safety Net & Core Techniques

Definition, Safety Net & Core Techniques

The Definition That Matters

Refactoring changes internal structure WITHOUT changing external behavior. A bug fix or a new feature — even one that also reorganizes code — is not, strictly, a refactoring. This distinction is why refactoring is considered comparatively low-risk: the goal is explicitly to preserve behavior.

Tests as the Safety Net

A test suite gives a fast way to verify behavior actually didn't change after each step. When code has NO tests, write "characterization tests" first — tests that lock in current actual behavior, even if imperfectly understood — before refactoring, per Michael Feathers' legacy-code approach.

Small Steps

A sequence of small, individually test-verified steps makes it far easier to pinpoint what broke than one large sweeping change bundling many edits together.

Core Techniques

// Extract Method — pull a fragment into its own well-named function
function printInvoice(order) {
  const total = order.items.reduce((sum, i) => sum + i.price, 0);
  console.log(`Total: $${total}`);
}
// ->
function calculateTotal(order) {
  return order.items.reduce((sum, i) => sum + i.price, 0);
}
function printInvoice(order) {
  console.log(`Total: $${calculateTotal(order)}`);
}

// Replace Magic Number with Named Constant
if (status === 3) { ... }          // BAD — what is 3?
const STATUS_APPROVED = 3;
if (status === STATUS_APPROVED) { ... }  // GOOD

Rename Variable/Method is one of the highest-value, lowest-risk refactorings available — no logic change, meaningful readability gain. IDE-automated rename/extract commands are safer than manual find-and-replace since they understand actual references, not just text matches.

Keep your own version of these notes — editable, searchable, and organised by your stack.

Start free