@@ -76,6 +76,61 @@ something prettier and more useful::
76
76
available, the handler uses a Symfony Response object; if not, it falls
77
77
back to a regular PHP response.
78
78
79
+ Catches PHP errors and turn them into exceptions
80
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
81
+
82
+ Most PHP core functions were written before exception handling was introduced to the
83
+ language and most of this functions do not throw an exception on failure. Instead,
84
+ they return ``false `` in case of error.
85
+
86
+ Let's take the following code example::
87
+
88
+ $data = json_decode(file_get_contents($filename), true);
89
+ $data['read_at'] = date($datetimeFormat);
90
+ file_put_contents($filename, json_encode($data));
91
+
92
+ All these functions ``file_get_contents ``, ``json_decode ``, ``date ``, ``json_encode ``
93
+ and ``file_put_contents `` will return ``false `` or ``null `` on error, having to
94
+ deal with those failures manually::
95
+
96
+ $content = @file_get_contents($filename);
97
+ if (false === $content) {
98
+ throw new \RuntimeException('Could not load file.');
99
+ }
100
+ $data = @json_decode($content, true);
101
+ if (null === $data) {
102
+ throw new \RuntimeException('File does not contain valid JSON.');
103
+ }
104
+ $datetime = @date($datetimeFormat);
105
+ if (false === $datetime) {
106
+ throw new \RuntimeException('Invalid datetime format.');
107
+ }
108
+ // ...
109
+
110
+ .. note ::
111
+
112
+ Since PHP 7.3 `json_decode `_ function will accept a new ``JSON_THROW_ON_ERROR `` option
113
+ that will let ``json_decode `` throw an exception instead of returning ``null `` on error.
114
+ However, it is not enabled by default, so you will need to explicitly configure it.
115
+
116
+ To simplify this behavior the :class: `Symfony\\ Component\\ ErrorHandler\\ ErrorHandler ` class
117
+ provides a :method: `Symfony\\ Component\\ ErrorHandler\\ ErrorHandler::call ` method that will
118
+ automatically throw an exception when such a failure occurs. This method will accept a ``callable ``
119
+ parameter and then the arguments needed to call it, returning back the result::
120
+
121
+ $content = ErrorHandler::call('file_get_contents', $filename);
122
+
123
+ This way, you could use a ``\Closure `` function to wrap a portion of code and be sure that it
124
+ breaks even if the `@-silencing operator `_ is used::
125
+
126
+ $data = ErrorHandler::call(static function () use ($filename, $datetimeFormat) {
127
+ $data = json_decode(file_get_contents($filename), true);
128
+ $data['read_at'] = date($datetimeFormat);
129
+ file_put_contents($filename, json_encode($data));
130
+
131
+ return $data;
132
+ });
133
+
79
134
.. _component-debug-class-loader :
80
135
81
136
Debugging a Class Loader
@@ -92,3 +147,6 @@ Using the ``DebugClassLoader`` is done by calling its static
92
147
use Symfony\Component\ErrorHandler\DebugClassLoader;
93
148
94
149
DebugClassLoader::enable();
150
+
151
+ .. _`@-silencing operator` : https://php.net/manual/en/function.json-decode.php
152
+ .. _`json_decode` : https://php.net/manual/en/language.operators.errorcontrol.php
0 commit comments