PluginProbe ʕ •ᴥ•ʔ
Jetpack – WP Security, Backup, Speed, & Growth / 16.2-a.1
Jetpack – WP Security, Backup, Speed, & Growth v16.2-a.1
16.1.2 16.2-a.1 16.1.1 16.1 16.1-beta 16.1-beta.2 16.1-beta.3 16.1-a.5 16.1-a.3 16.0.1 16.1-a.1 16.0 16.0-beta 16.0-a.7 16.0-a.5 15.9.1 16.0-a.3 16.0-a.1 15.9 15.9-beta 15.9-a.7 15.9-a.5 15.9-a.3 15.9-a.1 15.8 15.8-beta 15.8-a.7 15.8-a.5 5.2.5 5.3.4 5.4.4 5.5.5 5.6.5 5.7.5 5.8.4 5.9.4 6.0.4 6.1 6.1.1 6.1.2 6.1.3 6.1.4 6.1.5 6.2 6.2.1 6.2.2 6.2.3 6.2.4 6.2.5 6.3 6.3.1 6.3.2 6.3.3 6.3.4 6.3.5 6.3.6 6.3.7 6.4 6.4.1 6.4.2 6.4.3 6.4.4 6.4.5 6.4.6 6.5 6.5.1 6.5.2 6.5.3 6.5.4 6.6 6.6.1 6.6.2 6.6.3 6.6.4 6.6.5 6.7 6.7.1 6.7.2 6.7.3 6.7.4 6.8 6.8.1 6.8.2 6.8.3 6.8.4 6.8.5 6.9 6.9.1 6.9.2 6.9.3 6.9.4 7.0 7.0.1 7.0.2 7.0.3 7.0.4 7.0.5 7.1 7.1.1 7.1.2 7.1.3 7.1.4 7.1.5 7.2 7.2.1 7.2.1.1 7.2.2 7.2.3 7.2.4 7.2.5 7.3 7.3.0.1 7.3.1 7.3.1.1 7.3.2 7.3.3 7.3.4 7.3.5 7.4 7.4.1 7.4.2 7.4.3 7.4.4 7.4.5 7.5 7.5.0.1 7.5.1 7.5.2 7.5.3 7.5.4 7.5.5 7.5.6 7.5.7 7.6 7.6.1 7.6.2 7.6.3 7.6.4 7.7 7.7.1 7.7.2 7.7.3 7.7.4 7.7.5 7.7.6 7.8 7.8.1 7.8.2 7.8.3 7.8.4 7.9 7.9.1 7.9.2 7.9.3 7.9.4 8.0 8.0.1 8.0.2 8.0.3 8.1 8.1.1 8.1.2 8.1.3 8.1.4 8.2 8.2.0.1 8.2.1 8.2.2 8.2.3 8.2.4 8.2.5 8.2.6 8.3 8.3.1 8.3.2 8.3.3 8.4 8.4.1 8.4.2 8.4.3 8.4.4 8.4.5 8.5 8.5.1 8.5.2 8.5.3 8.6 8.6.1 8.6.2 8.6.3 8.6.4 8.7 8.7.0.1 8.7.1 8.7.2 8.7.3 8.7.4 8.8 8.8.1 8.8.2 8.8.3 8.8.4 8.8.5 8.9 8.9.1 8.9.2 8.9.3 8.9.4 9.0 9.0.1 9.0.2 9.0.3 9.0.4 9.0.5 9.1 9.1.1 9.1.2 9.1.3 9.2 9.2.1 9.2.2 9.2.3 9.2.4 9.3 9.3.1 9.3.2 9.3.3 9.3.4 9.3.5 9.4 9.4.1 9.4.2 9.4.3 9.4.4 9.5 9.5.1 9.5.2 9.5.3 9.5.4 9.5.5 9.6 9.6.1 9.6.2 9.6.3 9.6.4 9.7 9.7.1 9.7.2 15.7-beta.2 9.7.3 15.7.1 9.8 15.8-a.1 9.8.1 15.8-a.3 9.8.2 2.0.9 9.8.3 2.1.7 9.9 2.2.10 9.9.1 2.3.10 9.9.2 2.4.7 9.9.3 2.5.5 2.6.6 2.7.5 2.8.5 2.9.6 3.0.6 3.1.5 3.2.5 3.3.6 3.4.6 3.5.6 3.6.4 3.7.5 3.8.5 3.9.10 4.0.7 4.1.4 4.2.5 4.3.5 4.4.5 4.5.3 4.6.3 4.7.4 4.8.5 4.9.3 5.0.3 5.1.4 trunk 10.0 10.0.1 10.0.2 10.1 10.1.1 10.1.2 10.2 10.2.1 10.2.2 10.2.3 10.3 10.3.1 10.3.2 10.4 10.4.1 10.4.2 10.5 10.5.1 10.5.2 10.5.3 10.6 10.6.1 10.6.2 10.7 10.7.1 10.7.2 10.8 10.8.1 10.8.2 10.9 10.9.1 10.9.2 10.9.3 11.0 11.0.1 11.0.2 11.1 11.1.1 11.1.2 11.1.3 11.1.4 11.2 11.2.1 11.2.2 11.3 11.3.1 11.3.2 11.3.3 11.3.4 11.4 11.4.1 11.4.2 11.5 11.5.1 11.5.2 11.5.3 11.6 11.6.1 11.6.2 11.7 11.7.1 11.7.2 11.7.3 11.8 11.8.3 11.8.4 11.8.5 11.8.6 11.9 11.9.1 11.9.2 11.9.3 12.0 12.0.1 12.0.2 12.1 12.1.1 12.1.2 12.2 12.2.1 12.2.2 12.3 12.3.1 12.4 12.4.1 12.5 12.5.1 12.6 12.6.1 12.6.2 12.6.3 12.7 12.7.1 12.7.2 12.8 12.8.1 12.8.2 12.9 12.9.1 12.9.2 12.9.3 12.9.4 13.0 13.0.1 13.1 13.1.1 13.1.2 13.1.3 13.1.4 13.2 13.2.1 13.2.2 13.2.3 13.3 13.3.1 13.3.2 13.4 13.4.1 13.4.2 13.4.3 13.4.4 13.5 13.5.1 13.6 13.6.1 13.7 13.7.1 13.8 13.8.1 13.8.2 13.9 13.9.1 14.0 14.1 14.2 14.2.1 14.3 14.4 14.4.1 14.5 14.6 14.7 14.8 14.9 14.9.1 15.0 15.0.1 15.0.2 15.1 15.1.1 15.2 15.3 15.3.1 15.4 15.5 15.6 15.7 15.7-a.1 15.7-a.3 15.7-a.5 15.7-a.7 15.7-beta
jetpack / jetpack_vendor / automattic / jetpack-backup-helper-script-manager / src / class-throw-on-errors.php
jetpack / jetpack_vendor / automattic / jetpack-backup-helper-script-manager / src Last commit date
class-helper-script-manager-impl.php 1 year ago class-helper-script-manager.php 1 year ago class-throw-on-errors.php 8 months ago
class-throw-on-errors.php
499 lines
1 <?php // phpcs:disable Squiz.Commenting.FileComment.Missing
2
3 // phpcs:disable WordPress.PHP.DevelopmentFunctions.prevent_path_disclosure_error_reporting
4 // phpcs:disable WordPress.PHP.DiscouragedPHPFunctions.runtime_configuration_error_reporting
5 // phpcs:disable WordPress.PHP.IniSet.display_errors_Disallowed
6
7 // After changing this file, consider increasing the version number ("VXXX") in all the files using this namespace, in
8 // order to ensure that the specific version of this file always get loaded. Otherwise, Jetpack autoloader might decide
9 // to load an older/newer version of the class (if, for example, both the standalone and bundled versions of the plugin
10 // are installed, or in some other cases).
11 namespace Automattic\Jetpack\Backup\V0005;
12
13 use Exception;
14 use Throwable;
15
16 /**
17 * Wrappers for functions which throw an exception on errors and warnings instead of silently continuing operation.
18 *
19 * PHP is pretty lax with error reporting when doing I/O operations, e.g. a typical I/O helper function returns false,
20 * null, and/or emits a warning, but the whole PHP application continues operation. It's for the caller of the I/O
21 * helper function to test the returned result of the function, and notice + act upon I/O errors.
22 *
23 * We really want to know about each and every I/O error. Therefore, this class provides wrappers for some common
24 * (mostly) I/O operations that throw an exception on errors instead of just returning false, null, or something else.
25 * This wrapper class treats warnings as errors too.
26 *
27 * Given that static method names are similar to the ones used by PHP, they're prefixed with "t_" to not erroneously
28 * trigger various security scanners.
29 */
30 class Throw_On_Errors {
31
32 /**
33 * Execute a callable, throw an exception (together with a descriptive label) on PHP warnings / errors.
34 *
35 * @param callable $callable Callable to execute.
36 * @param string $label Label to add to the thrown exception to clarify what was attempted.
37 *
38 * @return mixed Callable's return value, if any.
39 * @throws Exception On warnings thrown by the callable.
40 * @noinspection PhpUnusedParameterInspection
41 */
42 private static function throw_on_warnings( $callable, $label ) {
43 $old_error_reporting = error_reporting( - 1 );
44 $old_display_errors = ini_set( 'display_errors', 'stderr' );
45
46 // phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_set_error_handler
47 set_error_handler(
48 /**
49 * Temporary error handler.
50 *
51 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.set-error-handler
52 * @see https://www.php.net/manual/en/function.set-error-handler.php
53 *
54 * @param int $errno Level of the error raised.
55 * @param string $errstr Error message.
56 * @param string|null $errfile Filename that the error was raised in.
57 * @param int|null $errline Line number where the error was raised.
58 * @param array|null $errcontext Deprecated, unused.
59 *
60 * @return never
61 * @throws Exception
62 */
63 // phpcs:ignore VariableAnalysis.CodeAnalysis.VariableAnalysis.UnusedVariable
64 function ( $errno, $errstr, $errfile = null, $errline = null, $errcontext = null ) {
65 throw new Exception( "$errstr (file: $errfile; line: $errline)" );
66 }
67 );
68
69 $result = null;
70 $error_message = null;
71 try {
72 $result = $callable();
73 } catch ( Throwable $throwable ) {
74 $error_message = $throwable->getMessage();
75 }
76
77 restore_error_handler();
78 ini_set( 'display_errors', $old_display_errors );
79 error_reporting( $old_error_reporting );
80
81 if ( $error_message !== null ) {
82 throw new Exception( "$label failed: $error_message" );
83 }
84
85 return $result;
86 }
87
88 /**
89 * Return canonicalized absolute pathname, throw on warnings / errors.
90 *
91 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.realpath
92 * @see https://www.php.net/manual/en/function.realpath.php
93 *
94 * @param string $path Path being checked.
95 *
96 * @return string Canonicalized absolute pathname
97 * @throws Exception On invalid parameters, or if realpath() has returned false or thrown warnings.
98 */
99 public static function t_realpath( $path ) {
100 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
101 if ( ! $path ) {
102 throw new Exception( 'Filename for realpath() is unset' );
103 }
104
105 $label = "realpath( '$path' )";
106
107 $realpath_result = static::throw_on_warnings(
108 function () use ( $path ) {
109 return realpath( $path );
110 },
111 $label
112 );
113
114 if ( false === $realpath_result ) {
115 throw new Exception( "Unable to $label" );
116 }
117
118 return $realpath_result;
119 }
120
121 /**
122 * Check whether a file or directory exists, throw on warnings / errors.
123 *
124 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.file-exists
125 * @see https://www.php.net/manual/en/function.file-exists.php
126 *
127 * @param string $filename Path to the file or directory.
128 *
129 * @return bool True if the file or directory specified by filename exists; false otherwise.
130 * @throws Exception On invalid parameters, or if file_exists() has thrown warnings.
131 */
132 public static function t_file_exists( $filename ) {
133 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
134 if ( ! $filename ) {
135 throw new Exception( 'Filename for file_exists() is unset' );
136 }
137
138 return static::throw_on_warnings(
139 function () use ( $filename ) {
140 return file_exists( $filename );
141 },
142 "file_exists( '$filename' )"
143 );
144 }
145
146 /**
147 * Tell whether the filename (or a directory) is readable, throw on warnings / errors.
148 *
149 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.is-readable
150 * @see https://www.php.net/manual/en/function.is-readable.php
151 *
152 * @param string $filename Filename (or directory) to check.
153 *
154 * @return bool True if the filename (or a directory) exists and is readable, false otherwise.
155 * @throws Exception On invalid parameters, or if is_readable() has thrown warnings.
156 */
157 public static function t_is_readable( $filename ) {
158 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
159 if ( ! $filename ) {
160 throw new Exception( 'Filename for is_readable() is unset' );
161 }
162
163 return static::throw_on_warnings(
164 function () use ( $filename ) {
165 return is_readable( $filename );
166 },
167 "is_readable( '$filename' )"
168 );
169 }
170
171 /**
172 * Tell whether the filename (or a directory) is writable, throw on warnings / errors.
173 *
174 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.is-writable
175 * @see https://www.php.net/manual/en/function.is-writable.php
176 *
177 * @param string $filename Filename (or directory) to check.
178 *
179 * @return bool True if the filename (or a directory) exists and is writable, false otherwise.
180 * @throws Exception On invalid parameters, or if is_writable() has thrown warnings.
181 */
182 public static function t_is_writable( $filename ) {
183 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
184 if ( ! $filename ) {
185 throw new Exception( 'Filename for is_writable() is unset' );
186 }
187
188 return static::throw_on_warnings(
189 function () use ( $filename ) {
190 // phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_operations_is_writable
191 return is_writable( $filename );
192 },
193 "is_writable( '$filename' )"
194 );
195 }
196
197 /**
198 * Get file size, throw on warnings / errors.
199 *
200 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.filesize
201 * @see https://www.php.net/manual/en/function.filesize.php
202 *
203 * @param string $filename Path to the file.
204 *
205 * @return int Size of the file in bytes
206 * @throws Exception On invalid parameters, or if filesize() has thrown warnings.
207 */
208 public static function t_filesize( $filename ) {
209 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
210 if ( ! $filename ) {
211 throw new Exception( 'Filename for filesize() is unset' );
212 }
213
214 $label = "filesize( '$filename' )";
215
216 $filesize_result = static::throw_on_warnings(
217 function () use ( $filename ) {
218 return filesize( $filename );
219 },
220 $label
221 );
222
223 if ( false === $filesize_result ) {
224 throw new Exception( "Unable to $label" );
225 }
226
227 return $filesize_result;
228 }
229
230 /**
231 * Get file modification time, throw on warnings / errors.
232 *
233 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.filemtime
234 * @see https://www.php.net/manual/en/function.filemtime.php
235 *
236 * @param string $filename Path to the file.
237 *
238 * @return int The time the file was last modified
239 * @throws Exception On invalid parameters, or if filemtime() has thrown warnings.
240 */
241 public static function t_filemtime( $filename ) {
242 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
243 if ( ! $filename ) {
244 throw new Exception( 'Filename for filemtime() is unset' );
245 }
246
247 $label = "filemtime( '$filename' )";
248
249 $filemtime_result = static::throw_on_warnings(
250 function () use ( $filename ) {
251 return filemtime( $filename );
252 },
253 $label
254 );
255
256 if ( false === $filemtime_result ) {
257 throw new Exception( "Unable to $label" );
258 }
259
260 return $filemtime_result;
261 }
262
263 /**
264 * Tell whether the filename is a directory (follow symlinks), throw on warnings / errors.
265 *
266 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.is-dir
267 * @see https://www.php.net/manual/en/function.is-dir.php
268 *
269 * @param string $filename Path to the file.
270 *
271 * @return bool True if the filename (or the symlink's target) exists and is a directory, false otherwise.
272 * @throws Exception On invalid parameters, if is_dir() has thrown warnings, or has failed.
273 */
274 public static function t_is_dir( $filename ) {
275 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
276 if ( ! $filename ) {
277 throw new Exception( 'Filename for is_dir() is unset' );
278 }
279
280 return static::throw_on_warnings(
281 function () use ( $filename ) {
282 return is_dir( $filename );
283 },
284 "is_dir( '$filename' )"
285 );
286 }
287
288 /**
289 * Make a directory, throw on warnings / errors.
290 *
291 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.mkdir
292 * @see https://www.php.net/manual/en/function.mkdir.php
293 *
294 * @param string $directory Directory path.
295 * @param int $permissions Permissions of the newly created directory.
296 * @param bool $recursive If true, then any parent directories to the directory specified will also be created,
297 * with the same permissions.
298 *
299 * @return void
300 * @throws Exception On invalid parameters, if mkdir() has thrown warnings, or has failed.
301 */
302 public static function t_mkdir( $directory, $permissions = 0777, $recursive = false ) {
303 // PHP 5.x won't complain about permissions being null, so let's do it ourselves.
304 if ( $permissions === null ) {
305 throw new Exception( 'Permissions for mkdir() are unset' );
306 }
307
308 $label = "mkdir( '$directory', 0" . decoct( $permissions ) . ', ' . ( $recursive ? 'true' : 'false' ) . ' )';
309
310 $mkdir_result = static::throw_on_warnings(
311 function () use ( $directory, $permissions, $recursive ) {
312 // phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_operations_mkdir
313 return mkdir( $directory, $permissions, $recursive );
314 },
315 $label
316 );
317
318 if ( false === $mkdir_result ) {
319 throw new Exception( "Unable to $label" );
320 }
321 }
322
323 /**
324 * List files and directories inside the specified path, throw on warnings / errors.
325 *
326 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.scandir
327 * @see https://www.php.net/manual/en/function.scandir.php
328 *
329 * @param string $directory Directory that will be scanned.
330 *
331 * @return string[] An array of filenames.
332 * @throws Exception If scandir() has thrown warnings, or has failed.
333 */
334 public static function t_scandir( $directory ) {
335
336 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
337 if ( ! $directory ) {
338 throw new Exception( 'Directory for scandir() is unset' );
339 }
340
341 $label = "scandir( '$directory' )";
342
343 $scandir_result = static::throw_on_warnings(
344 function () use ( $directory ) {
345 return scandir( $directory );
346 },
347 $label
348 );
349
350 if ( false === $scandir_result ) {
351 throw new Exception( "Unable to $label" );
352 }
353
354 return $scandir_result;
355 }
356
357 /**
358 * Remove a directory, throw on warnings / errors.
359 *
360 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.rmdir
361 * @see https://www.php.net/manual/en/function.rmdir.php
362 *
363 * @param string $directory Directory path.
364 *
365 * @return void
366 * @throws Exception On invalid parameters, if rmdir() has thrown warnings, or has failed.
367 */
368 public static function t_rmdir( $directory ) {
369 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
370 if ( ! $directory ) {
371 throw new Exception( 'Directory for mkdir() is unset' );
372 }
373
374 $label = "rmdir( '$directory' )";
375
376 $rmdir_result = static::throw_on_warnings(
377 function () use ( $directory ) {
378 // phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_operations_rmdir
379 return rmdir( $directory );
380 },
381 $label
382 );
383
384 if ( false === $rmdir_result ) {
385 throw new Exception( "Unable to $label" );
386 }
387 }
388
389 /**
390 * Delete a file, throw on warnings / errors.
391 *
392 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.unlink
393 * @see https://www.php.net/manual/en/function.unlink.php
394 *
395 * @param string $filename Path to the file.
396 *
397 * @return void
398 * @throws Exception If unlink() has thrown warnings, or has failed.
399 */
400 public static function t_unlink( $filename ) {
401
402 $label = "unlink( '$filename' )";
403
404 $unlink_result = static::throw_on_warnings(
405 function () use ( $filename ) {
406 // phpcs:ignore WordPress.WP.AlternativeFunctions.unlink_unlink
407 return unlink( $filename );
408 },
409 $label
410 );
411
412 if ( false === $unlink_result ) {
413 throw new Exception( "Unable to $label" );
414 }
415 }
416
417 /**
418 * Write data to a file, throw on warnings / errors.
419 *
420 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.file-put-contents
421 * @see https://www.php.net/manual/en/function.file-put-contents.php
422 *
423 * @param string $filename Path to the file where to write the data.
424 * @param string $data The data to write.
425 *
426 * @return void
427 * @throws Exception If file_put_contents() has thrown warnings, has failed, or if it didn't write all the bytes.
428 */
429 public static function t_file_put_contents( $filename, $data ) {
430
431 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
432 if ( ! $filename ) {
433 throw new Exception( 'Filename for f_p_c() is unset' );
434 }
435 if ( $data === null ) {
436 throw new Exception( 'Data to write is null' );
437 }
438
439 $data_length = strlen( $data );
440
441 // Weird label is intentional, otherwise security scanners find this label suspicious.
442 $label = "f_p_c( '$filename', $data_length bytes of data )";
443
444 $number_of_bytes_written = static::throw_on_warnings(
445 function () use ( $filename, $data ) {
446 // phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_operations_file_put_contents
447 return file_put_contents( $filename, $data );
448 },
449 $label
450 );
451
452 if ( false === $number_of_bytes_written ) {
453 throw new Exception( "Unable to $label" );
454 }
455
456 if ( $number_of_bytes_written !== $data_length ) {
457 throw new Exception(
458 "$label was expected to write $data_length bytes, but wrote $number_of_bytes_written bytes"
459 );
460 }
461 }
462
463 /**
464 * Read entire file into a string, throw on warnings / errors.
465 *
466 * @see https://php-legacy-docs.zend.com/manual/php5/en/function.file-get-contents
467 * @see https://www.php.net/manual/en/function.file-get-contents.php
468 *
469 * @param string $filename Name of the file to read.
470 *
471 * @return string The read data.
472 * @throws Exception If file_get_contents() has thrown warnings, or has failed.
473 */
474 public static function t_file_get_contents( $filename ) {
475
476 // PHP 5.x won't complain about parameter being unset, so let's do it ourselves.
477 if ( ! $filename ) {
478 throw new Exception( 'Filename for f_g_c() is unset' );
479 }
480
481 // Weird label is intentional, otherwise security scanners find this label suspicious.
482 $label = "f_g_c( '$filename' )";
483
484 $fgc_result = static::throw_on_warnings(
485 function () use ( $filename ) {
486 // phpcs:ignore WordPress.WP.AlternativeFunctions.file_get_contents_file_get_contents
487 return file_get_contents( $filename );
488 },
489 $label
490 );
491
492 if ( false === $fgc_result ) {
493 throw new Exception( "Unable to $label" );
494 }
495
496 return $fgc_result;
497 }
498 }
499