Search code examples
phpexception

Using additional data in php exceptions


I have php code that execute python cgi and I want to pass python trace (returned from cgi) as extra data to php exception how can I do this and how can I get that value from catch(Exception e) { (It should check if that extra value exesit or not).

I have code like this:

$response = json_decode(curl_exec($ch));
if (isset($response->error)) {
    // how to send $response->trace with exception.
    throw new Exception($response->error);
}
return $response->result;

and I use json-rpc library that should return that data to the user:

} catch (Exception $e) {
    //catch all exeption from user code
    $msg = $e->getMessage();
    echo response(null, $id, array("code"=>200, "message"=>$msg));
}

Do I need to write new type of exception or can I do this with normal Exception? I would like to send everything that was thrown in "data" =>


Solution

  • You need to extend Exception class:

    <?php
    
    class ResponseException extends \Exception 
    {
        private string $data = '';
    
        public function __construct($message, string $data) 
        {
            $this->data = $data;
            parent::__construct($message);
        }
    
        public function getData(): string
        {
            return $this->data;
        }
    }
    

    When throwing:

    <?php
    
    ...
    throw new ResponseException($response->error, $someData);
    ...
    

    And when catching:

    catch(ResponseException $e) {
        ...
        $data = $e->getData();
        ...
    }
    

    Dynamic Property (not recommended)

    Please note that this will cause deprecation error in PHP 8.2 and will stop working in PHP 9 according to one of the PHP RFC https://wiki.php.net/rfc/deprecate_dynamic_properties

    As the OP asking about doing this task without extending Exception class, you can totally skip ResponseException class declaration. I really not recommend do it this way, unless you've got really strong reason (see this topic for more details: https://softwareengineering.stackexchange.com/questions/186439/is-declaring-fields-on-classes-actually-harmful-in-php)

    In throwing section:

    ...
    $e = new Exception('Exception message');
    $e->data = $customData; // we're creating object property on the fly
    throw $e;
    ...
    

    and when catching:

    catch(Exception $e) {
        $data = $e->data; // Access data property
    }
    

    September 2018 edit: As some of readers found this answer useful, I have added a link to another Stack Overflow question which explains the downsides of using dynamically declared properties.