0

In a custom Drupal 8 module I decided to wrap a line of code in a try...catch block, in case $node was null.

I understand that in php errors and exceptions are different, and according to Error message - Trying to get property of non-object this is an error, so will not be handled by try...catch, and the code should continue to run after the error.

However when this code runs under Drupal 8 the error hander raises an exception. So I added the try...catch block. But the exception is still unhandled crashed the program.

This is a cut-down version of my code:

$node = null;
try {
  // The next line results in an unhandled exception 
  $f = $node->field_example;
} catch (Exception $e) {
  // Never gets here
  watchdog_exception('example', $e);
}
// Never gets here

Am I missing something? Surely this can't be the intended behaviour?

4
  • 3
    Yes, that’s the behaviour PHP intends; it has exceptions and errors as you say, and fundamentally misusing a data type is an example of an error. To avoid, use instanceof, is_object or similar
    – Clive
    May 23, 2020 at 17:55
  • 2
    It's explained in Errors in PHP 7. As the Error hierarchy does not inherit from Exception, code that uses catch (Exception $e) { ... } blocks to handle uncaught exceptions in PHP 5 will find that these Errors are not caught by these blocks. Either a catch (Error $e) { ... } block or a set_exception_handler() handler is required.
    – apaderno
    May 23, 2020 at 18:36
  • 5
    You can also just catch (\Throwable $e) if you want both
    – Clive
    May 23, 2020 at 19:16
  • Thanks @Clive that works.
    – hughworm
    May 24, 2020 at 9:46

2 Answers 2

2

I actually over-simplified by question. The crash doesn't happen in the simple case I posted, just an error and execution continues. It arises when I use field API syntax to refer to a null referenced entity, and only then when the target_id is not null.

$node->field_foo->target_id = 999; // term 999 does not exist
try {
  // The next line results in an unhandled exception 
  $v = $node->field_foo->entity->field_bar->value;
} catch (\Exception $e) {
  // Never gets here
  watchdog_exception('example', $e);
}
// And never gets to continue here

The issue was why and Drupal does this. The solution (thanks @Clive) is to replace catch (\Exception $e) with catch (\Throwable $e)

0

You are trying to catch Exception, when you should be catching \Exception.

} catch (\Exception $e) {

EDIT: Assuming that an exception is actually thrown as stated in the original post.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.