Passed
Pull Request — master (#192)
by Wilmer
17:17
created

Validator   A

Complexity

Total Complexity 15

Size/Duplication

Total Lines 87
Duplicated Lines 0 %

Test Coverage

Coverage 62.5%

Importance

Changes 2
Bugs 0 Features 0
Metric Value
eloc 39
c 2
b 0
f 0
dl 0
loc 87
ccs 25
cts 40
cp 0.625
rs 10
wmc 15

4 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 3 1
B validate() 0 53 9
A withFormatter() 0 5 1
A normalizeDataSet() 0 11 4
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Validator;
6
7
use Yiisoft\Validator\DataSet\ArrayDataSet;
8
use Yiisoft\Validator\DataSet\ScalarDataSet;
9
use Yiisoft\Validator\Rule\Nested;
10
11
use function is_array;
12
use function is_object;
13
14
/**
15
 * Validator validates {@link DataSetInterface} against rules set for data set attributes.
16
 */
17
final class Validator implements ValidatorInterface
18
{
19
    private ?FormatterInterface $formatter;
20
21 12
    public function __construct(?FormatterInterface $formatter = null)
22
    {
23 12
        $this->formatter = $formatter;
24
    }
25
26
    /**
27
     * @param DataSetInterface|mixed|RulesProviderInterface $data
28
     * @param Rule[][] $rules
29
     * @psalm-param iterable<string, Rule[]> $rules
30
     */
31 12
    public function validate($data, iterable $rules = []): Result
32
    {
33 12
        $data = $this->normalizeDataSet($data);
34
35 12
        if ($data instanceof RulesProviderInterface) {
36 2
            $rules = $data->getRules();
37
        }
38
39 12
        $context = new ValidationContext($data);
40 12
        $result = new Result();
41
42 12
        foreach ($rules as $attribute => $attributeRules) {
43 12
            $ruleSet = new RuleSet($attributeRules);
44
45 12
            if ($this->formatter !== null) {
46
                $ruleSet = $ruleSet->withFormatter($this->formatter);
47
            }
48
49 12
            if ($attributeRules[0] instanceof Nested) {
50
                $nesteds = $attributeRules[0]->getOptions();
51
52
                foreach ($nesteds as $nested => $options) {
53
                    $values[$nested] = $data->getAttributeValue($attribute . '.' . $nested);
54
                }
55
56
                $tempResult = $ruleSet->validate(
57
                    $values,
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $values does not seem to be defined for all execution paths leading up to this point.
Loading history...
58
                    $context->withAttribute($attribute . '.' . $nested)
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $nested does not seem to be defined for all execution paths leading up to this point.
Loading history...
59
                );
60
61
                foreach ($tempResult->getErrors() as $error) {
62
                    $result->addError(
63
                        $error->getMessage(),
64
                        [$attribute . '.' . $nested, ...$error->getValuePath()],
65
                    );
66
                }
67
            } else {
68 12
                $tempResult = $ruleSet->validate(
69 12
                    $data->getAttributeValue($attribute),
70 12
                    $context->withAttribute($attribute)
71
                );
72
73 12
                foreach ($tempResult->getErrors() as $error) {
74 3
                    $result->addError($error->getMessage(), [$attribute, ...$error->getValuePath()]);
75
                }
76
            }
77
        }
78
79 12
        if ($data instanceof PostValidationHookInterface) {
80
            $data->processValidationResult($result);
81
        }
82
83 12
        return $result;
84
    }
85
86
    public function withFormatter(?FormatterInterface $formatter): self
87
    {
88
        $new = clone $this;
89
        $new->formatter = $formatter;
90
        return $new;
91
    }
92
93 12
    private function normalizeDataSet($data): DataSetInterface
94
    {
95 12
        if ($data instanceof DataSetInterface) {
96 5
            return $data;
97
        }
98
99 7
        if (is_object($data) || is_array($data)) {
100 1
            return new ArrayDataSet((array)$data);
101
        }
102
103 6
        return new ScalarDataSet($data);
104
    }
105
}
106