InputParam::__invoke()   B
last analyzed

Complexity

Conditions 8
Paths 10

Size

Total Lines 31
Code Lines 17

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 8
eloc 17
c 1
b 0
f 0
nc 10
nop 3
dl 0
loc 31
rs 8.4444
1
<?php
2
3
declare(strict_types=1);
4
5
namespace BEAR\Resource;
6
7
use InvalidArgumentException;
8
use Override;
9
use Ray\Di\InjectorInterface;
10
use Ray\InputQuery\InputQueryInterface;
11
use ReflectionNamedType;
12
use ReflectionParameter;
13
14
use function array_key_exists;
15
use function assert;
16
use function class_exists;
17
18
/** @psalm-import-type Query from Types */
19
final class InputParam implements ParamInterface
20
{
21
    /** @param InputQueryInterface<object> $inputQuery */
22
    public function __construct(
23
        private readonly InputQueryInterface $inputQuery,
24
        private readonly ReflectionParameter $parameter,
25
    ) {
26
    }
27
28
    /**
29
     * {@inheritDoc}
30
     */
31
    #[Override]
32
    public function __invoke(string $varName, array $query, InjectorInterface $injector)
33
    {
34
        $type = $this->parameter->getType();
35
        if ($type instanceof ReflectionNamedType && ! $type->isBuiltin()) {
36
            $inputClass = $type->getName();
37
            assert(class_exists($inputClass));
38
39
            return $this->inputQuery->newInstance($inputClass, $query);
40
        }
41
42
        // For built-in types, handle missing values explicitly
43
        if (array_key_exists($varName, $query)) {
44
            return $query[$varName];
45
        }
46
47
        $type = $this->parameter->getType();
48
        $isRequired = true;
49
        if ($type instanceof ReflectionNamedType && $type->allowsNull()) {
50
            $isRequired = false;
51
        }
52
53
        if ($this->parameter->isDefaultValueAvailable()) {
54
            $isRequired = false;
55
        }
56
57
        if ($isRequired) {
58
            throw new InvalidArgumentException("Missing required parameter: {$varName}");
59
        }
60
61
        return null;
62
    }
63
}
64