Failed Conditions
Pull Request — master (#118)
by Gert de
03:12 queued 02:05
created

Assert::notWhitespaceOnly()   A

Complexity

Conditions 3
Paths 2

Size

Total Lines 9

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 6
CRAP Score 3

Importance

Changes 0
Metric Value
dl 0
loc 9
ccs 6
cts 6
cp 1
rs 9.9666
c 0
b 0
f 0
cc 3
nc 2
nop 2
crap 3
1
<?php
2
3
/*
4
 * This file is part of the webmozart/assert package.
5
 *
6
 * (c) Bernhard Schussek <[email protected]>
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
namespace Webmozart\Assert;
13
14
use ArrayAccess;
15
use BadMethodCallException;
16
use Closure;
17
use Countable;
18
use Exception;
19
use InvalidArgumentException;
20
use Throwable;
21
use Traversable;
22
23
/**
24
 * Efficient assertions to validate the input/output of your methods.
25
 *
26
 * @method static void nullOrString($value, $message = '')
27
 * @method static void nullOrStringNotEmpty($value, $message = '')
28
 * @method static void nullOrInteger($value, $message = '')
29
 * @method static void nullOrIntegerish($value, $message = '')
30
 * @method static void nullOrFloat($value, $message = '')
31
 * @method static void nullOrNumeric($value, $message = '')
32
 * @method static void nullOrNatural($value, $message = '')
33
 * @method static void nullOrBoolean($value, $message = '')
34
 * @method static void nullOrScalar($value, $message = '')
35
 * @method static void nullOrObject($value, $message = '')
36
 * @method static void nullOrResource($value, $type = null, $message = '')
37
 * @method static void nullOrIsCallable($value, $message = '')
38
 * @method static void nullOrIsArray($value, $message = '')
39
 * @method static void nullOrIsTraversable($value, $message = '')
40
 * @method static void nullOrIsArrayAccessible($value, $message = '')
41
 * @method static void nullOrIsCountable($value, $message = '')
42
 * @method static void nullOrIsIterable($value, $message = '')
43
 * @method static void nullOrIsInstanceOf($value, $class, $message = '')
44
 * @method static void nullOrNotInstanceOf($value, $class, $message = '')
45
 * @method static void nullOrIsInstanceOfAny($value, $classes, $message = '')
46
 * @method static void nullOrIsEmpty($value, $message = '')
47
 * @method static void nullOrNotEmpty($value, $message = '')
48
 * @method static void nullOrTrue($value, $message = '')
49
 * @method static void nullOrFalse($value, $message = '')
50
 * @method static void nullOrIp($value, $message = '')
51
 * @method static void nullOrIpv4($value, $message = '')
52
 * @method static void nullOrIpv6($value, $message = '')
53
 * @method static void nullOrEmail($value, $message = '')
54
 * @method static void nullOrUniqueValues($values, $message = '')
55
 * @method static void nullOrEq($value, $expect, $message = '')
56
 * @method static void nullOrNotEq($value, $expect, $message = '')
57
 * @method static void nullOrSame($value, $expect, $message = '')
58
 * @method static void nullOrNotSame($value, $expect, $message = '')
59
 * @method static void nullOrGreaterThan($value, $limit, $message = '')
60
 * @method static void nullOrGreaterThanEq($value, $limit, $message = '')
61
 * @method static void nullOrLessThan($value, $limit, $message = '')
62
 * @method static void nullOrLessThanEq($value, $limit, $message = '')
63
 * @method static void nullOrRange($value, $min, $max, $message = '')
64
 * @method static void nullOrOneOf($value, $values, $message = '')
65
 * @method static void nullOrContains($value, $subString, $message = '')
66
 * @method static void nullOrNotContains($value, $subString, $message = '')
67
 * @method static void nullOrNotWhitespaceOnly($value, $message = '')
68
 * @method static void nullOrStartsWith($value, $prefix, $message = '')
69
 * @method static void nullOrStartsWithLetter($value, $message = '')
70
 * @method static void nullOrEndsWith($value, $suffix, $message = '')
71
 * @method static void nullOrRegex($value, $pattern, $message = '')
72
 * @method static void nullOrNotRegex($value, $pattern, $message = '')
73
 * @method static void nullOrUnicodeLetters($value, $message = '')
74
 * @method static void nullOrAlpha($value, $message = '')
75
 * @method static void nullOrDigits($value, $message = '')
76
 * @method static void nullOrAlnum($value, $message = '')
77
 * @method static void nullOrLower($value, $message = '')
78
 * @method static void nullOrUpper($value, $message = '')
79
 * @method static void nullOrLength($value, $length, $message = '')
80
 * @method static void nullOrMinLength($value, $min, $message = '')
81
 * @method static void nullOrMaxLength($value, $max, $message = '')
82
 * @method static void nullOrLengthBetween($value, $min, $max, $message = '')
83
 * @method static void nullOrFileExists($value, $message = '')
84
 * @method static void nullOrFile($value, $message = '')
85
 * @method static void nullOrDirectory($value, $message = '')
86
 * @method static void nullOrReadable($value, $message = '')
87
 * @method static void nullOrWritable($value, $message = '')
88
 * @method static void nullOrClassExists($value, $message = '')
89
 * @method static void nullOrSubclassOf($value, $class, $message = '')
90
 * @method static void nullOrInterfaceExists($value, $message = '')
91
 * @method static void nullOrImplementsInterface($value, $interface, $message = '')
92
 * @method static void nullOrPropertyExists($value, $property, $message = '')
93
 * @method static void nullOrPropertyNotExists($value, $property, $message = '')
94
 * @method static void nullOrMethodExists($value, $method, $message = '')
95
 * @method static void nullOrMethodNotExists($value, $method, $message = '')
96
 * @method static void nullOrKeyExists($value, $key, $message = '')
97
 * @method static void nullOrKeyNotExists($value, $key, $message = '')
98
 * @method static void nullOrCount($value, $key, $message = '')
99
 * @method static void nullOrMinCount($value, $min, $message = '')
100
 * @method static void nullOrMaxCount($value, $max, $message = '')
101
 * @method static void nullOrIsList($value, $message = '')
102
 * @method static void nullOrIsMap($value, $message = '')
103
 * @method static void nullOrCountBetween($value, $min, $max, $message = '')
104
 * @method static void nullOrUuid($values, $message = '')
105
 * @method static void nullOrThrows($expression, $class = 'Exception', $message = '')
106
 * @method static void allString($values, $message = '')
107
 * @method static void allStringNotEmpty($values, $message = '')
108
 * @method static void allInteger($values, $message = '')
109
 * @method static void allIntegerish($values, $message = '')
110
 * @method static void allFloat($values, $message = '')
111
 * @method static void allNumeric($values, $message = '')
112
 * @method static void allNatural($values, $message = '')
113
 * @method static void allBoolean($values, $message = '')
114
 * @method static void allScalar($values, $message = '')
115
 * @method static void allObject($values, $message = '')
116
 * @method static void allResource($values, $type = null, $message = '')
117
 * @method static void allIsCallable($values, $message = '')
118
 * @method static void allIsArray($values, $message = '')
119
 * @method static void allIsTraversable($values, $message = '')
120
 * @method static void allIsArrayAccessible($values, $message = '')
121
 * @method static void allIsCountable($values, $message = '')
122
 * @method static void allIsIterable($values, $message = '')
123
 * @method static void allIsInstanceOf($values, $class, $message = '')
124
 * @method static void allNotInstanceOf($values, $class, $message = '')
125
 * @method static void allIsInstanceOfAny($values, $classes, $message = '')
126
 * @method static void allNull($values, $message = '')
127
 * @method static void allNotNull($values, $message = '')
128
 * @method static void allIsEmpty($values, $message = '')
129
 * @method static void allNotEmpty($values, $message = '')
130
 * @method static void allTrue($values, $message = '')
131
 * @method static void allFalse($values, $message = '')
132
 * @method static void allIp($values, $message = '')
133
 * @method static void allIpv4($values, $message = '')
134
 * @method static void allIpv6($values, $message = '')
135
 * @method static void allEmail($values, $message = '')
136
 * @method static void allUniqueValues($values, $message = '')
137
 * @method static void allEq($values, $expect, $message = '')
138
 * @method static void allNotEq($values, $expect, $message = '')
139
 * @method static void allSame($values, $expect, $message = '')
140
 * @method static void allNotSame($values, $expect, $message = '')
141
 * @method static void allGreaterThan($values, $limit, $message = '')
142
 * @method static void allGreaterThanEq($values, $limit, $message = '')
143
 * @method static void allLessThan($values, $limit, $message = '')
144
 * @method static void allLessThanEq($values, $limit, $message = '')
145
 * @method static void allRange($values, $min, $max, $message = '')
146
 * @method static void allOneOf($values, $values, $message = '')
147
 * @method static void allContains($values, $subString, $message = '')
148
 * @method static void allNotContains($values, $subString, $message = '')
149
 * @method static void allNotWhitespaceOnly($values, $message = '')
150
 * @method static void allStartsWith($values, $prefix, $message = '')
151
 * @method static void allStartsWithLetter($values, $message = '')
152
 * @method static void allEndsWith($values, $suffix, $message = '')
153
 * @method static void allRegex($values, $pattern, $message = '')
154
 * @method static void allNotRegex($values, $pattern, $message = '')
155
 * @method static void allUnicodeLetters($values, $message = '')
156
 * @method static void allAlpha($values, $message = '')
157
 * @method static void allDigits($values, $message = '')
158
 * @method static void allAlnum($values, $message = '')
159
 * @method static void allLower($values, $message = '')
160
 * @method static void allUpper($values, $message = '')
161
 * @method static void allLength($values, $length, $message = '')
162
 * @method static void allMinLength($values, $min, $message = '')
163
 * @method static void allMaxLength($values, $max, $message = '')
164
 * @method static void allLengthBetween($values, $min, $max, $message = '')
165
 * @method static void allFileExists($values, $message = '')
166
 * @method static void allFile($values, $message = '')
167
 * @method static void allDirectory($values, $message = '')
168
 * @method static void allReadable($values, $message = '')
169
 * @method static void allWritable($values, $message = '')
170
 * @method static void allClassExists($values, $message = '')
171
 * @method static void allSubclassOf($values, $class, $message = '')
172
 * @method static void allInterfaceExists($values, $message = '')
173
 * @method static void allImplementsInterface($values, $interface, $message = '')
174
 * @method static void allPropertyExists($values, $property, $message = '')
175
 * @method static void allPropertyNotExists($values, $property, $message = '')
176
 * @method static void allMethodExists($values, $method, $message = '')
177
 * @method static void allMethodNotExists($values, $method, $message = '')
178
 * @method static void allKeyExists($values, $key, $message = '')
179
 * @method static void allKeyNotExists($values, $key, $message = '')
180
 * @method static void allCount($values, $key, $message = '')
181
 * @method static void allMinCount($values, $min, $message = '')
182
 * @method static void allMaxCount($values, $max, $message = '')
183
 * @method static void allCountBetween($values, $min, $max, $message = '')
184
 * @method static void allIsList($values, $message = '')
185
 * @method static void allIsMap($values, $message = '')
186
 * @method static void allUuid($values, $message = '')
187
 * @method static void allThrows($expressions, $class = 'Exception', $message = '')
188
 *
189
 * @since  1.0
190
 *
191
 * @author Bernhard Schussek <[email protected]>
192
 */
193
class Assert
0 ignored issues
show
Coding Style introduced by
Since you have declared the constructor as private, maybe you should also declare the class as final.
Loading history...
194
{
195
    /**
196
     * @psalm-assert string $value
197
     *
198
     * @param mixed  $value
199
     * @param string $message
200
     */
201 122
    public static function string($value, $message = '')
202
    {
203 122
        if (!\is_string($value)) {
204 14
            static::reportInvalidArgument(\sprintf(
205 14
                $message ?: 'Expected a string. Got: %s',
206 14
                static::typeToString($value)
207
            ));
208
        }
209 108
    }
210
211
    /**
212
     * @psalm-assert string $value
213
     *
214
     * @param mixed  $value
215
     * @param string $message
216
     */
217 16
    public static function stringNotEmpty($value, $message = '')
218
    {
219 16
        static::string($value, $message);
220 12
        static::notEq($value, '', $message);
221 8
    }
222
223
    /**
224
     * @psalm-assert int $value
225
     *
226
     * @param mixed  $value
227
     * @param string $message
228
     */
229 17
    public static function integer($value, $message = '')
230
    {
231 17
        if (!\is_int($value)) {
232 13
            static::reportInvalidArgument(\sprintf(
233 13
                $message ?: 'Expected an integer. Got: %s',
234 13
                static::typeToString($value)
235
            ));
236
        }
237 4
    }
238
239
    /**
240
     * @psalm-assert numeric $value
241
     *
242
     * @param mixed  $value
243
     * @param string $message
244
     */
245 16
    public static function integerish($value, $message = '')
246
    {
247 16
        if (!\is_numeric($value) || $value != (int) $value) {
248 4
            static::reportInvalidArgument(\sprintf(
249 4
                $message ?: 'Expected an integerish value. Got: %s',
250 4
                static::typeToString($value)
251
            ));
252
        }
253 12
    }
254
255
    /**
256
     * @psalm-assert float $value
257
     *
258
     * @param mixed  $value
259
     * @param string $message
260
     */
261 16
    public static function float($value, $message = '')
262
    {
263 16
        if (!\is_float($value)) {
264 8
            static::reportInvalidArgument(\sprintf(
265 8
                $message ?: 'Expected a float. Got: %s',
266 8
                static::typeToString($value)
267
            ));
268
        }
269 8
    }
270
271
    /**
272
     * @psalm-assert numeric $value
273
     *
274
     * @param mixed  $value
275
     * @param string $message
276
     */
277 20
    public static function numeric($value, $message = '')
278
    {
279 20
        if (!\is_numeric($value)) {
280 4
            static::reportInvalidArgument(\sprintf(
281 4
                $message ?: 'Expected a numeric. Got: %s',
282 4
                static::typeToString($value)
283
            ));
284
        }
285 16
    }
286
287
    /**
288
     * @psalm-assert int $value
289
     *
290
     * @param mixed  $value
291
     * @param string $message
292
     */
293 24
    public static function natural($value, $message = '')
294
    {
295 24
        if (!\is_int($value) || $value < 0) {
296 16
            static::reportInvalidArgument(\sprintf(
297 16
                $message ?: 'Expected a non-negative integer. Got %s',
298 16
                static::valueToString($value)
299
            ));
300
        }
301 8
    }
302
303
    /**
304
     * @psalm-assert bool $value
305
     *
306
     * @param mixed  $value
307
     * @param string $message
308
     */
309 16
    public static function boolean($value, $message = '')
310
    {
311 16
        if (!\is_bool($value)) {
312 8
            static::reportInvalidArgument(\sprintf(
313 8
                $message ?: 'Expected a boolean. Got: %s',
314 8
                static::typeToString($value)
315
            ));
316
        }
317 8
    }
318
319
    /**
320
     * @psalm-assert scalar $value
321
     *
322
     * @param mixed  $value
323
     * @param string $message
324
     */
325 23
    public static function scalar($value, $message = '')
326
    {
327 23
        if (!\is_scalar($value)) {
328 11
            static::reportInvalidArgument(\sprintf(
329 11
                $message ?: 'Expected a scalar. Got: %s',
330 11
                static::typeToString($value)
331
            ));
332
        }
333 12
    }
334
335
    /**
336
     * @psalm-assert object $value
337
     *
338
     * @param mixed  $value
339
     * @param string $message
340
     */
341 23
    public static function object($value, $message = '')
342
    {
343 23
        if (!\is_object($value)) {
344 15
            static::reportInvalidArgument(\sprintf(
345 15
                $message ?: 'Expected an object. Got: %s',
346 15
                static::typeToString($value)
347
            ));
348
        }
349 8
    }
350
351
    /**
352
     * @psalm-assert resource $value
353
     *
354
     * @param mixed       $value
355
     * @param string|null $type    type of resource this should be. @see https://www.php.net/manual/en/function.get-resource-type.php
356
     * @param string      $message
357
     */
358 16
    public static function resource($value, $type = null, $message = '')
359
    {
360 16
        if (!\is_resource($value)) {
361 4
            static::reportInvalidArgument(\sprintf(
362 4
                $message ?: 'Expected a resource. Got: %s',
363 4
                static::typeToString($value)
364
            ));
365
        }
366
367 12
        if ($type && $type !== \get_resource_type($value)) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $type of type string|null is loosely compared to true; this is ambiguous if the string can be empty. You might want to explicitly use !== null instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
368 4
            static::reportInvalidArgument(\sprintf(
369 4
                $message ?: 'Expected a resource of type %2$s. Got: %s',
370 4
                static::typeToString($value),
371 4
                $type
372
            ));
373
        }
374 8
    }
375
376
    /**
377
     * @psalm-assert callable $value
378
     *
379
     * @param mixed  $value
380
     * @param string $message
381
     */
382 20
    public static function isCallable($value, $message = '')
383
    {
384 20
        if (!\is_callable($value)) {
385 8
            static::reportInvalidArgument(\sprintf(
386 8
                $message ?: 'Expected a callable. Got: %s',
387 8
                static::typeToString($value)
388
            ));
389
        }
390 12
    }
391
392
    /**
393
     * @psalm-assert array $value
394
     *
395
     * @param mixed  $value
396
     * @param string $message
397
     */
398 20
    public static function isArray($value, $message = '')
399
    {
400 20
        if (!\is_array($value)) {
401 12
            static::reportInvalidArgument(\sprintf(
402 12
                $message ?: 'Expected an array. Got: %s',
403 12
                static::typeToString($value)
404
            ));
405
        }
406 8
    }
407
408
    /**
409
     * @psalm-assert iterable $value
410
     *
411
     * @deprecated use "isIterable" or "isInstanceOf" instead
412
     *
413
     * @param mixed  $value
414
     * @param string $message
415
     */
416 20
    public static function isTraversable($value, $message = '')
417
    {
418 20
        @\trigger_error(
0 ignored issues
show
Security Best Practice introduced by
It seems like you do not handle an error condition here. This can introduce security issues, and is generally not recommended.

If you suppress an error, we recommend checking for the error condition explicitly:

// For example instead of
@mkdir($dir);

// Better use
if (@mkdir($dir) === false) {
    throw new \RuntimeException('The directory '.$dir.' could not be created.');
}
Loading history...
419 20
            \sprintf(
420 20
                'The "%s" assertion is deprecated. You should stop using it, as it will soon be removed in 2.0 version. Use "isIterable" or "isInstanceOf" instead.',
421 20
                __METHOD__
422
            ),
423 20
            \E_USER_DEPRECATED
424
        );
425
426 20
        if (!\is_array($value) && !($value instanceof Traversable)) {
427 8
            static::reportInvalidArgument(\sprintf(
428 8
                $message ?: 'Expected a traversable. Got: %s',
429 8
                static::typeToString($value)
430
            ));
431
        }
432 12
    }
433
434
    /**
435
     * @param mixed  $value
436
     * @param string $message
437
     */
438 20 View Code Duplication
    public static function isArrayAccessible($value, $message = '')
439
    {
440 20
        if (!\is_array($value) && !($value instanceof ArrayAccess)) {
441 8
            static::reportInvalidArgument(\sprintf(
442 8
                $message ?: 'Expected an array accessible. Got: %s',
443 8
                static::typeToString($value)
444
            ));
445
        }
446 12
    }
447
448
    /**
449
     * @psalm-assert countable $value
450
     *
451
     * @param mixed  $value
452
     * @param string $message
453
     */
454 24 View Code Duplication
    public static function isCountable($value, $message = '')
455
    {
456 24
        if (!\is_array($value) && !($value instanceof Countable)) {
457 12
            static::reportInvalidArgument(\sprintf(
458 12
                $message ?: 'Expected a countable. Got: %s',
459 12
                static::typeToString($value)
460
            ));
461
        }
462 12
    }
463
464
    /**
465
     * @psalm-assert iterable $value
466
     *
467
     * @param mixed  $value
468
     * @param string $message
469
     */
470 878 View Code Duplication
    public static function isIterable($value, $message = '')
471
    {
472 878
        if (!\is_array($value) && !($value instanceof Traversable)) {
473 8
            static::reportInvalidArgument(\sprintf(
474 8
                $message ?: 'Expected an iterable. Got: %s',
475 8
                static::typeToString($value)
476
            ));
477
        }
478 874
    }
479
480
    /**
481
     * @psalm-template ExpectedType of object
482
     * @psalm-param class-string<ExpectedType> $class
483
     * @psalm-assert ExpectedType $value
484
     *
485
     * @param mixed         $value
486
     * @param string|object $class
487
     * @param string        $message
488
     */
489 16
    public static function isInstanceOf($value, $class, $message = '')
490
    {
491 16
        if (!($value instanceof $class)) {
492 12
            static::reportInvalidArgument(\sprintf(
493 12
                $message ?: 'Expected an instance of %2$s. Got: %s',
494 12
                static::typeToString($value),
495 12
                $class
496
            ));
497
        }
498 4
    }
499
500
    /**
501
     * @psalm-template ExpectedType of object
502
     * @psalm-param class-string<ExpectedType> $class
503
     * @psalm-assert !ExpectedType $value
504
     *
505
     * @param mixed         $value
506
     * @param string|object $class
507
     * @param string        $message
508
     */
509 16
    public static function notInstanceOf($value, $class, $message = '')
510
    {
511 16
        if ($value instanceof $class) {
512 4
            static::reportInvalidArgument(\sprintf(
513 4
                $message ?: 'Expected an instance other than %2$s. Got: %s',
514 4
                static::typeToString($value),
515 4
                $class
516
            ));
517
        }
518 12
    }
519
520
    /**
521
     * @param mixed                $value
522
     * @param array<object|string> $classes
523
     * @param string               $message
524
     */
525 20
    public static function isInstanceOfAny($value, array $classes, $message = '')
526
    {
527 20
        foreach ($classes as $class) {
528 20
            if ($value instanceof $class) {
529 8
                return;
530
            }
531
        }
532
533 12
        static::reportInvalidArgument(\sprintf(
534 12
            $message ?: 'Expected an instance of any of %2$s. Got: %s',
535 12
            static::typeToString($value),
536 12
            \implode(', ', \array_map(array('static', 'valueToString'), $classes))
537
        ));
538
    }
539
540
    /**
541
     * @psalm-assert empty $value
542
     *
543
     * @param mixed  $value
544
     * @param string $message
545
     */
546 23
    public static function isEmpty($value, $message = '')
547
    {
548 23
        if (!empty($value)) {
549 8
            static::reportInvalidArgument(\sprintf(
550 8
                $message ?: 'Expected an empty value. Got: %s',
551 8
                static::valueToString($value)
552
            ));
553
        }
554 15
    }
555
556
    /**
557
     * @psalm-assert !empty $value
558
     *
559
     * @param mixed  $value
560
     * @param string $message
561
     */
562 23
    public static function notEmpty($value, $message = '')
563
    {
564 23
        if (empty($value)) {
565 15
            static::reportInvalidArgument(\sprintf(
566 15
                $message ?: 'Expected a non-empty value. Got: %s',
567 15
                static::valueToString($value)
568
            ));
569
        }
570 8
    }
571
572
    /**
573
     * @psalm-assert null $value
574
     *
575
     * @param mixed  $value
576
     * @param string $message
577
     */
578 11
    public static function null($value, $message = '')
579
    {
580 11
        if (null !== $value) {
581 8
            static::reportInvalidArgument(\sprintf(
582 8
                $message ?: 'Expected null. Got: %s',
583 8
                static::valueToString($value)
584
            ));
585
        }
586 3
    }
587
588
    /**
589
     * @psalm-assert !null $value
590
     *
591
     * @param mixed  $value
592
     * @param string $message
593
     */
594 11
    public static function notNull($value, $message = '')
595
    {
596 11
        if (null === $value) {
597 3
            static::reportInvalidArgument(
598 3
                $message ?: 'Expected a value other than null.'
599
            );
600
        }
601 8
    }
602
603
    /**
604
     * @psalm-assert true $value
605
     *
606
     * @param mixed  $value
607
     * @param string $message
608
     */
609 15
    public static function true($value, $message = '')
610
    {
611 15
        if (true !== $value) {
612 11
            static::reportInvalidArgument(\sprintf(
613 11
                $message ?: 'Expected a value to be true. Got: %s',
614 11
                static::valueToString($value)
615
            ));
616
        }
617 4
    }
618
619
    /**
620
     * @psalm-assert false $value
621
     *
622
     * @param mixed  $value
623
     * @param string $message
624
     */
625 19
    public static function false($value, $message = '')
626
    {
627 19
        if (false !== $value) {
628 15
            static::reportInvalidArgument(\sprintf(
629 15
                $message ?: 'Expected a value to be false. Got: %s',
630 15
                static::valueToString($value)
631
            ));
632
        }
633 4
    }
634
635
    /**
636
     * @param mixed  $value
637
     * @param string $message
638
     */
639 47 View Code Duplication
    public static function ip($value, $message = '')
640
    {
641 47
        if (false === \filter_var($value, \FILTER_VALIDATE_IP)) {
642 19
            static::reportInvalidArgument(\sprintf(
643 19
                $message ?: 'Expected a value to be an IP. Got: %s',
644 19
                static::valueToString($value)
645
            ));
646
        }
647 28
    }
648
649
    /**
650
     * @param mixed  $value
651
     * @param string $message
652
     */
653 47 View Code Duplication
    public static function ipv4($value, $message = '')
654
    {
655 47
        if (false === \filter_var($value, \FILTER_VALIDATE_IP, \FILTER_FLAG_IPV4)) {
656 35
            static::reportInvalidArgument(\sprintf(
657 35
                $message ?: 'Expected a value to be an IPv4. Got: %s',
658 35
                static::valueToString($value)
659
            ));
660
        }
661 12
    }
662
663
    /**
664
     * @param mixed  $value
665
     * @param string $message
666
     */
667 47 View Code Duplication
    public static function ipv6($value, $message = '')
668
    {
669 47
        if (false === \filter_var($value, \FILTER_VALIDATE_IP, \FILTER_FLAG_IPV6)) {
670 31
            static::reportInvalidArgument(\sprintf(
671 31
                $message ?: 'Expected a value to be an IPv6. Got %s',
672 31
                static::valueToString($value)
673
            ));
674
        }
675 16
    }
676
677
    /**
678
     * @param mixed  $value
679
     * @param string $message
680
     */
681 16 View Code Duplication
    public static function email($value, $message = '')
682
    {
683 16
        if (false === \filter_var($value, FILTER_VALIDATE_EMAIL)) {
684 12
            static::reportInvalidArgument(\sprintf(
685 12
                $message ?: 'Expected a value to be a valid e-mail address. Got %s',
686 12
                static::valueToString($value)
687
            ));
688
        }
689 4
    }
690
691
    /**
692
     * Does non strict comparisons on the items, so ['3', 3] will not pass the assertion.
693
     *
694
     * @param array  $values
695
     * @param string $message
696
     */
697 12
    public static function uniqueValues(array $values, $message = '')
698
    {
699 12
        $allValues = \count($values);
700 12
        $uniqueValues = \count(\array_unique($values));
701
702 12
        if ($allValues !== $uniqueValues) {
703 8
            $difference = $allValues - $uniqueValues;
704
705 8
            static::reportInvalidArgument(\sprintf(
706 8
                $message ?: 'Expected an array of unique values, but %s of them %s duplicated',
707 8
                $difference,
708 8
                (1 === $difference ? 'is' : 'are')
709
            ));
710
        }
711 4
    }
712
713
    /**
714
     * @param mixed  $value
715
     * @param mixed  $expect
716
     * @param string $message
717
     */
718 33
    public static function eq($value, $expect, $message = '')
719
    {
720 33
        if ($expect != $value) {
721 17
            static::reportInvalidArgument(\sprintf(
722 17
                $message ?: 'Expected a value equal to %2$s. Got: %s',
723 17
                static::valueToString($value),
724 17
                static::valueToString($expect)
725
            ));
726
        }
727 16
    }
728
729
    /**
730
     * @param mixed  $value
731
     * @param mixed  $expect
732
     * @param string $message
733
     */
734 28
    public static function notEq($value, $expect, $message = '')
735
    {
736 28
        if ($expect == $value) {
737 16
            static::reportInvalidArgument(\sprintf(
738 16
                $message ?: 'Expected a different value than %s.',
739 16
                static::valueToString($expect)
740
            ));
741
        }
742 12
    }
743
744
    /**
745
     * @psalm-template ExpectedType
746
     * @psalm-param ExpectedType $expect
747
     * @psalm-assert =ExpectedType $value
748
     *
749
     * @param mixed  $value
750
     * @param mixed  $expect
751
     * @param string $message
752
     */
753 16
    public static function same($value, $expect, $message = '')
754
    {
755 16
        if ($expect !== $value) {
756 12
            static::reportInvalidArgument(\sprintf(
757 12
                $message ?: 'Expected a value identical to %2$s. Got: %s',
758 12
                static::valueToString($value),
759 12
                static::valueToString($expect)
760
            ));
761
        }
762 4
    }
763
764
    /**
765
     * @param mixed  $value
766
     * @param mixed  $expect
767
     * @param string $message
768
     */
769 16
    public static function notSame($value, $expect, $message = '')
770
    {
771 16
        if ($expect === $value) {
772 4
            static::reportInvalidArgument(\sprintf(
773 4
                $message ?: 'Expected a value not identical to %s.',
774 4
                static::valueToString($expect)
775
            ));
776
        }
777 12
    }
778
779
    /**
780
     * @param mixed  $value
781
     * @param mixed  $limit
782
     * @param string $message
783
     */
784 8
    public static function greaterThan($value, $limit, $message = '')
785
    {
786 8
        if ($value <= $limit) {
787 4
            static::reportInvalidArgument(\sprintf(
788 4
                $message ?: 'Expected a value greater than %2$s. Got: %s',
789 4
                static::valueToString($value),
790 4
                static::valueToString($limit)
791
            ));
792
        }
793 4
    }
794
795
    /**
796
     * @param mixed  $value
797
     * @param mixed  $limit
798
     * @param string $message
799
     */
800 12
    public static function greaterThanEq($value, $limit, $message = '')
801
    {
802 12
        if ($value < $limit) {
803 4
            static::reportInvalidArgument(\sprintf(
804 4
                $message ?: 'Expected a value greater than or equal to %2$s. Got: %s',
805 4
                static::valueToString($value),
806 4
                static::valueToString($limit)
807
            ));
808
        }
809 8
    }
810
811
    /**
812
     * @param mixed  $value
813
     * @param mixed  $limit
814
     * @param string $message
815
     */
816 8
    public static function lessThan($value, $limit, $message = '')
817
    {
818 8
        if ($value >= $limit) {
819 4
            static::reportInvalidArgument(\sprintf(
820 4
                $message ?: 'Expected a value less than %2$s. Got: %s',
821 4
                static::valueToString($value),
822 4
                static::valueToString($limit)
823
            ));
824
        }
825 4
    }
826
827
    /**
828
     * @param mixed  $value
829
     * @param mixed  $limit
830
     * @param string $message
831
     */
832 12
    public static function lessThanEq($value, $limit, $message = '')
833
    {
834 12
        if ($value > $limit) {
835 4
            static::reportInvalidArgument(\sprintf(
836 4
                $message ?: 'Expected a value less than or equal to %2$s. Got: %s',
837 4
                static::valueToString($value),
838 4
                static::valueToString($limit)
839
            ));
840
        }
841 8
    }
842
843
    /**
844
     * Inclusive range, so Assert::(3, 3, 5) passes.
845
     *
846
     * @param mixed $value
847
     * @param mixed min
848
     * @param mixed max
849
     * @param string $message
850
     */
851 16 View Code Duplication
    public static function range($value, $min, $max, $message = '')
852
    {
853 16
        if ($value < $min || $value > $max) {
854 8
            static::reportInvalidArgument(\sprintf(
855 8
                $message ?: 'Expected a value between %2$s and %3$s. Got: %s',
856 8
                static::valueToString($value),
857 8
                static::valueToString($min),
858 8
                static::valueToString($max)
859
            ));
860
        }
861 8
    }
862
863
    /**
864
     * Does strict comparison, so Assert::oneOf(3, ['3']) does not pass the assertion.
865
     *
866
     * @psalm-template ExpectedType
867
     * @psalm-param array<ExpectedType> $values
868
     * @psalm-assert ExpectedType $value
869
     *
870
     * @param mixed  $value
871
     * @param array  $values
872
     * @param string $message
873
     */
874 8
    public static function oneOf($value, array $values, $message = '')
875
    {
876 8
        if (!\in_array($value, $values, true)) {
877 4
            static::reportInvalidArgument(\sprintf(
878 4
                $message ?: 'Expected one of: %2$s. Got: %s',
879 4
                static::valueToString($value),
880 4
                \implode(', ', \array_map(array('static', 'valueToString'), $values))
881
            ));
882
        }
883 4
    }
884
885
    /**
886
     * @param mixed  $value
887
     * @param string $subString
888
     * @param string $message
889
     */
890 80 View Code Duplication
    public static function contains($value, $subString, $message = '')
891
    {
892 80
        if (false === \strpos($value, $subString)) {
893 32
            static::reportInvalidArgument(\sprintf(
894 32
                $message ?: 'Expected a value to contain %2$s. Got: %s',
895 32
                static::valueToString($value),
896 32
                static::valueToString($subString)
897
            ));
898
        }
899 48
    }
900
901
    /**
902
     * @param mixed  $value
903
     * @param string $subString
904
     * @param string $message
905
     */
906 80 View Code Duplication
    public static function notContains($value, $subString, $message = '')
907
    {
908 80
        if (false !== \strpos($value, $subString)) {
909 48
            static::reportInvalidArgument(\sprintf(
910 48
                $message ?: '%2$s was not expected to be contained in a value. Got: %s',
911 48
                static::valueToString($value),
912 48
                static::valueToString($subString)
913
            ));
914
        }
915 32
    }
916
917
    /**
918
     * @param mixed  $value
919
     * @param string $message
920
     */
921 40
    public static function notWhitespaceOnly($value, $message = '')
922
    {
923 40
        if (\preg_match('/^\s*$/', $value)) {
924 24
            static::reportInvalidArgument(\sprintf(
925 24
                $message ?: 'Expected a non-whitespace string. Got: %s',
926 24
                static::valueToString($value)
927
            ));
928
        }
929 16
    }
930
931
    /**
932
     * @param mixed  $value
933
     * @param string $prefix
934
     * @param string $message
935
     */
936 48 View Code Duplication
    public static function startsWith($value, $prefix, $message = '')
937
    {
938 48
        if (0 !== \strpos($value, $prefix)) {
939 32
            static::reportInvalidArgument(\sprintf(
940 32
                $message ?: 'Expected a value to start with %2$s. Got: %s',
941 32
                static::valueToString($value),
942 32
                static::valueToString($prefix)
943
            ));
944
        }
945 16
    }
946
947
    /**
948
     * @param mixed  $value
949
     * @param string $message
950
     */
951 24
    public static function startsWithLetter($value, $message = '')
952
    {
953 24
        $valid = isset($value[0]);
954
955 24
        if ($valid) {
956 20
            $locale = \setlocale(LC_CTYPE, 0);
957 20
            \setlocale(LC_CTYPE, 'C');
958 20
            $valid = \ctype_alpha($value[0]);
959 20
            \setlocale(LC_CTYPE, $locale);
960
        }
961
962 24
        if (!$valid) {
963 12
            static::reportInvalidArgument(\sprintf(
964 12
                $message ?: 'Expected a value to start with a letter. Got: %s',
965 12
                static::valueToString($value)
966
            ));
967
        }
968 12
    }
969
970
    /**
971
     * @param mixed  $value
972
     * @param string $suffix
973
     * @param string $message
974
     */
975 48 View Code Duplication
    public static function endsWith($value, $suffix, $message = '')
976
    {
977 48
        if ($suffix !== \substr($value, -\strlen($suffix))) {
978 32
            static::reportInvalidArgument(\sprintf(
979 32
                $message ?: 'Expected a value to end with %2$s. Got: %s',
980 32
                static::valueToString($value),
981 32
                static::valueToString($suffix)
982
            ));
983
        }
984 16
    }
985
986
    /**
987
     * @param mixed  $value
988
     * @param mixed  $pattern
989
     * @param string $message
990
     */
991 12
    public static function regex($value, $pattern, $message = '')
992
    {
993 12
        if (!\preg_match($pattern, $value)) {
994 8
            static::reportInvalidArgument(\sprintf(
995 8
                $message ?: 'The value %s does not match the expected pattern.',
996 8
                static::valueToString($value)
997
            ));
998
        }
999 4
    }
1000
1001
    /**
1002
     * @param mixed  $value
1003
     * @param mixed  $pattern
1004
     * @param string $message
1005
     */
1006 12
    public static function notRegex($value, $pattern, $message = '')
1007
    {
1008 12
        if (\preg_match($pattern, $value, $matches, PREG_OFFSET_CAPTURE)) {
1009 4
            static::reportInvalidArgument(\sprintf(
1010 4
                $message ?: 'The value %s matches the pattern %s (at offset %d).',
1011 4
                static::valueToString($value),
1012 4
                static::valueToString($pattern),
1013 4
                $matches[0][1]
1014
            ));
1015
        }
1016 8
    }
1017
1018
    /**
1019
     * @psalm-assert !numeric $value
1020
     *
1021
     * @param mixed  $value
1022
     * @param string $message
1023
     */
1024 28 View Code Duplication
    public static function unicodeLetters($value, $message = '')
1025
    {
1026 28
        static::string($value);
1027
1028 28
        if (!\preg_match('/^\p{L}+$/u', $value)) {
1029 16
            static::reportInvalidArgument(\sprintf(
1030 16
                $message ?: 'Expected a value to contain only Unicode letters. Got: %s',
1031 16
                static::valueToString($value)
1032
            ));
1033
        }
1034 12
    }
1035
1036
    /**
1037
     * @param mixed  $value
1038
     * @param string $message
1039
     */
1040 12 View Code Duplication
    public static function alpha($value, $message = '')
1041
    {
1042 12
        $locale = \setlocale(LC_CTYPE, 0);
1043 12
        \setlocale(LC_CTYPE, 'C');
1044 12
        $valid = !\ctype_alpha($value);
1045 12
        \setlocale(LC_CTYPE, $locale);
1046
1047 12
        if ($valid) {
1048 8
            static::reportInvalidArgument(\sprintf(
1049 8
                $message ?: 'Expected a value to contain only letters. Got: %s',
1050 8
                static::valueToString($value)
1051
            ));
1052
        }
1053 4
    }
1054
1055
    /**
1056
     * @param mixed  $value
1057
     * @param string $message
1058
     */
1059 12 View Code Duplication
    public static function digits($value, $message = '')
1060
    {
1061 12
        $locale = \setlocale(LC_CTYPE, 0);
1062 12
        \setlocale(LC_CTYPE, 'C');
1063 12
        $valid = !\ctype_digit($value);
1064 12
        \setlocale(LC_CTYPE, $locale);
1065
1066 12
        if ($valid) {
1067 8
            static::reportInvalidArgument(\sprintf(
1068 8
                $message ?: 'Expected a value to contain digits only. Got: %s',
1069 8
                static::valueToString($value)
1070
            ));
1071
        }
1072 4
    }
1073
1074
    /**
1075
     * @param mixed  $value
1076
     * @param string $message
1077
     */
1078 12 View Code Duplication
    public static function alnum($value, $message = '')
1079
    {
1080 12
        $locale = \setlocale(LC_CTYPE, 0);
1081 12
        \setlocale(LC_CTYPE, 'C');
1082 12
        $valid = !\ctype_alnum($value);
1083 12
        \setlocale(LC_CTYPE, $locale);
1084
1085 12
        if ($valid) {
1086 8
            static::reportInvalidArgument(\sprintf(
1087 8
                $message ?: 'Expected a value to contain letters and digits only. Got: %s',
1088 8
                static::valueToString($value)
1089
            ));
1090
        }
1091 4
    }
1092
1093
    /**
1094
     * @param mixed  $value
1095
     * @param string $message
1096
     */
1097 16 View Code Duplication
    public static function lower($value, $message = '')
1098
    {
1099 16
        $locale = \setlocale(LC_CTYPE, 0);
1100 16
        \setlocale(LC_CTYPE, 'C');
1101 16
        $valid = !\ctype_lower($value);
1102 16
        \setlocale(LC_CTYPE, $locale);
1103
1104 16
        if ($valid) {
1105 12
            static::reportInvalidArgument(\sprintf(
1106 12
                $message ?: 'Expected a value to contain lowercase characters only. Got: %s',
1107 12
                static::valueToString($value)
1108
            ));
1109
        }
1110 4
    }
1111
1112
    /**
1113
     * @param mixed  $value
1114
     * @param string $message
1115
     */
1116 16 View Code Duplication
    public static function upper($value, $message = '')
1117
    {
1118 16
        $locale = \setlocale(LC_CTYPE, 0);
1119 16
        \setlocale(LC_CTYPE, 'C');
1120 16
        $valid = !\ctype_upper($value);
1121 16
        \setlocale(LC_CTYPE, $locale);
1122
1123 16
        if ($valid) {
1124 12
            static::reportInvalidArgument(\sprintf(
1125 12
                $message ?: 'Expected a value to contain uppercase characters only. Got: %s',
1126 12
                static::valueToString($value)
1127
            ));
1128
        }
1129 4
    }
1130
1131
    /**
1132
     * @param mixed  $value
1133
     * @param mixed  $length
1134
     * @param string $message
1135
     */
1136 36
    public static function length($value, $length, $message = '')
1137
    {
1138 36
        if ($length !== static::strlen($value)) {
1139 24
            static::reportInvalidArgument(\sprintf(
1140 24
                $message ?: 'Expected a value to contain %2$s characters. Got: %s',
1141 24
                static::valueToString($value),
1142 24
                $length
1143
            ));
1144
        }
1145 12
    }
1146
1147
    /**
1148
     * Inclusive min.
1149
     *
1150
     * @param mixed  $value
1151
     * @param mixed  $min
1152
     * @param string $message
1153
     */
1154 36
    public static function minLength($value, $min, $message = '')
1155
    {
1156 36
        if (static::strlen($value) < $min) {
1157 12
            static::reportInvalidArgument(\sprintf(
1158 12
                $message ?: 'Expected a value to contain at least %2$s characters. Got: %s',
1159 12
                static::valueToString($value),
1160 12
                $min
1161
            ));
1162
        }
1163 24
    }
1164
1165
    /**
1166
     * Inclusive max.
1167
     *
1168
     * @param mixed  $value
1169
     * @param mixed  $max
1170
     * @param string $message
1171
     */
1172 36
    public static function maxLength($value, $max, $message = '')
1173
    {
1174 36
        if (static::strlen($value) > $max) {
1175 12
            static::reportInvalidArgument(\sprintf(
1176 12
                $message ?: 'Expected a value to contain at most %2$s characters. Got: %s',
1177 12
                static::valueToString($value),
1178 12
                $max
1179
            ));
1180
        }
1181 24
    }
1182
1183
    /**
1184
     * Inclusive , so Assert::lengthBetween('asd', 3, 5); passes the assertion.
1185
     *
1186
     * @param mixed  $value
1187
     * @param mixed  $min
1188
     * @param mixed  $max
1189
     * @param string $message
1190
     */
1191 60 View Code Duplication
    public static function lengthBetween($value, $min, $max, $message = '')
1192
    {
1193 60
        $length = static::strlen($value);
1194
1195 60
        if ($length < $min || $length > $max) {
1196 24
            static::reportInvalidArgument(\sprintf(
1197 24
                $message ?: 'Expected a value to contain between %2$s and %3$s characters. Got: %s',
1198 24
                static::valueToString($value),
1199 24
                $min,
1200 24
                $max
1201
            ));
1202
        }
1203 36
    }
1204
1205
    /**
1206
     * Will also pass if $value is a directory, use Assert::file() instead if you need to be sure it is a file.
1207
     *
1208
     * @param mixed  $value
1209
     * @param string $message
1210
     */
1211 36 View Code Duplication
    public static function fileExists($value, $message = '')
1212
    {
1213 36
        static::string($value);
1214
1215 36
        if (!\file_exists($value)) {
1216 12
            static::reportInvalidArgument(\sprintf(
1217 12
                $message ?: 'The file %s does not exist.',
1218 12
                static::valueToString($value)
1219
            ));
1220
        }
1221 24
    }
1222
1223
    /**
1224
     * @param mixed  $value
1225
     * @param string $message
1226
     */
1227 12 View Code Duplication
    public static function file($value, $message = '')
1228
    {
1229 12
        static::fileExists($value, $message);
1230
1231 8
        if (!\is_file($value)) {
1232 4
            static::reportInvalidArgument(\sprintf(
1233 4
                $message ?: 'The path %s is not a file.',
1234 4
                static::valueToString($value)
1235
            ));
1236
        }
1237 4
    }
1238
1239
    /**
1240
     * @param mixed  $value
1241
     * @param string $message
1242
     */
1243 12 View Code Duplication
    public static function directory($value, $message = '')
1244
    {
1245 12
        static::fileExists($value, $message);
1246
1247 8
        if (!\is_dir($value)) {
1248 4
            static::reportInvalidArgument(\sprintf(
1249 4
                $message ?: 'The path %s is no directory.',
1250 4
                static::valueToString($value)
1251
            ));
1252
        }
1253 4
    }
1254
1255
    /**
1256
     * @param mixed  $value
1257
     * @param string $message
1258
     */
1259
    public static function readable($value, $message = '')
1260
    {
1261
        if (!\is_readable($value)) {
1262
            static::reportInvalidArgument(\sprintf(
1263
                $message ?: 'The path %s is not readable.',
1264
                static::valueToString($value)
1265
            ));
1266
        }
1267
    }
1268
1269
    /**
1270
     * @param mixed  $value
1271
     * @param string $message
1272
     */
1273
    public static function writable($value, $message = '')
1274
    {
1275
        if (!\is_writable($value)) {
1276
            static::reportInvalidArgument(\sprintf(
1277
                $message ?: 'The path %s is not writable.',
1278
                static::valueToString($value)
1279
            ));
1280
        }
1281
    }
1282
1283
    /**
1284
     * @psalm-assert class-string $value
1285
     *
1286
     * @param mixed  $value
1287
     * @param string $message
1288
     */
1289 8
    public static function classExists($value, $message = '')
1290
    {
1291 8
        if (!\class_exists($value)) {
1292 4
            static::reportInvalidArgument(\sprintf(
1293 4
                $message ?: 'Expected an existing class name. Got: %s',
1294 4
                static::valueToString($value)
1295
            ));
1296
        }
1297 4
    }
1298
1299
    /**
1300
     * @param mixed         $value
1301
     * @param string|object $class
1302
     * @param string        $message
1303
     */
1304 8
    public static function subclassOf($value, $class, $message = '')
1305
    {
1306 8
        if (!\is_subclass_of($value, $class)) {
1307 4
            static::reportInvalidArgument(\sprintf(
1308 4
                $message ?: 'Expected a sub-class of %2$s. Got: %s',
1309 4
                static::valueToString($value),
1310 4
                static::valueToString($class)
1311
            ));
1312
        }
1313 4
    }
1314
1315
    /**
1316
     * @psalm-assert class-string $value
1317
     *
1318
     * @param mixed  $value
1319
     * @param string $message
1320
     */
1321 8
    public static function interfaceExists($value, $message = '')
1322
    {
1323 8
        if (!\interface_exists($value)) {
1324 4
            static::reportInvalidArgument(\sprintf(
1325 4
                $message ?: 'Expected an existing interface name. got %s',
1326 4
                static::valueToString($value)
1327
            ));
1328
        }
1329 4
    }
1330
1331
    /**
1332
     * @param mixed  $value
1333
     * @param mixed  $interface
1334
     * @param string $message
1335
     */
1336 8 View Code Duplication
    public static function implementsInterface($value, $interface, $message = '')
1337
    {
1338 8
        if (!\in_array($interface, \class_implements($value))) {
1339 4
            static::reportInvalidArgument(\sprintf(
1340 4
                $message ?: 'Expected an implementation of %2$s. Got: %s',
1341 4
                static::valueToString($value),
1342 4
                static::valueToString($interface)
1343
            ));
1344
        }
1345 4
    }
1346
1347
    /**
1348
     * @param string|object $classOrObject
1349
     * @param mixed         $property
1350
     * @param string        $message
1351
     */
1352 12 View Code Duplication
    public static function propertyExists($classOrObject, $property, $message = '')
1353
    {
1354 12
        if (!\property_exists($classOrObject, $property)) {
1355 4
            static::reportInvalidArgument(\sprintf(
1356 4
                $message ?: 'Expected the property %s to exist.',
1357 4
                static::valueToString($property)
1358
            ));
1359
        }
1360 8
    }
1361
1362
    /**
1363
     * @param string|object $classOrObject
1364
     * @param mixed         $property
1365
     * @param string        $message
1366
     */
1367 12 View Code Duplication
    public static function propertyNotExists($classOrObject, $property, $message = '')
1368
    {
1369 12
        if (\property_exists($classOrObject, $property)) {
1370 8
            static::reportInvalidArgument(\sprintf(
1371 8
                $message ?: 'Expected the property %s to not exist.',
1372 8
                static::valueToString($property)
1373
            ));
1374
        }
1375 4
    }
1376
1377
    /**
1378
     * @param string|object $classOrObject
1379
     * @param mixed         $method
1380
     * @param string        $message
1381
     */
1382 27 View Code Duplication
    public static function methodExists($classOrObject, $method, $message = '')
1383
    {
1384 27
        if (!\method_exists($classOrObject, $method)) {
1385 19
            static::reportInvalidArgument(\sprintf(
1386 19
                $message ?: 'Expected the method %s to exist.',
1387 19
                static::valueToString($method)
1388
            ));
1389
        }
1390 8
    }
1391
1392
    /**
1393
     * @param string|object $classOrObject
1394
     * @param mixed         $method
1395
     * @param string        $message
1396
     */
1397 27 View Code Duplication
    public static function methodNotExists($classOrObject, $method, $message = '')
1398
    {
1399 27
        if (\method_exists($classOrObject, $method)) {
1400 8
            static::reportInvalidArgument(\sprintf(
1401 8
                $message ?: 'Expected the method %s to not exist.',
1402 8
                static::valueToString($method)
1403
            ));
1404
        }
1405 19
    }
1406
1407
    /**
1408
     * @param array      $array
1409
     * @param string|int $key
1410
     * @param string     $message
1411
     */
1412 12 View Code Duplication
    public static function keyExists($array, $key, $message = '')
1413
    {
1414 12
        if (!(isset($array[$key]) || \array_key_exists($key, $array))) {
1415 4
            static::reportInvalidArgument(\sprintf(
1416 4
                $message ?: 'Expected the key %s to exist.',
1417 4
                static::valueToString($key)
1418
            ));
1419
        }
1420 8
    }
1421
1422
    /**
1423
     * @param array      $array
1424
     * @param string|int $key
1425
     * @param string     $message
1426
     */
1427 12 View Code Duplication
    public static function keyNotExists($array, $key, $message = '')
1428
    {
1429 12
        if (isset($array[$key]) || \array_key_exists($key, $array)) {
1430 8
            static::reportInvalidArgument(\sprintf(
1431 8
                $message ?: 'Expected the key %s to not exist.',
1432 8
                static::valueToString($key)
1433
            ));
1434
        }
1435 4
    }
1436
1437
    /**
1438
     * Does not check if $array is countable, this can generate a warning on php versions after 7.2.
1439
     *
1440
     * @param mixed  $array
1441
     * @param mixed  $number
1442
     * @param string $message
1443
     */
1444 8
    public static function count($array, $number, $message = '')
1445
    {
1446 8
        static::eq(
1447 8
            \count($array),
1448
            $number,
1449 8
            $message ?: \sprintf('Expected an array to contain %d elements. Got: %d.', $number, \count($array))
1450
        );
1451 4
    }
1452
1453
    /**
1454
     * Does not check if $array is countable, this can generate a warning on php versions after 7.2.
1455
     *
1456
     * @param mixed  $array
1457
     * @param mixed  $min
1458
     * @param string $message
1459
     */
1460 12 View Code Duplication
    public static function minCount($array, $min, $message = '')
1461
    {
1462 12
        if (\count($array) < $min) {
1463 4
            static::reportInvalidArgument(\sprintf(
1464 4
                $message ?: 'Expected an array to contain at least %2$d elements. Got: %d',
1465 4
                \count($array),
1466 4
                $min
1467
            ));
1468
        }
1469 8
    }
1470
1471
    /**
1472
     * Does not check if $array is countable, this can generate a warning on php versions after 7.2.
1473
     *
1474
     * @param mixed  $array
1475
     * @param mixed  $max
1476
     * @param string $message
1477
     */
1478 12 View Code Duplication
    public static function maxCount($array, $max, $message = '')
1479
    {
1480 12
        if (\count($array) > $max) {
1481 4
            static::reportInvalidArgument(\sprintf(
1482 4
                $message ?: 'Expected an array to contain at most %2$d elements. Got: %d',
1483 4
                \count($array),
1484 4
                $max
1485
            ));
1486
        }
1487 8
    }
1488
1489
    /**
1490
     * Does not check if $array is countable, this can generate a warning on php versions after 7.2.
1491
     *
1492
     * @param mixed  $array
1493
     * @param mixed  $min
1494
     * @param mixed  $max
1495
     * @param string $message
1496
     */
1497 20
    public static function countBetween($array, $min, $max, $message = '')
1498
    {
1499 20
        $count = \count($array);
1500
1501 20
        if ($count < $min || $count > $max) {
1502 8
            static::reportInvalidArgument(\sprintf(
1503 8
                $message ?: 'Expected an array to contain between %2$d and %3$d elements. Got: %d',
1504 8
                $count,
1505 8
                $min,
1506 8
                $max
1507
            ));
1508
        }
1509 12
    }
1510
1511
    /**
1512
     * @param mixed  $array
1513
     * @param string $message
1514
     */
1515 24
    public static function isList($array, $message = '')
1516
    {
1517 24
        if (!\is_array($array) || !$array || \array_keys($array) !== \range(0, \count($array) - 1)) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $array of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
1518 20
            static::reportInvalidArgument(
1519 20
                $message ?: 'Expected list - non-associative array.'
1520
            );
1521
        }
1522 4
    }
1523
1524
    /**
1525
     * @param mixed  $array
1526
     * @param string $message
1527
     */
1528 16
    public static function isMap($array, $message = '')
1529
    {
1530
        if (
1531 16
            !\is_array($array) ||
1532 16
            !$array ||
0 ignored issues
show
Bug Best Practice introduced by
The expression $array of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
1533
            \array_keys($array) !== \array_filter(\array_keys($array), function ($key) {
1534 12
                return \is_string($key);
1535 16
            })
1536
        ) {
1537 12
            static::reportInvalidArgument(
1538 12
                $message ?: 'Expected map - associative array with string keys.'
1539
            );
1540
        }
1541 4
    }
1542
1543
    /**
1544
     * @param mixed  $value
1545
     * @param string $message
1546
     */
1547 56
    public static function uuid($value, $message = '')
1548
    {
1549 56
        $value = \str_replace(array('urn:', 'uuid:', '{', '}'), '', $value);
1550
1551
        // The nil UUID is special form of UUID that is specified to have all
1552
        // 128 bits set to zero.
1553 56
        if ('00000000-0000-0000-0000-000000000000' === $value) {
1554 4
            return;
1555
        }
1556
1557 52
        if (!\preg_match('/^[0-9A-Fa-f]{8}-[0-9A-Fa-f]{4}-[0-9A-Fa-f]{4}-[0-9A-Fa-f]{4}-[0-9A-Fa-f]{12}$/', $value)) {
1558 20
            static::reportInvalidArgument(\sprintf(
1559 20
                $message ?: 'Value %s is not a valid UUID.',
1560 20
                static::valueToString($value)
1561
            ));
1562
        }
1563 32
    }
1564
1565
    /**
1566
     * @param Closure       $expression
1567
     * @param string|object $class
1568
     * @param string        $message
1569
     */
1570 24
    public static function throws(Closure $expression, $class = 'Exception', $message = '')
1571
    {
1572 24
        static::string($class);
1573
1574 24
        $actual = 'none';
1575
1576
        try {
1577 24
            $expression();
1578 24
        } catch (Exception $e) {
1579 20
            $actual = \get_class($e);
1580 20
            if ($e instanceof $class) {
1581 20
                return;
1582
            }
1583 4
        } catch (Throwable $e) {
0 ignored issues
show
Bug introduced by
The class Throwable does not exist. Is this class maybe located in a folder that is not analyzed, or in a newer version of your dependencies than listed in your composer.lock/composer.json?
Loading history...
1584 4
            $actual = \get_class($e);
1585 4
            if ($e instanceof $class) {
1586 4
                return;
1587
            }
1588
        }
1589
1590 8
        static::reportInvalidArgument($message ?: \sprintf(
1591 8
            'Expected to throw "%s", got "%s"',
1592 8
            $class,
1593 8
            $actual
1594
        ));
1595
    }
1596
1597 1383
    public static function __callStatic($name, $arguments)
1598
    {
1599 1383
        if ('nullOr' === \substr($name, 0, 6)) {
1600 514
            if (null !== $arguments[0]) {
1601 421
                $method = \lcfirst(\substr($name, 6));
1602 421
                \call_user_func_array(array('static', $method), $arguments);
1603
            }
1604
1605 296
            return;
1606
        }
1607
1608 869
        if ('all' === \substr($name, 0, 3)) {
1609 868
            static::isIterable($arguments[0]);
1610
1611 868
            $method = \lcfirst(\substr($name, 3));
1612 868
            $args = $arguments;
1613
1614 868
            foreach ($arguments[0] as $entry) {
1615 868
                $args[0] = $entry;
1616
1617 868
                \call_user_func_array(array('static', $method), $args);
1618
            }
1619
1620 412
            return;
1621
        }
1622
1623 1
        throw new BadMethodCallException('No such method: '.$name);
1624
    }
1625
1626
    /**
1627
     * @param mixed $value
1628
     *
1629
     * @return string
1630
     */
1631 694
    protected static function valueToString($value)
1632
    {
1633 694
        if (null === $value) {
1634 20
            return 'null';
1635
        }
1636
1637 676
        if (true === $value) {
1638 15
            return 'true';
1639
        }
1640
1641 666
        if (false === $value) {
1642 25
            return 'false';
1643
        }
1644
1645 641
        if (\is_array($value)) {
1646 13
            return 'array';
1647
        }
1648
1649 628
        if (\is_object($value)) {
1650 2
            if (\method_exists($value, '__toString')) {
1651 1
                return \get_class($value).': '.self::valueToString($value->__toString());
1652
            }
1653
1654 1
            return \get_class($value);
1655
        }
1656
1657 627
        if (\is_resource($value)) {
1658 1
            return 'resource';
1659
        }
1660
1661 627
        if (\is_string($value)) {
1662 525
            return '"'.$value.'"';
1663
        }
1664
1665 110
        return (string) $value;
1666
    }
1667
1668
    /**
1669
     * @param mixed $value
1670
     *
1671
     * @return string
1672
     */
1673 169
    protected static function typeToString($value)
1674
    {
1675 169
        return \is_object($value) ? \get_class($value) : \gettype($value);
1676
    }
1677
1678 168
    protected static function strlen($value)
1679
    {
1680 168
        if (!\function_exists('mb_detect_encoding')) {
1681
            return \strlen($value);
1682
        }
1683
1684 168
        if (false === $encoding = \mb_detect_encoding($value)) {
1685
            return \strlen($value);
1686
        }
1687
1688 168
        return \mb_strlen($value, $encoding);
1689
    }
1690
1691
    /**
1692
     * @param string $message
1693
     */
1694 918
    protected static function reportInvalidArgument($message)
1695
    {
1696 918
        throw new InvalidArgumentException($message);
1697
    }
1698
1699
    private function __construct()
1700
    {
1701
    }
1702
}
1703