Skip to content

Commit 29d7543

Browse files
committed
Improved Squiz.CSS.DuplicateClassDefinitionSniff to handle media blocks as "scope".
1 parent cc83d36 commit 29d7543

File tree

3 files changed

+62
-3
lines changed

3 files changed

+62
-3
lines changed

CodeSniffer/Standards/Squiz/Sniffs/CSS/DuplicateClassDefinitionSniff.php

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -69,15 +69,33 @@ public function process(PHP_CodeSniffer_File $phpcsFile, $stackPtr)
6969
return;
7070
}
7171

72+
// Save the class names in a "scope",
73+
// to prevent false positives with @media blocks.
74+
$scope = 'main';
75+
7276
$find = array(
7377
T_CLOSE_CURLY_BRACKET,
78+
T_OPEN_CURLY_BRACKET,
7479
T_COMMENT,
7580
T_OPEN_TAG,
7681
);
7782

83+
$exclude = array(
84+
T_WHITESPACE,
85+
T_COMMENT,
86+
);
87+
7888
while ($next !== false) {
7989
$prev = $phpcsFile->findPrevious($find, ($next - 1));
8090

91+
// Check if an inner block was closed.
92+
$beforePrev = $phpcsFile->findPrevious($exclude, ($prev - 1), null, true);
93+
if ($beforePrev !== false
94+
&& $tokens[$beforePrev]['code'] === T_CLOSE_CURLY_BRACKET
95+
) {
96+
$scope = 'main';
97+
}
98+
8199
// Create a sorted name for the class so we can compare classes
82100
// even when the individual names are all over the place.
83101
$name = '';
@@ -94,13 +112,16 @@ public function process(PHP_CodeSniffer_File $phpcsFile, $stackPtr)
94112
sort($names);
95113
$name = implode(',', $names);
96114

97-
if (isset($classNames[$name]) === true) {
98-
$first = $classNames[$name];
115+
if ($name{0} === '@') {
116+
// Media block has its own "scope".
117+
$scope = $name;
118+
} else if (isset($classNames[$scope][$name]) === true) {
119+
$first = $classNames[$scope][$name];
99120
$error = 'Duplicate class definition found; first defined on line %s';
100121
$data = array($tokens[$first]['line']);
101122
$phpcsFile->addError($error, $next, 'Found', $data);
102123
} else {
103-
$classNames[$name] = $next;
124+
$classNames[$scope][$name] = $next;
104125
}
105126

106127
$next = $phpcsFile->findNext(T_OPEN_CURLY_BRACKET, ($next + 1));

CodeSniffer/Standards/Squiz/Tests/CSS/DuplicateClassDefinitionUnitTest.css

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,3 +31,40 @@
3131

3232
.YourClass, .MyClass, .OurClass {
3333
}
34+
35+
36+
.ClassAtTopOfMediaBlock {
37+
}
38+
39+
@media print {
40+
.ClassAtTopOfMediaBlock {
41+
}
42+
43+
.ClassInMultipleMediaBlocks {
44+
}
45+
}
46+
47+
.ClassNotAtTopOfMediaBlock {
48+
}
49+
50+
@media handheld {
51+
.SameClassInMediaBlock {
52+
}
53+
54+
.ClassNotAtTopOfMediaBlock {
55+
}
56+
57+
.SameClassInMediaBlock {
58+
}
59+
}
60+
61+
@media braille {
62+
.PlaceholderClass {
63+
}
64+
65+
.ClassNotAtTopOfMediaBlock {
66+
}
67+
68+
.ClassInMultipleMediaBlocks {
69+
}
70+
}

CodeSniffer/Standards/Squiz/Tests/CSS/DuplicateClassDefinitionUnitTest.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ public function getErrorList()
4343
return array(
4444
9 => 1,
4545
29 => 1,
46+
57 => 1,
4647
);
4748

4849
}//end getErrorList()

0 commit comments

Comments
 (0)