Регистрируйте пойманное исключение с трассировкой стека
Если я не поймаю исключение в PHP, я получу полезное сообщение об ошибке в моем файле error.log
с трассировкой стека. Например, если я запущу:
<?php
function foo() {
throw new Exception('Oh no!');
}
foo();
?>
Затем я записываю это в свои журналы:
[Ср. 06 марта 10:35:32 2013] [ошибка] [клиент 86.146.145.175] Фатальная ошибка PHP: Неперехваченное исключение "Исключение" с сообщением "О нет!" в /var/www/test.php:4\nstack трассировка: \n#0/var/www/test.php (7): foo()\n#1{основной}\n добавлено/var/www/test.php в режиме онлайн 4
Иногда я хотел бы поймать исключение, но все равно регистрировать эту деталь. Я представляю себе что-то вроде:
<?php
function foo() {
throw new Exception('Oh no!');
}
try {
foo();
} catch (Exception $e) {
log_exception($e);
}
?>
Где log_exception
запишет в журнал ошибок что-то в основном в том же формате, что и то, что автоматически записывается для неперехваченного исключения - возможно, буквально идентично, кроме того, что Caught exception
вместо PHP Fatal error: Uncaught exception
.
Есть ли встроенная функция для регистрации информации об исключениях, подобной этой, или для записи ее в строку? Я представляю себе что-то похожее на traceback.format_exc()
в Питон.
4 answers
error_log($e);
Делает то, что вы хотите. Он регистрирует точно то же самое, что было бы зарегистрировано, если бы вы не поймали исключение, за вычетом слова "Неперехваченный" в начале. Он делает это, потому что это то, что Exception
возвращает магический метод класса __toString()
.
Вы можете сделать это в блоке catch
:
try {
foo();
} catch (Exception $e) {
error_log("Caught $e");
}
Или в обработчике исключений:
set_exception_handler(function($exception) {
error_log($exception);
error_page("Something went wrong!");
});
Вы можете использовать методы из базового класса PHP Exception
.
Используйте getMessage
для получения сообщения Oh no!
и используйте getTraceAsString
для получения отформатированной трассировки.
Мы используем Monolog для ведения журнала в нашем приложении. В монологе есть форматировщик, который может печатать трассировки стека. Для регистрации исключений с трассировками мы используем линейный формататор и вызываем на нем функцию includeStacktraces(). (код ниже)
$handler = new \Monolog\Handler\StreamHandler(STDOUT);
$lineFormatter = new \Monolog\Formatter\LineFormatter();
$lineFormatter->includeStacktraces();
$handler->setFormatter($lineFormatter);
$logger = new \Monolog\Logger('root', [$handler]);
try {
//do some throwing
} catch (Exception $e) {
//do some logging, add exception to context
$logger->error($e->getMessage(), ['exception' => $e]);
}
Вы можете использовать http://php.net/manual/en/function.set-exception-handler.php зарегистрировать функцию обратного вызова, которая получит сообщение от $e->GetMessage(); и сбросить его в файл.