Completed
Push — master ( 36b156...03fea2 )
by Christian
04:21
created

Dispatcher::getOrderedDispatcherArguments()   A

Complexity

Conditions 5
Paths 5

Size

Total Lines 18
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 5
eloc 9
nc 5
nop 1
dl 0
loc 18
rs 9.6111
c 0
b 0
f 0
1
<?php
2
namespace RemotelyLiving\PHPDNS\Observability\Traits;
3
4
use RemotelyLiving\PHPDNS\Observability\Events\ObservableEventAbstract;
5
use Symfony\Component\EventDispatcher\EventDispatcher;
6
use Symfony\Component\EventDispatcher\EventDispatcherInterface;
7
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
8
9
trait Dispatcher
10
{
11
    /**
12
     * @var \Symfony\Component\EventDispatcher\EventDispatcherInterface|null
13
     */
14
    private $dispatcher = null;
15
16
    public function setDispatcher(EventDispatcherInterface $dispatcher): void
17
    {
18
        $this->dispatcher = $dispatcher;
19
    }
20
21
    public function addSubscriber(EventSubscriberInterface $subscriber): void
22
    {
23
        $this->getDispatcher()->addSubscriber($subscriber);
24
    }
25
26
    public function addListener(string $eventName, callable $listener, int $priority = 0): void
27
    {
28
        $this->getDispatcher()->addListener($eventName, $listener, $priority);
29
    }
30
31
    public function dispatch(ObservableEventAbstract $event): void
32
    {
33
        call_user_func_array([$this->getDispatcher(), 'dispatch'], $this->getOrderedDispatcherArguments($event));
34
    }
35
36
    private function getOrderedDispatcherArguments(ObservableEventAbstract $event) : array
37
    {
38
        $reflection = new \ReflectionClass($this->getDispatcher());
39
40
        foreach ($reflection->getMethods(\ReflectionMethod::IS_PUBLIC) as $method) {
41
            if ($method->getName() !== 'dispatch') {
42
                continue;
43
            }
44
            
45
            // handle the reverse argument BC from symfony dispatcher 3.* to 4.*
46
            foreach ($method->getParameters() as $parameter) {
47
                return ($parameter->getName() === 'event')
48
                    ? [$event, $event::getName()]
49
                    : [$event::getName(), $event];
50
            }
51
        }
52
53
        throw new \LogicException('Could not determine argument order for dispatcher');
54
    }
55
56
    private function getDispatcher(): EventDispatcherInterface
57
    {
58
        if ($this->dispatcher === null) {
59
            $this->dispatcher = new EventDispatcher();
60
        }
61
62
        return $this->dispatcher;
63
    }
64
}
65