Completed
Push — master ( 63117e...c0048b )
by Sebastian
02:30
created

Filter::ruleToField()   B

Complexity

Conditions 5
Paths 7

Size

Total Lines 23
Code Lines 14

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 30

Importance

Changes 0
Metric Value
cc 5
eloc 14
nc 7
nop 1
dl 0
loc 23
ccs 0
cts 18
cp 0
crap 30
rs 8.5906
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * Linna Filter
5
 *
6
 * @author Sebastian Rapetti <[email protected]>
7
 * @copyright (c) 2017, Sebastian Rapetti
8
 * @license http://opensource.org/licenses/MIT MIT License
9
 */
10
declare(strict_types = 1);
11
12
namespace Linna\Filter;
13
14
use ReflectionClass;
15
16
/**
17
 * Filter.
18
 */
19
class Filter
20
{
21
    /**
22
     * @var array Rules for filtering.
23
     */
24
    private $rules = [];
25
26
    /**
27
     * @var array User data.
28
     */
29
    private $data = [];
30
31
    /**
32
     * @var array Error messages.
33
     */
34
    private $messages = [];
35
36
    /**
37
     * @var int Occurred errors.
38
     */
39
    private $errors = 0;
40
41
    /**
42
     * Class constructor.
43
     *
44
     * @param array $rules
45
     * @param array $data
46
     */
47
    public function __construct(array $rules, array $data)
48
    {
49
        $this->rules = $rules;
50
        $this->data = $data;
51
52
        $this->getRules();
53
    }
54
55
    /**
56
     * Return occurred error number.
57
     *
58
     * @return int
59
     */
60
    public function getErrors(): int
61
    {
62
        return $this->errors;
63
    }
64
65
    /**
66
     * Return error messages.
67
     *
68
     * @return array
69
     */
70
    public function getMessages(): array
71
    {
72
        return $this->messages;
73
    }
74
75
    /**
76
     * Return passed data.
77
     *
78
     * @return array
79
     */
80
    public function getData(): array
81
    {
82
        return $this->data;
83
    }
84
85
    /**
86
     * Get parsed rules.
87
     */
88
    private function getRules()
89
    {
90
        $rules = $this->rules;
91
92
        foreach ($rules as $rule) {
93
            $this->ruleToField((new RuleInterpreter($rule))->get());
94
        }
95
    }
96
97
    /**
98
     * Apply rules to a field.
99
     *
100
     * @param array $rules
101
     */
102
    private function ruleToField(array $rules)
103
    {
104
        foreach ($rules as $rule) {
105
            $field = $rule[0];
106
            $filter = $rule[2][0];
107
108
            $reflection = new ReflectionClass('Linna\Filter\Rules\\' . $filter);
109
            $instance = $reflection->newInstance();
110
            
111
            $received = '';
112
113
            if (isset($this->data[$field])) {
114
                $received = $this->data[$field];
115
            }
116
            
117
            if (call_user_func_array([$instance, 'validate'], $this->getArguments($rule[2][2], $rule[3], $received))) {
118
                $this->errors++;
119
                $this->messages[$field][$filter] = ['expected' => $rule[3], 'received' => $received];
120
                continue;
121
            }
122
            
123
            if ($reflection->hasMethod('sanitize')) {
124
                $instance->sanitize($this->data[$field]);
125
            }
126
        }
127
    }
128
129
    /**
130
     * Return arguments for validation.
131
     *
132
     * @param int $args
133
     * @param mixed $expected
134
     * @param mixed $received
135
     *
136
     * @return array
137
     */
138
    private function getArguments(int $args, $expected, $received): array
139
    {
140
        if ($args === 0) {
141
            return [$received];
142
        }
143
144
        if (is_array($expected)) {
145
            array_unshift($expected, $received);
146
            return $expected;
147
        }
148
149
        return [$received, $expected];
150
    }
151
}
152