Construisez une stratégie d'erreurs complète : exceptions métier chaînées, finally maîtrisé et gestionnaires globaux en dernier rempart.
Ouvrir cette leçon dans KodokonDepuis PHP 7, tout ce qui se lance implémente Throwable, avec deux branches : Error (défaillances du moteur et du typage, comme TypeError) et Exception (échecs applicatifs). Vous n'attrapez Error qu'aux frontières du programme. Côté applicatif, la SPL fournit une hiérarchie prête à l'emploi : LogicException signale un bug du développeur, à corriger ; RuntimeException un aléa d'exécution, à gérer. Le réflexe professionnel : dériver vos exceptions métier de ces bases, une par situation identifiable.
<?php
declare(strict_types=1);
abstract class AppException extends RuntimeException
{
}
final class UserNotFound extends AppException
{
public static function withEmail(
string $email
): self {
return new self("No user for $email");
}
}
try {
throw UserNotFound::withEmail('lea@example.com');
} catch (UserNotFound $e) {
echo $e->getMessage();
}try/catch n'a de valeur que si vous savez quoi faire de l'erreur - sinon, laissez-la remonter. Trois outils affinent le contrôle : le multi-catch catch (JsonException | ValueError $e) regroupe les traitements identiques ; le paramètre previous chaîne la cause d'origine quand vous traduisez une exception technique en exception métier ; finally s'exécute dans tous les cas - succès, exception, même return anticipé - idéal pour libérer une ressource.
<?php
declare(strict_types=1);
final class PayloadInvalid extends RuntimeException
{
}
function decode(string $json): mixed
{
try {
return json_decode(
$json,
true,
flags: JSON_THROW_ON_ERROR,
);
} catch (JsonException $e) {
throw new PayloadInvalid(
'Invalid JSON payload',
previous: $e,
);
} finally {
echo "decode() finished\n";
}
}
try {
decode('{broken');
} catch (PayloadInvalid $e) {
echo $e->getPrevious()?->getMessage();
}En bout de chaîne, deux gestionnaires globaux ferment le dispositif. set_exception_handler attrape tout ce qui n'a pas été géré : journalisation structurée, réponse 500 générique - sans jamais divulguer message ni trace à l'utilisateur. set_error_handler convertit les erreurs héritées (warnings, notices) en ErrorException, unifiant les deux mondes : tout devient exception, tout suit le même circuit de traitement.
<?php
declare(strict_types=1);
set_error_handler(function (
int $severity,
string $message,
string $file,
int $line,
): bool {
throw new ErrorException(
$message,
0,
$severity,
$file,
$line,
);
});
set_exception_handler(function (Throwable $e): void {
error_log($e->getMessage());
http_response_code(500);
echo 'A technical error occurred.';
});
trigger_error('Legacy warning', E_USER_WARNING);
echo 'Never reached';Error et Exception en PHP moderne ?Error hérite d'ExceptionThrowablefinally s'exécute-t-il ?previous d'une exception ?