Lines 91.66% 11 / 12
Functions and Methods 75.00% 3 / 4
Classes and Traits 0.00% 0 / 1
Name Lines Functions and Methods CRAP Classes and Traits
LoopErrorReporter 91.66% 11 / 12 75.00% 3 / 4 6.02 0.00% 0 / 1
 __construct 100.00% 1 / 1 100.00% 1 / 1 1
 install 100.00% 5 / 5 100.00% 1 / 1 2
 restorePrevious 80.00% 4 / 5 0.00% 0 / 1 2.03
 reportError 100.00% 1 / 1 100.00% 1 / 1 1
1<?php
2
3declare(strict_types=1);
4
5namespace Stewart\Runtime\Worker;
6
7use Closure;
8use Revolt\EventLoop;
9use Stewart\Runtime\Lifecycle\AppFailurePhase;
10use Stewart\Runtime\Model\ResourceScope;
11use Throwable;
12
13final class LoopErrorReporter
14{
15    private const string LOOP_ORIGIN = 'event loop';
16
17    /** @var (Closure(Throwable): void)|null */
18    private ?Closure $previous = null;
19
20    private bool $installed = false;
21
22    public function __construct(private readonly AppFailureReporter $failures) {}
23
24    public function install(): void
25    {
26        if ($this->installed) {
27            return;
28        }
29
30        $this->previous = EventLoop::getErrorHandler();
31        EventLoop::setErrorHandler($this->reportError(...));
32        $this->installed = true;
33    }
34
35    public function restorePrevious(): void
36    {
37        if (!$this->installed) {
38            return;
39        }
40
41        EventLoop::setErrorHandler($this->previous);
42        $this->previous = null;
43        $this->installed = false;
44    }
45
46    private function reportError(Throwable $error): void
47    {
48        $this->failures->report(ResourceScope::shared(), AppFailurePhase::Handler, $error, self::LOOP_ORIGIN);
49    }
50}