Passed
Push — main ( ee7b7b...414146 )
by Fractal
02:40
created

RequestConverter   A

Complexity

Total Complexity 9

Size/Duplication

Total Lines 49
Duplicated Lines 0 %

Test Coverage

Coverage 100%

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 23
c 1
b 0
f 0
dl 0
loc 49
ccs 23
cts 23
cp 1
rs 10
wmc 9

3 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 8 1
A validate() 0 4 2
A convert() 0 27 6
1
<?php
2
3
declare(strict_types=1);
4
5
namespace FRZB\Component\RequestMapper\Converter;
6
7
use FRZB\Component\DependencyInjection\Attribute\AsService;
8
use FRZB\Component\RequestMapper\Data\ConverterData;
9
use FRZB\Component\RequestMapper\Data\ValidationError;
10
use FRZB\Component\RequestMapper\Exception\ClassExtractorException;
11
use FRZB\Component\RequestMapper\Exception\ConverterException;
12
use FRZB\Component\RequestMapper\Exception\ValidationException;
13
use FRZB\Component\RequestMapper\Extractor\ConstraintExtractor;
14
use FRZB\Component\RequestMapper\Extractor\DiscriminatorMapExtractor;
15
use FRZB\Component\RequestMapper\Extractor\ParametersExtractor;
16
use FRZB\Component\RequestMapper\Parser\ExceptionConverterInterface as ExceptionConverter;
17
use Symfony\Component\Serializer\Annotation\DiscriminatorMap;
18
use Symfony\Component\Serializer\Normalizer\DenormalizerInterface as Denormalizer;
19
use Symfony\Component\Validator\Constraints\Collection;
20
use Symfony\Component\Validator\Validator\ValidatorInterface as Validator;
21
22
#[AsService]
23 1
class RequestConverter implements ConverterInterface
24
{
25
    private const DENORMALIZE_TYPE = 'array';
26
27 16
    public function __construct(
28
        private Validator $validator,
29
        private Denormalizer $denormalizer,
30
        private ExceptionConverter $exceptionConverter,
31
        private DiscriminatorMapExtractor $classExtractor,
32
        private ConstraintExtractor $constraintExtractor,
33
        private ParametersExtractor $parametersExtractor,
34
    ) {
35 16
    }
36
37 16
    public function convert(ConverterData $data): object
38
    {
39
        try {
40 16
            $parameters = $data->getRequest()->request->all();
41 16
            $class = $this->classExtractor->extract($data->getParameterClass(), $parameters);
0 ignored issues
show
Bug introduced by
It seems like $data->getParameterClass() can also be of type null; however, parameter $class of FRZB\Component\RequestMa...MapExtractor::extract() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

41
            $class = $this->classExtractor->extract(/** @scrutinizer ignore-type */ $data->getParameterClass(), $parameters);
Loading history...
42 2
        } catch (ClassExtractorException $e) {
43 1
            throw ValidationException::fromErrors(ValidationError::fromTypeAndClassExtractorException(DiscriminatorMap::class, $e));
44 1
        } catch (\Throwable $e) {
45 1
            throw ConverterException::fromThrowable($e);
46
        }
47
48 14
        if ($data->isValidationNeeded()) {
49 14
            $constraints = $this->constraintExtractor->extract($class);
50 14
            $parameters = $this->parametersExtractor->extract($data->getParameterClass(), $parameters);
0 ignored issues
show
Bug introduced by
It seems like $data->getParameterClass() can also be of type null; however, parameter $class of FRZB\Component\RequestMa...ersExtractor::extract() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

50
            $parameters = $this->parametersExtractor->extract(/** @scrutinizer ignore-type */ $data->getParameterClass(), $parameters);
Loading history...
51
52 14
            $this->validate($parameters, $data->getValidationGroups(), $constraints);
53
        }
54
55
        try {
56 12
            $object = $this->denormalizer->denormalize($parameters, $class, self::DENORMALIZE_TYPE, $data->getSerializerContext());
57 2
        } catch (\TypeError $e) {
58 1
            throw ValidationException::fromErrors($this->exceptionConverter->convert($e, $parameters));
59 1
        } catch (\Throwable $e) {
60 1
            throw ConverterException::fromThrowable($e);
61
        }
62
63 10
        return $object;
64
    }
65
66
    /** @throws ValidationException */
67 14
    private function validate(mixed $target, array $validationGroups, ?Collection $constraints = null): void
68
    {
69 14
        if (($violations = $this->validator->validate($target, $constraints, $validationGroups))->count()) {
70 2
            throw ValidationException::fromConstraintViolationList($violations);
71
        }
72 12
    }
73
}
74