Passed
Pull Request — master (#477)
by Alexander
03:43 queued 01:15
created

Email::__construct()   A

Complexity

Conditions 3
Paths 2

Size

Total Lines 17
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 12

Importance

Changes 0
Metric Value
cc 3
eloc 2
nc 2
nop 11
dl 0
loc 17
ccs 0
cts 0
cp 0
crap 12
rs 10
c 0
b 0
f 0

How to fix   Many Parameters   

Many Parameters

Methods with many parameters are not only hard to understand, but their parameters also often become inconsistent when you need more, or different data.

There are several approaches to avoid long parameter lists:

1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Validator\Rule;
6
7
use Attribute;
8
use Closure;
9
use RuntimeException;
10
use Yiisoft\Validator\Rule\Trait\SkipOnEmptyTrait;
11
use Yiisoft\Validator\Rule\Trait\SkipOnErrorTrait;
12
use Yiisoft\Validator\Rule\Trait\WhenTrait;
13
use Yiisoft\Validator\RuleWithOptionsInterface;
14
use Yiisoft\Validator\SkipOnEmptyInterface;
15
use Yiisoft\Validator\SkipOnErrorInterface;
16
use Yiisoft\Validator\WhenInterface;
17
18
use function function_exists;
19
20
/**
21
 * Validates that the value is a valid email address.
22
 *
23
 * @psalm-import-type WhenType from WhenInterface
24
 */
25
#[Attribute(Attribute::TARGET_PROPERTY | Attribute::IS_REPEATABLE)]
26
final class Email implements RuleWithOptionsInterface, SkipOnErrorInterface, WhenInterface, SkipOnEmptyInterface
27
{
28
    use SkipOnEmptyTrait;
29
    use SkipOnErrorTrait;
30
    use WhenTrait;
31
32 3
    /**
33
     * @param string $pattern The regular expression used to validate the value. See {@link https://www.regular-expressions.info/email.html}.
34
     * @param string $fullPattern The regular expression used to validate email addresses with the name part.
35
     * This property is used only when {@see $allowName} is `true`.
36
     * @param string $idnEmailPattern The regular expression used to validate complex emails when {@see $enableIdn} is `true`.
37
     * @param bool $allowName bool Whether to allow a name in the email address (e.g. "John Smith <[email protected]>").
38
     * Defaults to `false`. See {@see $fullPattern}.
39
     * @param bool $checkDns bool Whether to check email's domain exists and has either an A or MX record.
40
     * Be aware that this check can fail due to temporary DNS problems even if the email address is
41
     * valid and an email would be deliverable. Defaults to `false`.
42
     * @param bool $enableIdn Whether validation process should take IDN (internationalized domain names) into account.
43
     * Defaults to false meaning that validation of emails containing IDN will always fail.
44
     * Note that in order to use IDN validation you have to install and enable `intl` PHP extension,
45
     * otherwise an exception would be thrown.
46
     * @param string $incorrectInputMessage A message used when the input is incorrect.
47
     *
48
     * You may use the following placeholders in the message:
49
     *
50
     * - `{attribute}`: the label of the attribute being validated.
51
     * - `{type}`: the type of the attribute being validated.
52
     * @param string $message A message used when the value is not valid.
53
     *
54
     * You may use the following placeholders in the message:
55
     *
56
     * - `{attribute}`: the label of the attribute being validated.
57
     * - `{value}`: the value of the attribute being validated.
58
     * @param bool|callable|null $skipOnEmpty Whether to skip this rule if the value validated is empty. See {@see SkipOnEmptyInterface}.
59
     * @param bool $skipOnError Whether to skip this rule if any of the previous rules gave an error. See {@see SkipOnErrorInterface}.
60
     * @param Closure|null $when A callable to define a condition for applying the rule. See {@see WhenInterface}.
61
     * @psalm-param WhenType $when
62
     */
63
    public function __construct(
64
        private string $pattern = '/^[a-zA-Z0-9!#$%&\'*+\\/=?^_`{|}~-]+(?:\.[a-zA-Z0-9!#$%&\'*+\\/=?^_`{|}~-]+)*@(?:[a-zA-Z0-9](?:[a-zA-Z0-9-]*[a-zA-Z0-9])?\.)+[a-zA-Z0-9](?:[a-zA-Z0-9-]*[a-zA-Z0-9])?$/',
65
        private string $fullPattern = '/^[^@]*<[a-zA-Z0-9!#$%&\'*+\\/=?^_`{|}~-]+(?:\.[a-zA-Z0-9!#$%&\'*+\\/=?^_`{|}~-]+)*@(?:[a-zA-Z0-9](?:[a-zA-Z0-9-]*[a-zA-Z0-9])?\.)+[a-zA-Z0-9](?:[a-zA-Z0-9-]*[a-zA-Z0-9])?>$/',
66
        private string $idnEmailPattern = '/^([a-zA-Z0-9._%+-]+)@((\[\d{1,3}\.\d{1,3}\.\d{1,3}\.)|(([\w-]+\.)+))([a-zA-Z]{2,4}|\d{1,3})(\]?)$/',
67
        private bool $allowName = false,
68
        private bool $checkDns = false,
69
        private bool $enableIdn = false,
70
        private string $incorrectInputMessage = 'The value must have a string type.',
71
        private string $message = 'This value is not a valid email address.',
72
        private $skipOnEmpty = null,
73
        private bool $skipOnError = false,
74
        private Closure|null $when = null,
75
    ) {
76
        if ($enableIdn && !function_exists('idn_to_ascii')) {
77
            // Tested via separate CI configuration (see ".github/workflows/build.yml").
78
            // @codeCoverageIgnoreStart
79
            throw new RuntimeException('In order to use IDN validation intl extension must be installed and enabled.');
80
            // @codeCoverageIgnoreEnd
81
        }
82
    }
83
84
    public function getName(): string
85
    {
86 3
        return 'email';
87
    }
88
89
    /**
90
     * Get the regular expression used to validate the value.
91
     *
92
     * @return string The regular expression.
93
     *
94 1
     * @see $pattern
95
     */
96 1
    public function getPattern(): string
97
    {
98
        return $this->pattern;
99 83
    }
100
101 83
    /**
102
     * Get the regular expression used to validate email addresses with the name part.
103
     *
104 20
     * @return string The regular expression.
105
     *
106 20
     * @see $fullPattern
107
     */
108
    public function getFullPattern(): string
109 10
    {
110
        return $this->fullPattern;
111 10
    }
112
113
    /**
114 48
     * Get the regular expression used to validate complex emails when {@see $enableIdn} is `true`.
115
     *
116 48
     * @return string The regular expression.
117
     *
118
     * @see $idnEmailPattern
119 48
     */
120
    public function getIdnEmailPattern(): string
121 48
    {
122
        return $this->idnEmailPattern;
123
    }
124 94
125
    /**
126 94
     * Whether to allow a name in the email address (e.g. "John Smith <[email protected]>").
127
     *
128
     * @return bool Whether to allow a name in the email address.
129 5
     *
130
     * @see $allowName
131 5
     */
132
    public function isNameAllowed(): bool
133
    {
134 49
        return $this->allowName;
135
    }
136 49
137
    /**
138
     * Whether to check email's domain exists and has either an A or MX record.
139 4
     *
140
     * @return bool Whether to check email's domain exists and has either an A or MX record.
141
     *
142 4
     * @see $checkDns
143 4
     */
144 4
    public function shouldCheckDns(): bool
145 4
    {
146 4
        return $this->checkDns;
147 4
    }
148
149 4
    /**
150
     * Whether validation process should take IDN (internationalized domain names) into account.
151
     *
152
     * @return bool Whether validation process should take IDN (internationalized domain names) into account.
153 4
     *
154
     * @see $enableIdn
155
     */
156 4
    public function isIdnEnabled(): bool
157 4
    {
158
        return $this->enableIdn;
159
    }
160
161 99
    /**
162
     * Get a message used when the input is incorrect.
163 99
     *
164
     * @return string A message used when the input is incorrect.
165
     *
166
     * @see $incorrectInputMessage
167
     */
168
    public function getIncorrectInputMessage(): string
169
    {
170
        return $this->incorrectInputMessage;
171
    }
172
173
    /**
174
     * Get a message used when the value is not valid.
175
     *
176
     * @return string A message used when the value is not valid.
177
     *
178
     * @see $message
179
     */
180
    public function getMessage(): string
181
    {
182
        return $this->message;
183
    }
184
185
    public function getOptions(): array
186
    {
187
        return [
188
            'pattern' => $this->pattern,
189
            'fullPattern' => $this->fullPattern,
190
            'idnEmailPattern' => $this->idnEmailPattern,
191
            'allowName' => $this->allowName,
192
            'checkDns' => $this->checkDns,
193
            'enableIdn' => $this->enableIdn,
194
            'incorrectInputMessage' => [
195
                'template' => $this->incorrectInputMessage,
196
                'parameters' => [],
197
            ],
198
            'message' => [
199
                'template' => $this->message,
200
                'parameters' => [],
201
            ],
202
            'skipOnEmpty' => $this->getSkipOnEmptyOption(),
203
            'skipOnError' => $this->skipOnError,
204
        ];
205
    }
206
207
    public function getHandler(): string
208
    {
209
        return EmailHandler::class;
210
    }
211
}
212