Passed
Push — master ( 239abe...00bc3e )
by Björn
02:21
created

CamelCaseVariableSniff::areRequirementsMet()   A

Complexity

Conditions 5
Paths 5

Size

Total Lines 19

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 19
rs 9.3222
c 0
b 0
f 0
cc 5
nc 5
nop 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace BestIt\Sniffs\NamingConventions;
6
7
use BestIt\Sniffs\AbstractSniff;
8
use BestIt\Sniffs\VariableRegistrationTrait;
9
use PHP_CodeSniffer\Util\Common;
10
use SlevomatCodingStandard\Helpers\PropertyHelper;
11
use SlevomatCodingStandard\Helpers\TokenHelper;
12
use function array_key_exists;
13
use function substr;
14
use const T_EQUAL;
15
use const T_SEMICOLON;
16
17
/**
18
 * Registers an error if the variables are not in camelCase (lc first).
19
 *
20
 * @author blange <[email protected]>
21
 * @package BestIt\Sniffs\NamingConventions
22
 */
23
class CamelCaseVariableSniff extends AbstractSniff
24
{
25
    use VariableRegistrationTrait;
26
27
    /**
28
     * The error code for this sniff.
29
     *
30
     * @var string
31
     */
32
    public const CODE_NOT_CAMEL_CASE = 'NotCamelCase';
33
34
    /**
35
     * The error message for this sniff.
36
     *
37
     * @var string
38
     */
39
    private const MESSAGE_NOT_CAMEL_CASE = 'Variable %s should be in camelCase (lowercase first).';
40
41
    /**
42
     * The previously sniffed file.
43
     *
44
     * @var string
45
     */
46
    private $prevSniffedFile = '';
47
48
    /**
49
     * The vars which were sniffed in this file.
50
     *
51
     * @var array
52
     */
53
    private $sniffedVars = [];
54
55
    /**
56
     * Returns true if there is a value assignment or a property declaration, but which can be without an assignment.
57
     *
58
     * @return bool
59
     */
60
    protected function areRequirementsMet(): bool
61
    {
62
        $var = $this->token['content'];
63
64
        // We need to check everything != $this.
65
        if ($return = $var !== '$this') {
66
            $nextPos = (int) TokenHelper::findNextEffective($this->file->getBaseFile(), $this->stackPos + 1);
67
68
            if ($nextPos > 0) {
69
                $isProperty = PropertyHelper::isProperty($this->file->getBaseFile(), $this->stackPos);
70
                $nextTokenCode = $this->tokens[$nextPos]['code'];
71
72
                // The var should be followed by an "=" or can be followed by a semicolon if its a property.
73
                $return = ($nextTokenCode === T_EQUAL) || ($nextTokenCode === T_SEMICOLON && $isProperty);
74
            }
75
        }
76
77
        return $return;
78
    }
79
80
    /**
81
     * Processes the token.
82
     *
83
     * @see self::setUp()
84
     *
85
     * @return void
86
     */
87
    protected function processToken(): void
88
    {
89
        // "Sniff" the var name only once, but register the possible error everytime the var is declared.
90
        if (!$this->sniffedVars[$var = $this->token['content']]) {
91
            $this->file->recordMetric($this->stackPos, 'CamelCase var name', 'no');
92
93
            if (!$this->isSniffSuppressed(static::CODE_NOT_CAMEL_CASE)) {
94
                $this->file->addError(
95
                    self::MESSAGE_NOT_CAMEL_CASE,
96
                    $this->stackPos,
97
                    static::CODE_NOT_CAMEL_CASE,
98
                    [
99
                        $var
100
                    ]
101
                );
102
            }
103
        } else {
104
            $this->file->recordMetric($this->stackPos, 'CamelCase var name', 'yes');
105
        }
106
    }
107
108
    /**
109
     * Sets up the sniff.
110
     *
111
     * @return void
112
     */
113
    protected function setUp(): void
114
    {
115
        parent::setUp();
116
117
        $this->prevSniffedFile = $this->file->getFilename();
118
119
        if (!array_key_exists($var = $this->token['content'], $this->sniffedVars)) {
120
            // "Sniff" the var name only once ...
121
            $this->sniffedVars[$var] = Common::isCamelCaps(substr($var, 1));
122
        }
123
    }
124
125
    /**
126
     * Cleans the cache of this sniff.
127
     *
128
     * @return void
129
     */
130
    protected function tearDown(): void
131
    {
132
        parent::tearDown();
133
134
        if ($this->prevSniffedFile && $this->prevSniffedFile !== $this->file->getFilename()) {
135
            $this->sniffedVars = [];
136
            $this->prevSniffedFile = '';
137
        }
138
    }
139
}
140