Passed
Pull Request — master (#222)
by Alexander
04:33 queued 02:13
created

CompareTo::getMessage()   B

Complexity

Conditions 10
Paths 10

Size

Total Lines 23
Code Lines 19

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 18
CRAP Score 10.0145

Importance

Changes 0
Metric Value
cc 10
eloc 19
nc 10
nop 0
dl 0
loc 23
ccs 18
cts 19
cp 0.9474
crap 10.0145
rs 7.6666
c 0
b 0
f 0

How to fix   Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Validator\Rule;
6
7
use Attribute;
8
use Closure;
9
use InvalidArgumentException;
10
use JetBrains\PhpStorm\ArrayShape;
11
use RuntimeException;
12
use Yiisoft\Validator\ParametrizedRuleInterface;
13
use Yiisoft\Validator\PreValidatableRuleInterface;
14
use Yiisoft\Validator\Rule\Trait\HandlerClassNameTrait;
0 ignored issues
show
Bug introduced by
A parse error occurred: Syntax error, unexpected T_TRAIT, expecting T_STRING or '{' on line 14 at column 27
Loading history...
15
use Yiisoft\Validator\Rule\Trait\PreValidatableTrait;
16
use Yiisoft\Validator\Rule\Trait\RuleNameTrait;
17
18
/**
19
 * Compares the specified value with another value.
20
 *
21
 * The value being compared with a constant {@see CompareTo::$compareValue}, which is set
22
 * in the constructor.
23
 *
24
 * It supports different comparison operators, specified
25
 * via the {@see CompareTo::$operator}.
26
 *
27
 * The default comparison function is based on string values, which means the values
28
 * are compared byte by byte. When comparing numbers, make sure to change {@see CompareTo::$type} to
29
 * {@see CompareTo::TYPE_NUMBER} to enable numeric comparison.
30
 */
31
#[Attribute(Attribute::TARGET_PROPERTY)]
32
final class CompareTo implements ParametrizedRuleInterface, PreValidatableRuleInterface
33
{
34
    use HandlerClassNameTrait;
35
    use PreValidatableTrait;
36
    use RuleNameTrait;
37
38
    /**
39
     * Constant for specifying the comparison as string values.
40
     * No conversion will be done before comparison.
41
     *
42
     * @see $type
43
     */
44
    public const TYPE_STRING = 'string';
45
    /**
46
     * Constant for specifying the comparison as numeric values.
47
     * String values will be converted into numbers before comparison.
48
     *
49
     * @see $type
50
     */
51
    public const TYPE_NUMBER = 'number';
52
53
    private array $validOperators = [
54
        '==' => 1,
55
        '===' => 1,
56
        '!=' => 1,
57
        '!==' => 1,
58
        '>' => 1,
59
        '>=' => 1,
60
        '<' => 1,
61
        '<=' => 1,
62
    ];
63
64 2
    public function __construct(
65
        /**
66
         * @var mixed the constant value to be compared with.
67
         */
68
        private $compareValue,
69
        /**
70
         * @var string|null user-defined error message
71
         */
72
        private ?string $message = null,
73
        /**
74
         * @var string the type of the values being compared.
75
         */
76
        private string $type = self::TYPE_STRING,
77
        /**
78
         * @var string the operator for comparison. The following operators are supported:
79
         *
80
         * - `==`: check if two values are equal. The comparison is done is non-strict mode.
81
         * - `===`: check if two values are equal. The comparison is done is strict mode.
82
         * - `!=`: check if two values are NOT equal. The comparison is done is non-strict mode.
83
         * - `!==`: check if two values are NOT equal. The comparison is done is strict mode.
84
         * - `>`: check if value being validated is greater than the value being compared with.
85
         * - `>=`: check if value being validated is greater than or equal to the value being compared with.
86
         * - `<`: check if value being validated is less than the value being compared with.
87
         * - `<=`: check if value being validated is less than or equal to the value being compared with.
88
         *
89
         * When you want to compare numbers, make sure to also chabge @see CompareTo::$type} to
90
         * {@see CompareTo::TYPE_NUMBER}.
91
         */
92
        private string $operator = '==',
93
        private bool $skipOnEmpty = false,
94
        private bool $skipOnError = false,
95
        private ?Closure $when = null,
96
    ) {
97 2
        if (!isset($this->validOperators[$operator])) {
98
            throw new InvalidArgumentException("Operator \"$operator\" is not supported.");
99
        }
100
    }
101
102
    /**
103
     * @return mixed
104
     */
105 30
    public function getCompareValue(): mixed
106
    {
107 30
        return $this->compareValue;
108
    }
109
110
    /**
111
     * @return string
112
     */
113 30
    public function getType(): string
114
    {
115 30
        return $this->type;
116
    }
117
118
    /**
119
     * @return string
120
     */
121 30
    public function getOperator(): string
122
    {
123 30
        return $this->operator;
124
    }
125
126 22
    public function getMessage(): string
127
    {
128 22
        return $this->message ?? match ($this->operator) {
129 6
            '==', '===' => 'Value must be equal to "{compareValue}".',
130 7
            '!=', '!==' => 'Value must not be equal to "{compareValue}".',
131 2
            '>' => 'Value must be greater than "{compareValue}".',
132 2
            '>=' => 'Value must be greater than or equal to "{compareValue}".',
133 2
            '<' => 'Value must be less than "{compareValue}".',
134 1
            '<=' => 'Value must be less than or equal to "{compareValue}".',
135 22
            default => throw new RuntimeException("Unknown operator: {$this->operator}"),
136
        };
137
    }
138
139 7
    #[ArrayShape([
140
        'compareValue' => '',
141
        'message' => 'array',
142
        'type' => 'string',
143
        'operator' => 'string',
144
        'skipOnEmpty' => 'bool',
145
        'skipOnError' => 'bool',
146
    ])]
147
    public function getOptions(): array
148
    {
149
        return [
150 7
            'compareValue' => $this->compareValue,
151
            'message' => [
152 7
                'message' => $this->getMessage(),
153 7
                'parameters' => ['compareValue' => $this->compareValue],
154
            ],
155 7
            'type' => $this->type,
156 7
            'operator' => $this->operator,
157 7
            'skipOnEmpty' => $this->skipOnEmpty,
158 7
            'skipOnError' => $this->skipOnError,
159
        ];
160
    }
161
}
162