Software Testing Best Practices

Chapter 2 · Practice 4 of 5

Prefer readable tests over clever, deduplicated ones

From Writing good unit tests

Why it matters

Production code should avoid repetition. Test code should first be easy to read, because a test is documentation that someone opens only when it fails. Fowler notes that readability matters in tests and that some duplication is acceptable when it makes a test clearer.

Practical rules:

  • Keep the important values in the test. If the assertion expects 108, the reader should see 120 in the same test, not in a shared fixture three files away.
  • Use builders or factories for boring setup. A makeUser({ role: 'admin' }) helper hides the 15 irrelevant fields and shows the one that matters.
  • No logic in tests. Loops, conditionals and computed expected values in a test can contain the same bug as the code. Write the expected value as a literal.
  • Refactor shared test code only when you see the same pattern three times, a rule of thumb Fowler calls the Rule of Three.

Avoid

  • Computing the expected value with the same formula as the code under test

Example

TypeScript
// Hard to read: where does 108 come from?
expect(applyDiscount(fixtures.orders[3])).toBe(expected[3]);

// Clear: the relevant input and output are both in view
const order = makeOrder({ subtotal: 120 });
expect(applyDiscount(order)).toBe(108);