Guard Clause Pattern
debt(d3/e1/b1/t3)
Closest to 'default linter catches the common case' (d3). The detection_hints list phpcs, rector, and php-cs-fixer — all standard PHP tooling that can detect deeply nested if-blocks and flag the absence of guard clauses as a style violation. The pattern `if (isValid()) { entire function body }` is mechanically detectable by these tools.
Closest to 'one-line patch or single-call swap' (e1). The quick_fix is explicit: invert the condition and return early at the top of the function. This is a mechanical, single-location change — invert the condition, add a return, and remove one level of indentation. Rector can even automate this.
Closest to 'minimal commitment' (b1). Guard clauses are a local style choice within individual functions. The tags (style, readability, refactoring, clean-code) and applies_to scope confirm this is a function-level pattern with no architectural reach or cross-cutting burden. Adopting or not adopting it in one function has zero effect on the rest of the codebase.
Closest to 'minor surprise (one edge case)' (t3). The misconception field reveals the trap: developers believe early returns make code harder to follow, when in fact they reduce cognitive load. This is a common but mild conceptual inversion — experienced developers recognise it quickly. The common_mistakes also note ordering and grouping subtleties, but these are minor rather than catastrophic.
Also Known As
TL;DR
Explanation
A guard clause validates a precondition at the top of a function and returns (or throws) immediately if it fails, before the main logic. This inverts the typical 'happy path wrapped in conditions' to 'early exits at the top, happy path at the bottom' — dramatically flattening code that would otherwise nest 4–5 levels deep. Guard clauses make the contract of a function explicit: the reader sees all invalid states first, then understands what normal execution looks like.
Common Misconception
Why It Matters
Common Mistakes
- Not using guard clauses and nesting the entire function body in an if block instead.
- Guard clauses that throw generic exceptions — throw specific, descriptive exceptions.
- Too many guard clauses that make the function's purpose hard to identify — group related checks.
- Guard clauses in the wrong order — check the cheapest/most common conditions first.
Code Examples
function process($user) {
if ($user !== null) {
if ($user->isActive()) {
// main logic
}
}
}
function process($user) {
if ($user === null) return;
if (!$user->isActive()) return;
// main logic
}