Completed
Branch v2.0.0 (addc15)
by Alexander
03:27
created

UserPasswordValidation   A

Complexity

Total Complexity 12

Size/Duplication

Total Lines 88
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 1

Importance

Changes 0
Metric Value
wmc 12
lcom 1
cbo 1
dl 0
loc 88
c 0
b 0
f 0
rs 10

7 Methods

Rating   Name   Duplication   Size   Complexity  
A validate() 0 8 1
A doValidation() 0 18 6
A validateLength() 0 6 1
A validateLetters() 0 4 1
A validateNumbers() 0 4 1
A validateCaseDiff() 0 4 1
A validateWeakPasswords() 0 20 1
1
<?php
2
/**
3
 * @author Alexander Torosh <[email protected]>
4
 */
5
6
namespace Domain\User\Validation;
7
8
use Domain\Core\DomainException;
9
10
class UserPasswordValidation
11
{
12
    /**
13
     * @throws DomainException
14
     */
15
    public static function validate(string $password): bool
16
    {
17
        $password = trim($password);
18
        self::doValidation($password);
19
20
        // Default result
21
        return true;
22
    }
23
24
    /**
25
     * @throws DomainException
26
     */
27
    private static function doValidation(string $password)
28
    {
29
        if (!self::validateLength($password)) {
30
            throw new DomainException('Password length must be at least 8 characters.');
31
        }
32
        if (!self::validateLetters($password)) {
0 ignored issues
show
Bug Best Practice introduced by
The expression self::validateLetters($password) of type false|integer is loosely compared to false; this is ambiguous if the integer can be zero. 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 integer values, zero is a special case, in particular the following results might be unexpected:

0   == false // true
0   == null  // true
123 == false // false
123 == null  // false

// It is often better to use strict comparison
0 === false // false
0 === null  // false
Loading history...
33
            throw new DomainException('Password must contain at least one letter.');
34
        }
35
        if (!self::validateNumbers($password)) {
0 ignored issues
show
Bug Best Practice introduced by
The expression self::validateNumbers($password) of type false|integer is loosely compared to false; this is ambiguous if the integer can be zero. 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 integer values, zero is a special case, in particular the following results might be unexpected:

0   == false // true
0   == null  // true
123 == false // false
123 == null  // false

// It is often better to use strict comparison
0 === false // false
0 === null  // false
Loading history...
36
            throw new DomainException('Password must contain at least one number.');
37
        }
38
        if (!self::validateCaseDiff($password)) {
0 ignored issues
show
Bug Best Practice introduced by
The expression self::validateCaseDiff($password) of type false|integer is loosely compared to false; this is ambiguous if the integer can be zero. 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 integer values, zero is a special case, in particular the following results might be unexpected:

0   == false // true
0   == null  // true
123 == false // false
123 == null  // false

// It is often better to use strict comparison
0 === false // false
0 === null  // false
Loading history...
39
            throw new DomainException('Password must contain at least one uppercase and one lowercase letter.');
40
        }
41
        if (!self::validateWeakPasswords($password)) {
42
            throw new DomainException('Your password doesn\'t meet our minimum requirements. Please enter a stronger password.');
43
        }
44
    }
45
46
    private static function validateLength(string $password): bool
47
    {
48
        $length = mb_strlen($password);
49
50
        return $length >= 8;
51
    }
52
53
    /**
54
     * @return false|int
55
     */
56
    private static function validateLetters(string $password)
57
    {
58
        return preg_match('/\pL/u', $password);
59
    }
60
61
    /**
62
     * @return false|int
63
     */
64
    private static function validateNumbers(string $password)
65
    {
66
        return preg_match('/\pN/u', $password);
67
    }
68
69
    /**
70
     * @return false|int
71
     */
72
    private static function validateCaseDiff(string $password)
73
    {
74
        return preg_match('/(\p{Ll}+.*\p{Lu})|(\p{Lu}+.*\p{Ll})/u', $password);
75
    }
76
77
    private static function validateWeakPasswords(string $password): bool
78
    {
79
        $weakList = [
80
            'password',
81
            '12345678',
82
            '123456789',
83
            '1234567890',
84
            'qwertyui',
85
            'baseball',
86
            'football',
87
            'abc12345',
88
            'abcd1234',
89
            'jennifer',
90
            '11111111',
91
            'superman',
92
            'pussycat',
93
        ];
94
95
        return false === in_array($password, $weakList, true);
96
    }
97
}
98