Do Not Use Exception Class Directly ################################### :category: PHP :tags: good practices, opinion :date: 2024-11-18 23:08:00 +0200 It is a bad practice to use the ``Exception`` class directly in PHP. That means 2 points: * Do not throw ``Exception`` directly * Do not catch ``Exception`` directly Subclassing ``Exception`` is not a direct use in this context. Do not throw ``Exception`` ========================== There are a lot of specific ``Exception`` descendants in PHP. `See documentation for the full list.`__ It's not necessary to use and remember all of them, many have unclear use cases, but at very least you should separate your exceptions into ``RuntimeException`` and ``LogicException``. As the doc says, ``LogicException`` means code misuse. Throw ``LogicException`` in cases when the upstream must be fixed because it uses your code incorrectly. Throw ``RuntimeException`` in cases that are not predictable by the upstream, like service failures or invalid user input. .. __: https://www.php.net/manual/en/spl.exceptions.php In case you use exceptions for flow control, you need your own custom exceptions anyway. In this case you can extend the base ``Exception``, extending ``Exception`` directly is not a sin, especially if your exceptions are not error conditions. Do not catch ``Exception`` ========================== Assuming you follow the previous point, there is no need to catch ``Exception``\ 's. 1. If you don't guard against a specific situation, catch all ``RuntimeException``\ 's. ``LogicException``\ 's should go to your logger. 2. In a global error handler that writes your logs, you need to catch Errors too, so you need to go even further and catch ``Throwable``. 3. If you use exceptions for flow control (please don't haha) you already catching your own exceptions, and if you follow the previous point, they are already separated from actual error conditions and won't be caught mistakenly by a wrong level. Notable exceptions to the rule: * You use PHP below 7.0 and don't have ``Throwable``. Well, it's 2024 already so this is another call for you to upgrade. Otherwise assume point 2 allows you to catch a base ``Exception``. * You use a library that throws plain ``Exception`` instances. Well, bad for you, but maybe it's a good idea to report this thing as a problem.