Skip to content

Commit 0e77c7f

Browse files
committed
MM-4961: [EQP][Sniffs Consolidation] Move Magento core sniffs to consolidated repo
- moved sniffs from magento dev/tests/static
1 parent 7630545 commit 0e77c7f

File tree

52 files changed

+3873
-107
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

52 files changed

+3873
-107
lines changed

.travis.yml

-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
language: php
22
php:
3-
- 5.5
43
- 5.6
54
- 7.0
65
- 7.1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,318 @@
1+
<?php
2+
/**
3+
* Copyright © Magento, Inc. All rights reserved.
4+
* See COPYING.txt for license details.
5+
*/
6+
namespace Magento\Sniffs\Annotation;
7+
8+
use PHP_CodeSniffer\Files\File;
9+
10+
/**
11+
* Class to validate annotation format
12+
*/
13+
class AnnotationFormatValidator
14+
{
15+
/**
16+
* Gets the short description end pointer position
17+
*
18+
* @param File $phpcsFile
19+
* @param int $shortPtr
20+
* @param int $commentEndPtr
21+
* @return int
22+
*/
23+
private function getShortDescriptionEndPosition(File $phpcsFile, $shortPtr, $commentEndPtr)
24+
{
25+
$tokens = $phpcsFile->getTokens();
26+
$shortPtrEnd = $shortPtr;
27+
for ($i = ($shortPtr + 1); $i < $commentEndPtr; $i++) {
28+
if ($tokens[$i]['code'] === T_DOC_COMMENT_STRING) {
29+
if ($tokens[$i]['line'] === $tokens[$shortPtrEnd]['line'] + 1) {
30+
$shortPtrEnd = $i;
31+
} else {
32+
break;
33+
}
34+
}
35+
}
36+
return $shortPtrEnd;
37+
}
38+
39+
/**
40+
* Validates whether the short description has multi lines in description
41+
*
42+
* @param File $phpcsFile
43+
* @param int $shortPtr
44+
* @param int $commentEndPtr
45+
*/
46+
private function validateMultiLinesInShortDescription(
47+
File $phpcsFile,
48+
$shortPtr,
49+
$commentEndPtr
50+
) {
51+
$tokens = $phpcsFile->getTokens();
52+
$shortPtrEnd = $this->getShortDescriptionEndPosition(
53+
$phpcsFile,
54+
(int)$shortPtr,
55+
$commentEndPtr
56+
);
57+
$shortPtrEndContent = $tokens[$shortPtrEnd]['content'];
58+
if (preg_match('/^[a-z]/', $shortPtrEndContent)
59+
&& $shortPtrEnd != $shortPtr
60+
&& !preg_match('/\bSee\b/', $shortPtrEndContent)
61+
&& $tokens[$shortPtr]['line'] + 1 === $tokens[$shortPtrEnd]['line']
62+
&& $tokens[$shortPtrEnd]['code'] !== T_DOC_COMMENT_TAG
63+
) {
64+
$error = 'Short description should not be in multi lines';
65+
$phpcsFile->addWarning($error, $shortPtrEnd + 1, 'MethodAnnotation');
66+
}
67+
}
68+
69+
/**
70+
* Validates whether the spacing between short and long descriptions
71+
*
72+
* @param File $phpcsFile
73+
* @param int $shortPtr
74+
* @param int $commentEndPtr
75+
* @param array $emptyTypeTokens
76+
*/
77+
private function validateSpacingBetweenShortAndLongDescriptions(
78+
File $phpcsFile,
79+
$shortPtr,
80+
$commentEndPtr,
81+
array $emptyTypeTokens
82+
) {
83+
$tokens = $phpcsFile->getTokens();
84+
$shortPtrEnd = $this->getShortDescriptionEndPosition(
85+
$phpcsFile,
86+
(int)$shortPtr,
87+
$commentEndPtr
88+
);
89+
$shortPtrEndContent = $tokens[$shortPtrEnd]['content'];
90+
if (preg_match('/^[A-Z]/', $shortPtrEndContent)
91+
&& !preg_match('/\bSee\b/', $shortPtrEndContent)
92+
&& $tokens[$shortPtr]['line'] + 1 === $tokens[$shortPtrEnd]['line']
93+
&& $tokens[$shortPtrEnd]['code'] !== T_DOC_COMMENT_TAG
94+
) {
95+
$error = 'There must be exactly one blank line between lines';
96+
$phpcsFile->addWarning($error, $shortPtrEnd + 1, 'MethodAnnotation');
97+
}
98+
if ($shortPtrEnd != $shortPtr) {
99+
$this->validateLongDescriptionFormat($phpcsFile, $shortPtrEnd, $commentEndPtr, $emptyTypeTokens);
100+
} else {
101+
$this->validateLongDescriptionFormat($phpcsFile, $shortPtr, $commentEndPtr, $emptyTypeTokens);
102+
}
103+
}
104+
105+
/**
106+
* Validates short description format
107+
*
108+
* @param File $phpcsFile
109+
* @param int $shortPtr
110+
* @param int $stackPtr
111+
* @param int $commentEndPtr
112+
* @param array $emptyTypeTokens
113+
*/
114+
private function validateShortDescriptionFormat(
115+
File $phpcsFile,
116+
$shortPtr,
117+
$stackPtr,
118+
$commentEndPtr,
119+
array $emptyTypeTokens
120+
) {
121+
$tokens = $phpcsFile->getTokens();
122+
if ($tokens[$shortPtr]['line'] !== $tokens[$stackPtr]['line'] + 1) {
123+
$error = 'No blank lines are allowed before short description';
124+
$phpcsFile->addWarning($error, $shortPtr, 'MethodAnnotation');
125+
}
126+
if (strtolower($tokens[$shortPtr]['content']) === '{@inheritdoc}') {
127+
$error = 'If the @inheritdoc not inline it shouldn’t have braces';
128+
$phpcsFile->addWarning($error, $shortPtr, 'MethodAnnotation');
129+
}
130+
$shortPtrContent = $tokens[$shortPtr]['content'];
131+
if (preg_match('/^\p{Ll}/u', $shortPtrContent) === 1) {
132+
$error = 'Short description must start with a capital letter';
133+
$phpcsFile->addWarning($error, $shortPtr, 'MethodAnnotation');
134+
}
135+
$this->validateNoExtraNewLineBeforeShortDescription(
136+
$phpcsFile,
137+
$stackPtr,
138+
$commentEndPtr,
139+
$emptyTypeTokens
140+
);
141+
$this->validateSpacingBetweenShortAndLongDescriptions(
142+
$phpcsFile,
143+
$shortPtr,
144+
$commentEndPtr,
145+
$emptyTypeTokens
146+
);
147+
$this->validateMultiLinesInShortDescription(
148+
$phpcsFile,
149+
$shortPtr,
150+
$commentEndPtr
151+
);
152+
}
153+
154+
/**
155+
* Validates long description format
156+
*
157+
* @param File $phpcsFile
158+
* @param int $shortPtrEnd
159+
* @param int $commentEndPtr
160+
* @param array $emptyTypeTokens
161+
*/
162+
private function validateLongDescriptionFormat(
163+
File $phpcsFile,
164+
$shortPtrEnd,
165+
$commentEndPtr,
166+
array $emptyTypeTokens
167+
) {
168+
$tokens = $phpcsFile->getTokens();
169+
$longPtr = $phpcsFile->findNext($emptyTypeTokens, $shortPtrEnd + 1, $commentEndPtr - 1, true);
170+
if (strtolower($tokens[$longPtr]['content']) === '@inheritdoc') {
171+
$error = '@inheritdoc imports only short description, annotation must have long description';
172+
$phpcsFile->addWarning($error, $longPtr, 'MethodAnnotation');
173+
}
174+
if ($longPtr !== false && $tokens[$longPtr]['code'] === T_DOC_COMMENT_STRING) {
175+
if ($tokens[$longPtr]['line'] !== $tokens[$shortPtrEnd]['line'] + 2) {
176+
$error = 'There must be exactly one blank line between descriptions';
177+
$phpcsFile->addWarning($error, $longPtr, 'MethodAnnotation');
178+
}
179+
if (preg_match('/^\p{Ll}/u', $tokens[$longPtr]['content']) === 1) {
180+
$error = 'Long description must start with a capital letter';
181+
$phpcsFile->addWarning($error, $longPtr, 'MethodAnnotation');
182+
}
183+
}
184+
}
185+
186+
/**
187+
* Validates tags spacing format
188+
*
189+
* @param File $phpcsFile
190+
* @param int $commentStartPtr
191+
* @param array $emptyTypeTokens
192+
*/
193+
public function validateTagsSpacingFormat(File $phpcsFile, $commentStartPtr, array $emptyTypeTokens)
194+
{
195+
$tokens = $phpcsFile->getTokens();
196+
if (isset($tokens[$commentStartPtr]['comment_tags'][0])) {
197+
$firstTagPtr = $tokens[$commentStartPtr]['comment_tags'][0];
198+
$commentTagPtrContent = $tokens[$firstTagPtr]['content'];
199+
$prevPtr = $phpcsFile->findPrevious($emptyTypeTokens, $firstTagPtr - 1, $commentStartPtr, true);
200+
if ($tokens[$firstTagPtr]['line'] !== $tokens[$prevPtr]['line'] + 2
201+
&& strtolower($commentTagPtrContent) !== '@inheritdoc'
202+
) {
203+
$error = 'There must be exactly one blank line before tags';
204+
$phpcsFile->addWarning($error, $firstTagPtr, 'MethodAnnotation');
205+
}
206+
}
207+
}
208+
209+
/**
210+
* Validates tag grouping format
211+
*
212+
* @param File $phpcsFile
213+
* @param int $commentStartPtr
214+
*/
215+
public function validateTagGroupingFormat(File $phpcsFile, $commentStartPtr)
216+
{
217+
$tokens = $phpcsFile->getTokens();
218+
$tagGroups = [];
219+
$groupId = 0;
220+
$paramGroupId = null;
221+
foreach ($tokens[$commentStartPtr]['comment_tags'] as $position => $tag) {
222+
if ($position > 0) {
223+
$prevPtr = $phpcsFile->findPrevious(
224+
T_DOC_COMMENT_STRING,
225+
$tag - 1,
226+
$tokens[$commentStartPtr]['comment_tags'][$position - 1]
227+
);
228+
if ($prevPtr === false) {
229+
$prevPtr = $tokens[$commentStartPtr]['comment_tags'][$position - 1];
230+
}
231+
232+
if ($tokens[$prevPtr]['line'] !== $tokens[$tag]['line'] - 1) {
233+
$groupId++;
234+
}
235+
}
236+
237+
if (strtolower($tokens[$tag]['content']) === '@param') {
238+
if ($paramGroupId !== null
239+
&& $paramGroupId !== $groupId) {
240+
$error = 'Parameter tags must be grouped together';
241+
$phpcsFile->addWarning($error, $tag, 'MethodAnnotation');
242+
}
243+
if ($paramGroupId === null) {
244+
$paramGroupId = $groupId;
245+
}
246+
}
247+
$tagGroups[$groupId][] = $tag;
248+
}
249+
}
250+
251+
/**
252+
* Validates extra newline before short description
253+
*
254+
* @param File $phpcsFile
255+
* @param int $commentStartPtr
256+
* @param int $commentEndPtr
257+
* @param array $emptyTypeTokens
258+
*/
259+
private function validateNoExtraNewLineBeforeShortDescription(
260+
File $phpcsFile,
261+
$commentStartPtr,
262+
$commentEndPtr,
263+
array $emptyTypeTokens
264+
) {
265+
$tokens = $phpcsFile->getTokens();
266+
$prevPtr = $phpcsFile->findPrevious($emptyTypeTokens, $commentEndPtr - 1, $commentStartPtr, true);
267+
if ($tokens[$prevPtr]['line'] < ($tokens[$commentEndPtr]['line'] - 1)) {
268+
$error = 'Additional blank lines found at end of the annotation block';
269+
$phpcsFile->addWarning($error, $commentEndPtr, 'MethodAnnotation');
270+
}
271+
}
272+
273+
/**
274+
* Validates structure description format
275+
*
276+
* @param File $phpcsFile
277+
* @param int $commentStartPtr
278+
* @param int $shortPtr
279+
* @param int $commentEndPtr
280+
* @param array $emptyTypeTokens
281+
*/
282+
public function validateDescriptionFormatStructure(
283+
File $phpcsFile,
284+
$commentStartPtr,
285+
$shortPtr,
286+
$commentEndPtr,
287+
array $emptyTypeTokens
288+
) {
289+
$tokens = $phpcsFile->getTokens();
290+
if (isset($tokens[$commentStartPtr]['comment_tags'][0])
291+
) {
292+
$commentTagPtr = $tokens[$commentStartPtr]['comment_tags'][0];
293+
$commentTagPtrContent = $tokens[$commentTagPtr]['content'];
294+
if ($tokens[$shortPtr]['code'] !== T_DOC_COMMENT_STRING
295+
&& strtolower($commentTagPtrContent) !== '@inheritdoc'
296+
) {
297+
$error = 'Missing short description';
298+
$phpcsFile->addWarning($error, $commentStartPtr, 'MethodAnnotation');
299+
} else {
300+
$this->validateShortDescriptionFormat(
301+
$phpcsFile,
302+
(int)$shortPtr,
303+
$commentStartPtr,
304+
$commentEndPtr,
305+
$emptyTypeTokens
306+
);
307+
}
308+
} else {
309+
$this->validateShortDescriptionFormat(
310+
$phpcsFile,
311+
(int)$shortPtr,
312+
$commentStartPtr,
313+
$commentEndPtr,
314+
$emptyTypeTokens
315+
);
316+
}
317+
}
318+
}

0 commit comments

Comments
 (0)