Skip to content

Commit

Permalink
Custo findEndOfStatement in ScopeIndent sniff as the original one has…
Browse files Browse the repository at this point in the history
… a bug

The function File::findEndOfStatement has a bug in finding end of statement
for fn closures, see: squizlabs/PHP_CodeSniffer#2748
  • Loading branch information
michalbundyra committed Dec 8, 2019
1 parent 4fb677f commit e38d51c
Show file tree
Hide file tree
Showing 3 changed files with 75 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -572,7 +572,7 @@ public function process(File $phpcsFile, $stackPtr)
if ($tokens[$prev]['line'] === $tokens[$i]['line']
&& ! ($fp = $this->findPrevious($phpcsFile, $i, [T_OBJECT_OPERATOR]))
) {
$endOfStatement = min($phpcsFile->findEndOfStatement($i), $this->findNext($phpcsFile, $i));
$endOfStatement = min($this->findEndOfStatement($phpcsFile, $i), $this->findNext($phpcsFile, $i));
$newLine = $this->hasContainNewLine($phpcsFile, $i, $endOfStatement);

if ($newLine) {
Expand Down Expand Up @@ -618,7 +618,7 @@ public function process(File $phpcsFile, $stackPtr)
],
true
)) {
$endOfStatement = $phpcsFile->findEndOfStatement($i);
$endOfStatement = $this->findEndOfStatement($phpcsFile, $i);
$newLine = $this->hasContainNewLine($phpcsFile, $i, $endOfStatement);

if ($newLine) {
Expand All @@ -640,7 +640,7 @@ public function process(File $phpcsFile, $stackPtr)
&& isset($tokens[$next]['scope_closer'])
&& $tokens[$next]['scope_closer'] === $next
) {
$endOfStatement = $phpcsFile->findEndOfStatement($next);
$endOfStatement = $this->findEndOfStatement($phpcsFile, $next);
$this->extras($endOfStatement, $this->indent);

$extraIndent += $this->indent;
Expand Down Expand Up @@ -946,6 +946,70 @@ private function findNext(File $phpcsFile, int $ptr, array $search = []) : ?int
return null;
}

/**
* Overrides File::findEndOfStatement as temporary solution until
* https://github.com/squizlabs/PHP_CodeSniffer/issues/2748
* is fixed.
*/
private function findEndOfStatement(File $phpcsFile, int $ptr) : int
{
$closingBracket = [
T_CLOSE_PARENTHESIS,
T_CLOSE_SQUARE_BRACKET,
T_CLOSE_CURLY_BRACKET,
T_CLOSE_SHORT_ARRAY,
];

$tokens = $phpcsFile->getTokens();
$lastToken = $phpcsFile->numTokens;

if ($tokens[$ptr]['code'] === T_DOUBLE_ARROW && $ptr < $lastToken) {
++$ptr;
}

while ($ptr < $lastToken) {
if ($tokens[$ptr]['code'] === T_OPEN_PARENTHESIS) {
$ptr = $tokens[$ptr]['parenthesis_closer'] + 1;
continue;
}

if ($tokens[$ptr]['code'] === T_OPEN_CURLY_BRACKET
|| $tokens[$ptr]['code'] === T_OPEN_SQUARE_BRACKET
|| $tokens[$ptr]['code'] === T_OPEN_SHORT_ARRAY
) {
$ptr = $tokens[$ptr]['bracket_closer'] + 1;
continue;
}

if (isset($tokens[$ptr]['scope_closer']) && $ptr < $tokens[$ptr]['scope_closer']) {
$ptr = $tokens[$ptr]['scope_closer'];
if (in_array($tokens[$ptr]['code'], $closingBracket, true)) {
++$ptr;
}
} elseif (isset($tokens[$ptr]['parenthesis_closer']) && $ptr < $tokens[$ptr]['parenthesis_closer']) {
$ptr = $tokens[$ptr]['parenthesis_closer'];
if (in_array($tokens[$ptr]['code'], $closingBracket, true)) {
++$ptr;
}
}

if ($tokens[$ptr]['code'] === T_COMMA
|| $tokens[$ptr]['code'] === T_SEMICOLON
|| $tokens[$ptr]['code'] === T_DOUBLE_ARROW
) {
return $ptr;
}

if (in_array($tokens[$ptr]['code'], $closingBracket, true)) {
return $phpcsFile->findPrevious(Tokens::$emptyTokens, $ptr - 1, null, true);
}

++$ptr;
}

return $lastToken;
}

/**
* Checks if there is another object operator
* before $ptr token.
Expand Down
4 changes: 4 additions & 0 deletions test/Sniffs/WhiteSpace/ScopeIndentUnitTest.inc
Original file line number Diff line number Diff line change
Expand Up @@ -712,3 +712,7 @@ $a = [
int $d
) => $d,
];

$fn1 = fn (int $a) : int => $a;

$fn2 = fn (int $b) : int => $b;
4 changes: 4 additions & 0 deletions test/Sniffs/WhiteSpace/ScopeIndentUnitTest.inc.fixed
Original file line number Diff line number Diff line change
Expand Up @@ -713,3 +713,7 @@ $a = [
int $d
) => $d,
];

$fn1 = fn (int $a) : int => $a;

$fn2 = fn (int $b) : int => $b;

0 comments on commit e38d51c

Please sign in to comment.