Passed
Pull Request — master (#99)
by Def
02:18
created

Validator::translate()   A

Complexity

Conditions 4
Paths 4

Size

Total Lines 15
Code Lines 7

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 8
CRAP Score 4

Importance

Changes 0
Metric Value
cc 4
eloc 7
nc 4
nop 2
dl 0
loc 15
ccs 8
cts 8
cp 1
crap 4
rs 10
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Validator;
6
7
use Yiisoft\Translator\TranslatorInterface;
8
9
/**
10
 * Validator validates {@link DataSetInterface} against rules set for data set attributes.
11
 */
12
final class Validator implements ValidatorInterface
13
{
14
    /**
15
     * @var Rules[] $attributeRules
16
     */
17
    private array $attributeRules = [];
18
19 9
    public function __construct(iterable $rules = [])
20
    {
21 9
        foreach ($rules as $attribute => $ruleSets) {
22 8
            if ($ruleSets instanceof Rule) {
23 3
                $ruleSets = [$ruleSets];
24 8
            } elseif (!is_iterable($ruleSets)) {
25 1
                throw new \InvalidArgumentException('Attribute rules should be either an instance of Rule class or an array of instances of Rule class.');
26
            }
27 7
            foreach ($ruleSets as $rule) {
28 7
                $this->addRule($attribute, $rule);
29
            }
30
        }
31 8
    }
32
33 5
    public function validate(DataSetInterface $dataSet): ResultSet
34
    {
35 5
        $results = new ResultSet();
36 5
        foreach ($this->attributeRules as $attribute => $rules) {
37 5
            $results->addResult(
38 5
                $attribute,
39 5
                $rules->validate($dataSet->getAttributeValue($attribute), $dataSet)
40
            );
41
        }
42 5
        return $results;
43
    }
44
45
    /**
46
     * @param string $attribute
47
     * @param callable|Rule $rule
48
     */
49 8
    public function addRule(string $attribute, $rule): void
50
    {
51 8
        if (!isset($this->attributeRules[$attribute])) {
52 8
            $this->attributeRules[$attribute] = new Rules([]);
53
        }
54 8
        $this->attributeRules[$attribute]->add($rule);
55 8
    }
56
57
    /**
58
     * Return all attribute rules as array.
59
     *
60
     * For example:
61
     *
62
     * ```php
63
     * [
64
     *    'amount' => [
65
     *        [
66
     *            'number',
67
     *            'integer' => true,
68
     *            'max' => 100,
69
     *            'notANumberMessage' => 'Value must be an integer.',
70
     *            'tooBigMessage' => 'Value must be no greater than 100.'
71
     *        ],
72
     *        ['callback'],
73
     *    ],
74
     *    'name' => [
75
     *        'hasLength',
76
     *        'max' => 20,
77
     *        'message' => 'Value must contain at most 20 characters.'
78
     *    ],
79
     * ]
80
     * ```
81
     *
82
     * @return array
83
     */
84 3
    public function asArray(?TranslatorInterface $translator = null): array
85
    {
86 3
        $rulesOfArray = [];
87 3
        foreach ($this->attributeRules as $attribute => $rules) {
88 3
            $rulesOfArray[$attribute] = $rules->asArray($translator);
89
        }
90 3
        return $rulesOfArray;
91
    }
92
93
    /**
94
     * @param mixed $translatableObject
95
     * @param TranslatorInterface|null $translator
96
     *
97
     * @return mixed
98
     */
99 4
    public static function translate($translatableObject, ?TranslatorInterface $translator)
100
    {
101 4
        if ($translatableObject instanceof ErrorMessage) {
102 4
            return $translatableObject->getMessage($translator);
103
        }
104
105 3
        if (!is_iterable($translatableObject)) {
106 1
            return $translatableObject;
107
        }
108
109 3
        foreach ($translatableObject as &$value) {
110 3
            $value = self::translate($value, $translator);
111
        }
112
113 3
        return $translatableObject;
114
    }
115
}
116