Completed
Push — master ( eeebc2...21cf4a )
by Matze
03:31
created

Controller::handleRouteAnnotation()   B

Complexity

Conditions 2
Paths 2

Size

Total Lines 26
Code Lines 15

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 5
CRAP Score 2.0185

Importance

Changes 1
Bugs 0 Features 1
Metric Value
c 1
b 0
f 1
dl 0
loc 26
ccs 5
cts 6
cp 0.8333
rs 8.8571
cc 2
eloc 15
nc 2
nop 5
crap 2.0185
1
<?php
2
3
namespace BrainExe\Core\Annotations\Builder;
4
5
use BrainExe\Annotations\Annotations\Service;
6
use BrainExe\Annotations\Builder\ServiceDefinition;
7
use BrainExe\Core\Annotations\Guest;
8
use BrainExe\Core\Annotations\Role;
9
use BrainExe\Core\Annotations\Route;
10
use BrainExe\Core\DependencyInjection\CompilerPass\ControllerCompilerPass;
11
use BrainExe\Core\Annotations\Controller as ControllerAnnotation;
12
use ReflectionClass;
13
use ReflectionMethod;
14
use Symfony\Component\DependencyInjection\Definition;
15
16
class Controller extends ServiceDefinition
17
{
18
19
    /**
20 2
     * @param ReflectionClass $reflectionClass
21
     * @param ControllerAnnotation|Service $annotation
22
     * @return array
23 2
     */
24
    public function build(ReflectionClass $reflectionClass, $annotation)
25
    {
26
        /** @var Definition $definition */
27
        list ($serviceId, $definition) = parent::build(
28 2
            $reflectionClass,
29
            $annotation
30
        );
31 2
        $serviceId = sprintf('__controller.%s', $serviceId);
32 2
33
        $definition->addTag(ControllerCompilerPass::CONTROLLER_TAG);
34
        $definition->setPublic(true);
35
        $definition->setShared(false);
36
37
        foreach ($reflectionClass->getMethods() as $method) {
38
            /** @var Route $routeAnnotation */
39
            $routeAnnotation = $this->reader->getMethodAnnotation($method, Route::class);
40 2
41
            if ($routeAnnotation) {
42 2
                $this->handleRouteAnnotation(
43
                    $annotation,
0 ignored issues
show
Compatibility introduced by
$annotation of type object<BrainExe\Annotations\Annotations\Service> is not a sub-type of object<BrainExe\Core\Annotations\Controller>. It seems like you assume a child class of the class BrainExe\Annotations\Annotations\Service to be always present.

This check looks for parameters that are defined as one type in their type hint or doc comment but seem to be used as a narrower type, i.e an implementation of an interface or a subclass.

Consider changing the type of the parameter or doing an instanceof check before assuming your parameter is of the expected type.

Loading history...
44 2
                    $method,
45
                    $routeAnnotation,
46 2
                    $serviceId,
47
                    $definition
48 2
                );
49
            }
50 2
        }
51
52
        return [$serviceId, $definition];
53 2
    }
54
55 2
56
    /**
57
     * @param Route $routeAnnotation
58
     * @param ReflectionMethod $method
59
     * @param string $serviceId
60
     * @param Guest $guestAnnotation
61
     * @param Role $roleAnnotation
62 2
     */
63
    protected function setDefaults(
64
        Route $routeAnnotation,
65 2
        ReflectionMethod $method,
66
        string $serviceId,
67
        Guest $guestAnnotation = null,
68
        Role $roleAnnotation = null
69
    ) {
70 2
        $defaults = $routeAnnotation->getDefaults();
71
        $defaults['_controller'] = [
72 2
            $serviceId,
73 2
            $method->getName()
74 2
        ];
75
76
        if ($guestAnnotation) {
77
            $defaults['_guest'] = true;
78
        }
79
80
        if ($roleAnnotation) {
81
            $defaults['_role'] = $roleAnnotation->role;
82
        }
83
84 2
        $routeAnnotation->setDefaults($defaults);
85
    }
86
87
    /**
88
     * @param ControllerAnnotation $annotation
89
     * @param ReflectionMethod $method
90 2
     * @param Route $routeAnnotation
91 2
     * @param string $serviceId
92 2
     * @param Definition $definition
93 2
     */
94
    private function handleRouteAnnotation(
95 2
        ControllerAnnotation $annotation,
96 2
        ReflectionMethod$method,
97
        Route $routeAnnotation,
98
        string $serviceId,
99 2
        Definition $definition
100
    ) {
101
        /** @var Guest $guestAnnotation */
102
        $guestAnnotation = $this->reader->getMethodAnnotation($method, Guest::class);
103 2
104 2
        /** @var Role $roleAnnotation */
105
        $roleAnnotation = $this->reader->getMethodAnnotation($method, Role::class);
106
107
        $this->setDefaults($routeAnnotation, $method, $serviceId, $guestAnnotation, $roleAnnotation);
108
109
        if ($annotation->requirements) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $annotation->requirements of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
110
            $routeAnnotation->setRequirements(
111
                array_merge(
112
                    $routeAnnotation->getRequirements(),
113
                    $annotation->requirements
114
                )
115
            );
116
        }
117
118
        $definition->addTag(ControllerCompilerPass::ROUTE_TAG, [$routeAnnotation]);
119
    }
120
}
121