Result Pattern
Result<T> Pattern
Explicit error handling without exceptions.
Philosophy
Return Result<T> objects that force explicit error handling at compile time instead of throwing exceptions.
Benefits
- No uncaught exceptions - Failures are explicit in the type system
- Visible in type system -
Result<T>clearly indicates operation can fail - Cannot ignore errors - Must check success/failure explicitly
- Functional programming - Supports map, flatMap, onSuccess, onFailure
Implementation
interface ResultInterface {
public function isSuccess(): bool;
public function isFailure(): bool;
public function getValue(): mixed;
public function getValueOr(mixed $default): mixed;
public function getError(): ?Throwable;
public function map(callable $fn): Result;
public function onSuccess(callable $fn): Result;
public function onFailure(callable $fn): Result;
}
Usage
Check Before Using
$result = SystemMetrics::cpu();
if ($result->isSuccess()) {
$cpu = $result->getValue();
// Use $cpu safely
} else {
$error = $result->getError();
// Handle error
}
Provide Default Value
$cpu = SystemMetrics::cpu()->getValueOr(null);
if ($cpu === null) {
// Handle failure
}
Functional Style
SystemMetrics::memory()
->map(fn($mem) => $mem->usedPercentage())
->onSuccess(fn($pct) => echo "Memory: {$pct}%\n")
->onFailure(fn($err) => error_log($err->getMessage()));
Comparison with Exceptions
Traditional Exceptions
// Easy to forget try/catch
$cpu = getCpuMetrics(); // Can throw!
// Broad catches hide errors
try {
// lots of code
} catch (Exception $e) {
// What threw?
}
Result<T> Pattern
// Must handle explicitly
$result = SystemMetrics::cpu();
if ($result->isSuccess()) {
// Can only get value after checking
$cpu = $result->getValue();
}
// Errors are explicit
if ($result->isFailure()) {
$error = $result->getError();
// Know exactly what failed
}
Related Documentation
- Error Handling - Complete guide
- API Reference - All Result<T> methods