minor #14179 [Debug] Made code in ErrorHandler easier to read (lyrixx)
This PR was merged into the 2.6 branch.
Discussion
----------
[Debug] Made code in ErrorHandler easier to read
| Q | A
| ------------- | ---
| Bug fix? | no
| New feature? | no
| BC breaks? | no
| Deprecations? | no
| Tests pass? | yes
| Fixed tickets |
| License | MIT
| Doc PR |
Commits
-------
15ef182
[Debug] Made code in ErrorHandler easier to read
This commit is contained in:
commit
dec2ac917e
@ -356,69 +356,71 @@ class ErrorHandler
|
|||||||
$throw = $this->thrownErrors & $type & $level;
|
$throw = $this->thrownErrors & $type & $level;
|
||||||
$type &= $level | $this->screamedErrors;
|
$type &= $level | $this->screamedErrors;
|
||||||
|
|
||||||
if ($type && ($log || $throw)) {
|
if (!$type || (!$log && !$throw)) {
|
||||||
if (PHP_VERSION_ID < 50400 && isset($context['GLOBALS']) && ($this->scopedErrors & $type)) {
|
return $type && $log;
|
||||||
$e = $context; // Whatever the signature of the method,
|
}
|
||||||
unset($e['GLOBALS'], $context); // $context is always a reference in 5.3
|
|
||||||
$context = $e;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ($throw) {
|
if (PHP_VERSION_ID < 50400 && isset($context['GLOBALS']) && ($this->scopedErrors & $type)) {
|
||||||
if (($this->scopedErrors & $type) && class_exists('Symfony\Component\Debug\Exception\ContextErrorException')) {
|
$e = $context; // Whatever the signature of the method,
|
||||||
// Checking for class existence is a work around for https://bugs.php.net/42098
|
unset($e['GLOBALS'], $context); // $context is always a reference in 5.3
|
||||||
$throw = new ContextErrorException($this->levels[$type].': '.$message, 0, $type, $file, $line, $context);
|
$context = $e;
|
||||||
} else {
|
}
|
||||||
$throw = new \ErrorException($this->levels[$type].': '.$message, 0, $type, $file, $line);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (PHP_VERSION_ID <= 50407 && (PHP_VERSION_ID >= 50400 || PHP_VERSION_ID <= 50317)) {
|
if ($throw) {
|
||||||
// Exceptions thrown from error handlers are sometimes not caught by the exception
|
if (($this->scopedErrors & $type) && class_exists('Symfony\Component\Debug\Exception\ContextErrorException')) {
|
||||||
// handler and shutdown handlers are bypassed before 5.4.8/5.3.18.
|
// Checking for class existence is a work around for https://bugs.php.net/42098
|
||||||
// We temporarily re-enable display_errors to prevent any blank page related to this bug.
|
$throw = new ContextErrorException($this->levels[$type].': '.$message, 0, $type, $file, $line, $context);
|
||||||
|
|
||||||
$throw->errorHandlerCanary = new ErrorHandlerCanary();
|
|
||||||
}
|
|
||||||
|
|
||||||
throw $throw;
|
|
||||||
}
|
|
||||||
|
|
||||||
// For duplicated errors, log the trace only once
|
|
||||||
$e = md5("{$type}/{$line}/{$file}\x00{$message}", true);
|
|
||||||
$trace = true;
|
|
||||||
|
|
||||||
if (!($this->tracedErrors & $type) || isset($this->loggedTraces[$e])) {
|
|
||||||
$trace = false;
|
|
||||||
} else {
|
} else {
|
||||||
$this->loggedTraces[$e] = 1;
|
$throw = new \ErrorException($this->levels[$type].': '.$message, 0, $type, $file, $line);
|
||||||
}
|
}
|
||||||
|
|
||||||
$e = compact('type', 'file', 'line', 'level');
|
if (PHP_VERSION_ID <= 50407 && (PHP_VERSION_ID >= 50400 || PHP_VERSION_ID <= 50317)) {
|
||||||
|
// Exceptions thrown from error handlers are sometimes not caught by the exception
|
||||||
|
// handler and shutdown handlers are bypassed before 5.4.8/5.3.18.
|
||||||
|
// We temporarily re-enable display_errors to prevent any blank page related to this bug.
|
||||||
|
|
||||||
if ($type & $level) {
|
$throw->errorHandlerCanary = new ErrorHandlerCanary();
|
||||||
if ($this->scopedErrors & $type) {
|
|
||||||
$e['context'] = $context;
|
|
||||||
if ($trace) {
|
|
||||||
$e['stack'] = debug_backtrace(true); // Provide object
|
|
||||||
}
|
|
||||||
} elseif ($trace) {
|
|
||||||
$e['stack'] = debug_backtrace(PHP_VERSION_ID >= 50306 ? DEBUG_BACKTRACE_IGNORE_ARGS : false);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($this->isRecursive) {
|
throw $throw;
|
||||||
$log = 0;
|
}
|
||||||
} elseif (self::$stackedErrorLevels) {
|
|
||||||
self::$stackedErrors[] = array($this->loggers[$type], $message, $e);
|
|
||||||
} else {
|
|
||||||
try {
|
|
||||||
$this->isRecursive = true;
|
|
||||||
$this->loggers[$type][0]->log($this->loggers[$type][1], $message, $e);
|
|
||||||
$this->isRecursive = false;
|
|
||||||
} catch (\Exception $e) {
|
|
||||||
$this->isRecursive = false;
|
|
||||||
|
|
||||||
throw $e;
|
// For duplicated errors, log the trace only once
|
||||||
|
$e = md5("{$type}/{$line}/{$file}\x00{$message}", true);
|
||||||
|
$trace = true;
|
||||||
|
|
||||||
|
if (!($this->tracedErrors & $type) || isset($this->loggedTraces[$e])) {
|
||||||
|
$trace = false;
|
||||||
|
} else {
|
||||||
|
$this->loggedTraces[$e] = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
$e = compact('type', 'file', 'line', 'level');
|
||||||
|
|
||||||
|
if ($type & $level) {
|
||||||
|
if ($this->scopedErrors & $type) {
|
||||||
|
$e['context'] = $context;
|
||||||
|
if ($trace) {
|
||||||
|
$e['stack'] = debug_backtrace(true); // Provide object
|
||||||
}
|
}
|
||||||
|
} elseif ($trace) {
|
||||||
|
$e['stack'] = debug_backtrace(PHP_VERSION_ID >= 50306 ? DEBUG_BACKTRACE_IGNORE_ARGS : false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($this->isRecursive) {
|
||||||
|
$log = 0;
|
||||||
|
} elseif (self::$stackedErrorLevels) {
|
||||||
|
self::$stackedErrors[] = array($this->loggers[$type], $message, $e);
|
||||||
|
} else {
|
||||||
|
try {
|
||||||
|
$this->isRecursive = true;
|
||||||
|
$this->loggers[$type][0]->log($this->loggers[$type][1], $message, $e);
|
||||||
|
$this->isRecursive = false;
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
$this->isRecursive = false;
|
||||||
|
|
||||||
|
throw $e;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -487,40 +489,44 @@ class ErrorHandler
|
|||||||
public static function handleFatalError(array $error = null)
|
public static function handleFatalError(array $error = null)
|
||||||
{
|
{
|
||||||
self::$reservedMemory = '';
|
self::$reservedMemory = '';
|
||||||
|
|
||||||
$handler = set_error_handler('var_dump', 0);
|
$handler = set_error_handler('var_dump', 0);
|
||||||
$handler = is_array($handler) ? $handler[0] : null;
|
$handler = is_array($handler) ? $handler[0] : null;
|
||||||
restore_error_handler();
|
restore_error_handler();
|
||||||
if ($handler instanceof self) {
|
|
||||||
if (null === $error) {
|
|
||||||
$error = error_get_last();
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
if (!$handler instanceof self) {
|
||||||
while (self::$stackedErrorLevels) {
|
return;
|
||||||
static::unstackErrors();
|
}
|
||||||
}
|
|
||||||
} catch (\Exception $exception) {
|
|
||||||
// Handled below
|
|
||||||
}
|
|
||||||
|
|
||||||
if ($error && ($error['type'] & (E_PARSE | E_ERROR | E_CORE_ERROR | E_COMPILE_ERROR))) {
|
if (null === $error) {
|
||||||
// Let's not throw anymore but keep logging
|
$error = error_get_last();
|
||||||
$handler->throwAt(0, true);
|
}
|
||||||
|
|
||||||
if (0 === strpos($error['message'], 'Allowed memory') || 0 === strpos($error['message'], 'Out of memory')) {
|
try {
|
||||||
$exception = new OutOfMemoryException($handler->levels[$error['type']].': '.$error['message'], 0, $error['type'], $error['file'], $error['line'], 2, false);
|
while (self::$stackedErrorLevels) {
|
||||||
} else {
|
static::unstackErrors();
|
||||||
$exception = new FatalErrorException($handler->levels[$error['type']].': '.$error['message'], 0, $error['type'], $error['file'], $error['line'], 2, true);
|
|
||||||
}
|
|
||||||
} elseif (!isset($exception)) {
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
} catch (\Exception $exception) {
|
||||||
|
// Handled below
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
if ($error && ($error['type'] & (E_PARSE | E_ERROR | E_CORE_ERROR | E_COMPILE_ERROR))) {
|
||||||
$handler->handleException($exception, $error);
|
// Let's not throw anymore but keep logging
|
||||||
} catch (FatalErrorException $e) {
|
$handler->throwAt(0, true);
|
||||||
// Ignore this re-throw
|
|
||||||
|
if (0 === strpos($error['message'], 'Allowed memory') || 0 === strpos($error['message'], 'Out of memory')) {
|
||||||
|
$exception = new OutOfMemoryException($handler->levels[$error['type']].': '.$error['message'], 0, $error['type'], $error['file'], $error['line'], 2, false);
|
||||||
|
} else {
|
||||||
|
$exception = new FatalErrorException($handler->levels[$error['type']].': '.$error['message'], 0, $error['type'], $error['file'], $error['line'], 2, true);
|
||||||
}
|
}
|
||||||
|
} elseif (!isset($exception)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
$handler->handleException($exception, $error);
|
||||||
|
} catch (FatalErrorException $e) {
|
||||||
|
// Ignore this re-throw
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user