-
Notifications
You must be signed in to change notification settings - Fork 189
Expand file tree
/
Copy pathHandler.php
More file actions
125 lines (98 loc) · 3.68 KB
/
Handler.php
File metadata and controls
125 lines (98 loc) · 3.68 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
<?php
namespace TightenCo\Jigsaw\Exceptions;
use Closure;
use Illuminate\Console\View\Components\BulletList;
use Illuminate\Console\View\Components\Error;
use Illuminate\Console\View\Components\Warn;
use Illuminate\Contracts\Debug\ExceptionHandler;
use Illuminate\Support\Traits\ReflectsClosures;
use Illuminate\View\ViewException;
use InvalidArgumentException;
use NunoMaduro\Collision\Adapters\Laravel\Inspector;
use NunoMaduro\Collision\Provider;
use Symfony\Component\Console\Application as ConsoleApplication;
use Symfony\Component\Console\Exception\CommandNotFoundException;
use Symfony\Component\Console\Exception\ExceptionInterface as SymfonyConsoleExceptionInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Throwable;
class Handler implements ExceptionHandler
{
use ReflectsClosures;
/** @var array<string, Closure> */
private array $exceptionMap = [];
public function report(Throwable $e): void
{
//
}
public function shouldReport(Throwable $e): bool
{
return true;
}
public function render($request, Throwable $e): void
{
//
}
/**
* @param OutputInterface $output
*/
public function renderForConsole($output, Throwable $e): void
{
if ($e instanceof CommandNotFoundException) {
$message = str($e->getMessage())->explode('.')->first();
if (! empty($alternatives = $e->getAlternatives())) {
(new Error($output))->render("{$message}. Did you mean one of these?");
(new BulletList($output))->render($alternatives);
} else {
(new Error($output))->render($message);
}
return;
}
if ($e instanceof SymfonyConsoleExceptionInterface) {
(new ConsoleApplication)->renderThrowable($e, $output);
return;
}
if ($e instanceof DeprecationException) {
// If the deprecation appears to have come from a compiled Blade view, wrap it in
// a ViewException and map it manually so Ignition will add the uncompiled path
if (preg_match('/cache\/\w+\.php$/', $e->getFile()) === 1) {
$e = $this->mapException(
new ViewException("{$e->getMessage()} (View: )", 0, 1, $e->getFile(), $e->getLine(), $e),
);
}
(new Warn($output))->render("{$e->getMessage()} in {$e->getFile()} on line {$e->getLine()}");
return;
}
$e = $this->mapException($e);
/** @var Provider $provider */
$provider = app(Provider::class);
$handler = $provider->register()->getHandler()->setOutput($output);
$handler->setInspector(new Inspector($e));
$handler->handle();
}
public function map(Closure|string $from, Closure|string|null $to = null): static
{
if (is_string($to)) {
$to = fn ($exception) => new $to('', 0, $exception);
}
if (is_callable($from) && is_null($to)) {
$from = $this->firstClosureParameterType($to = $from);
}
if (! is_string($from) || ! $to instanceof Closure) {
throw new InvalidArgumentException('Invalid exception mapping.');
}
$this->exceptionMap[$from] = $to;
return $this;
}
protected function mapException(Throwable $e): Throwable
{
if (method_exists($e, 'getInnerException') && ($inner = $e->getInnerException()) instanceof Throwable) {
return $inner;
}
foreach ($this->exceptionMap as $class => $mapper) {
if ($e instanceof $class) {
return $mapper($e);
}
}
return $e;
}
}