Try/Catch block в PHP не ловит Исключение

Я пытаюсь запустить этот пример # 1 с этой страницы: http://php.net/manual/en/language.exceptions.php

<?php
function inverse($x) {
    if (!$x) {
        throw new Exception('Division by zero.');
    }
    return 1/$x;
}
try {
    echo inverse(5) . "\n";
    echo inverse(0) . "\n";
} catch (Exception $e) {
    echo 'Caught exception: ',  $e->getMessage(), "\n";
}
// Continue execution
echo "Hello World\n";
?>

Однако вместо желаемого вывода я получаю:

0.2
Fatal error: Uncaught exception 'Exception' with message 'Division by zero.' 
in xxx:
7 Stack trace: #0 xxx(14): inverse(0) #1 {main} thrown in xxx on line 7

Я использую среду разработчика UniServer 3.5 с PHP 5.2.3

Ответ 1

У меня просто была эта точная проблема, когда мне показалось, что я даже скопировал название исключения, но все же не поймал его. Оказалось, что это была моя глупая ошибка, но я думал, что должен опубликовать свой случай здесь, если в той же ситуации есть кто-то другой.

У меня было мое исключение в моем пространстве имен A, а script - в пространстве имен, называемом B. Проблема заключалась в том, что у меня было A\MyException, которое равно (в PHP)\B\A\MyException (потому что мой script находится в пространстве имен B!). Все, что я должен был сделать, чтобы исправить это, заключалось в том, чтобы добавить к имени исключения обратную косую черту (или что-то еще), чтобы она выглядела так:\A\MyException

Ответ 2

Довольно старый вопрос, но...

У меня тоже была эта проблема (и что я нашел этот пост), но простой эксперимент позволил мне найти решение. Просто попробуйте изменить Exception на \Exception. Работал для меня!

EDIT:

Как указал Сиванн в комментариях, использование пространства имен должно делать то же самое. Поэтому просто введите use \Exception as Exception; перед объявлением класса.

Ответ 3

Попробуйте поставить catch(\Exception $e) вместо catch(Exception $e). Если вы используете код, который вы не знаете об этом очень хорошо, или, особенно - если вы используете фреймворк, он может переопределить PHP Exception по умолчанию одним из своих, и, следовательно, вы можете пойти по неправильному пути и получить нежелательный результат. Если вы просто положили \Exception, то вы уверены, что вы поймаете базовое исключение PHP.

Ответ 4

Вы не можете использовать типичные блоки try {} catch {} в PHP, как вы могли бы сделать на другом языке, таком как С# (Csharp).

Если вы это сделаете:

try{
    //division by zero
    $number = 5/0;
}
catch(Exception $ex){
    echo 'Got it!';
}

Вы не увидите "Получил"! сообщение никогда. Зачем? Это просто потому, что PHP всегда нуждается в исключении, которое будет "брошено". Вам нужно установить свой собственный обработчик ошибок и выбросить с ним исключение.

Смотрите функцию set_error_handler: http://php.net/manual/es/function.set-error-handler.php

Ответ 5

У вас не работает идентичный код, иначе исключение будет выбрано в строке 4 вместо 7. Какой код вы используете точно?

Ответ 6

Мое начальное, хотя у вас есть опечатка в имени исключения, которое вы ловите/бросаете, но если ваш код точно такой же, я точно не знаю, что происходит.

Попробуйте выполнить следующую модификацию оригинала script и вставьте свои результаты. Это поможет немного лучше диагностировать вашу проблему.

<?php

//set up exception handler to report what we didn't catch
function exception_handler($exception) {

    if($exception instanceof MyException) {
        echo "you didn't catch a myexception instance\n";

    } else if($exception instanceof Exception) {
        echo "you didn't catch a exception instance\n";

    } else {
        echo "uncaught exception of type: ".gettype($exception)."\n";
    }

    echo "Uncaught exception: " , $exception->getMessage(), "\n";
}

//install the handler
set_exception_handler('exception_handler');

class MyException extends Exception {
}

function inverse($x) {
    if (!$x) {
        throw new MyException('Division by zero.');
    }
    else return 1/$x;
}

try {
    echo inverse(5) . "\n";
    echo inverse(0) . "\n";
} catch (MyException $e) {
    echo 'Caught myexception: ',  $e->getMessage(), "\n";
} catch (Exception $e) {
    echo 'Caught exception: ',  $e->getMessage(), "\n";
}

// Continue execution
echo 'Hello World';
?>

Ответ 7

У меня была та же проблема со следующими конфигурациями,

PHP 5.2.14 (cli) (построено: 12 августа 2010 г. 17:32:30) Copyright (c) 1997-2010 PHP Group Zend Engine v2.2.0, Copyright (c) 1998-2010 Zend Technologies   с eAccelerator v0.9.5.1, Copyright (c) 2004-2006 eAccelerator, by eAccelerator

Решение состоит в том, чтобы отключить eAccelerator или обновить его. Я попробовал оба, и оба исправления работали. Об ошибке сообщается здесь https://eaccelerator.net/ticket/242 (NB. Firefox жалуется на их сертификат SSL).

Теперь я запускаю try catch правильно со следующими конфигурациями,

PHP 5.2.4 (cli) (построено: 16.10.2007 09:13:35) Copyright (c) 1997-2007 Группа PHP Zend Engine v2.2.0, Copyright (c) 1998-2007 Zend Technologies   с eAccelerator v0.9.6.1, Copyright (c) 2004-2010 eAccelerator, by eAccelerator

Ответ 8

в Xdebug существует параметр:

xdebug.show_exception_trace = 1

Это заставит php выводить исключения даже в блок catch try. Поверните это на 0

Ответ 9

Возможно, попробуйте отключить некоторые сторонние расширения, которые вы, возможно, установили? http://bugs.php.net/bug.php?id=41744

Ответ 10

\Исключение не работает для меня, но я нашел решение.

Мне нужно было заменить try {} catch (Exception $ e) {} на try {} catch (Throwable $ e) {}.

Для получения дополнительной информации: https://trowski.com/2015/06/24/throwable-exceptions-and-errors-in-php7/