diff --git a/CHANGELOG.md b/CHANGELOG.md index 9d03717..aa2d639 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,7 +1,8 @@ # Yii Error Handler Change Log -## 3.3.1 under development +## 3.4.0 under development +- Enh #125: Add error code & show function arguments (@xepozz) - Enh #130: Pass exception message instead of rendered exception to logger in `ErrorHandler` (@olegbaturin) - Enh #133: Extract response generator from `ErrorCatcher` middleware into separate `ThrowableResponseFactory` class (@olegbaturin) diff --git a/src/ErrorHandler.php b/src/ErrorHandler.php index bafea8e..79ec64d 100644 --- a/src/ErrorHandler.php +++ b/src/ErrorHandler.php @@ -134,7 +134,8 @@ public function register(): void return true; } - $backtrace = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS); + $backtrace = debug_backtrace(); + array_shift($backtrace); throw new ErrorException($message, $severity, $severity, $file, $line, null, $backtrace); }); diff --git a/src/Renderer/HtmlRenderer.php b/src/Renderer/HtmlRenderer.php index d01b87b..f51b561 100644 --- a/src/Renderer/HtmlRenderer.php +++ b/src/Renderer/HtmlRenderer.php @@ -256,22 +256,34 @@ public function renderCallStack(Throwable $t, array $trace = []): string [], ); - $length = count($trace); - for ($i = 0; $i < $length; ++$i) { - $file = !empty($trace[$i]['file']) ? $trace[$i]['file'] : null; - $line = !empty($trace[$i]['line']) ? $trace[$i]['line'] : null; - $class = !empty($trace[$i]['class']) ? $trace[$i]['class'] : null; - $args = !empty($trace[$i]['args']) ? $trace[$i]['args'] : []; + $index = 1; + if ($t instanceof ErrorException) { + $index = 0; + } + + foreach ($trace as $traceItem) { + $file = !empty($traceItem['file']) ? $traceItem['file'] : null; + $line = !empty($traceItem['line']) ? $traceItem['line'] : null; + $class = !empty($traceItem['class']) ? $traceItem['class'] : null; + $args = !empty($traceItem['args']) ? $traceItem['args'] : []; $parameters = []; $function = null; - if (!empty($trace[$i]['function']) && $trace[$i]['function'] !== 'unknown') { - $function = $trace[$i]['function']; - if ($class !== null && !str_contains($function, '{closure}')) { - $parameters = (new \ReflectionMethod($class, $function))->getParameters(); + if (!empty($traceItem['function']) && $traceItem['function'] !== 'unknown') { + $function = $traceItem['function']; + if (!str_contains($function, '{closure}')) { + try { + if ($class !== null && class_exists($class)) { + $parameters = (new \ReflectionMethod($class, $function))->getParameters(); + } elseif (function_exists($function)) { + $parameters = (new \ReflectionFunction($function))->getParameters(); + } + } catch (\ReflectionException) { + // pass + } } } - $index = $i + 2; + $index++; if ($this->isVendorFile($file)) { $vendor[$index] = $this->renderCallStackItem( @@ -588,7 +600,7 @@ private function groupVendorCallStackItems(array $items): array $groupedItems[$groupIndex][$index] = $item; } - /** @psalm-var array> $groupedItems It's need for Psalm <=4.30 only. */ + /** @psalm-var array> $groupedItems It's needed for Psalm <=4.30 only. */ return $groupedItems; } diff --git a/templates/development.php b/templates/development.php index c6a48c2..669dc1e 100644 --- a/templates/development.php +++ b/templates/development.php @@ -73,6 +73,7 @@ + (Code #getCode() ?>)