diff --git a/composer.json b/composer.json index 5cf3dbf..6aa0936 100644 --- a/composer.json +++ b/composer.json @@ -13,7 +13,7 @@ "require": { "php": ">=8.1", "illuminate/view": "*", - "nikic/php-parser": "^4.15", + "nikic/php-parser": "^5.0", "symfony/console": "^6.1||^7.0", "symfony/process": "^6.1||^7.0" }, diff --git a/src/BaseFormatter.php b/src/BaseFormatter.php index e7dc065..d471636 100644 --- a/src/BaseFormatter.php +++ b/src/BaseFormatter.php @@ -2,12 +2,11 @@ namespace Tighten\TLint; -use PhpParser\Lexer; use PhpParser\Parser; class BaseFormatter extends AbstractBase { - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { return $this->code; } diff --git a/src/Formatters/ArrayParametersOverViewWith.php b/src/Formatters/ArrayParametersOverViewWith.php index 918decc..4bebc9a 100644 --- a/src/Formatters/ArrayParametersOverViewWith.php +++ b/src/Formatters/ArrayParametersOverViewWith.php @@ -3,11 +3,10 @@ namespace Tighten\TLint\Formatters; use Closure; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\Node\Arg; +use PhpParser\Node\ArrayItem; use PhpParser\Node\Expr\Array_; -use PhpParser\Node\Expr\ArrayItem; use PhpParser\Node\Expr\FuncCall; use PhpParser\Node\Name; use PhpParser\NodeTraverser; @@ -27,19 +26,21 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); $oldStmts = $parser->parse($this->code); + $oldTokens = $parser->getTokens(); + $newStmts = $traverser->traverse($oldStmts); $traverser = new NodeTraverser; $traverser->addVisitor($this->visitor()); $newStmts = $traverser->traverse($newStmts); - return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $lexer->getTokens())); + return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $oldTokens)); } private function visitor(): NodeVisitorAbstract diff --git a/src/Formatters/FullyQualifiedFacades.php b/src/Formatters/FullyQualifiedFacades.php index 1b3e020..c08838f 100644 --- a/src/Formatters/FullyQualifiedFacades.php +++ b/src/Formatters/FullyQualifiedFacades.php @@ -2,11 +2,10 @@ namespace Tighten\TLint\Formatters; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\Node\Name; use PhpParser\Node\Stmt\Use_; -use PhpParser\Node\Stmt\UseUse; +use PhpParser\Node\UseItem; use PhpParser\NodeTraverser; use PhpParser\NodeVisitor\CloningVisitor; use PhpParser\NodeVisitorAbstract; @@ -21,12 +20,14 @@ class FullyQualifiedFacades extends BaseFormatter public const DESCRIPTION = 'Import facades using their full namespace.'; - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); $oldStmts = $parser->parse($this->code); + $oldTokens = $parser->getTokens(); + $newStmts = $traverser->traverse($oldStmts); $traverser = new NodeTraverser; @@ -43,7 +44,7 @@ public function format(Parser $parser, Lexer $lexer): string $traverser->addVisitor($this->transformFacadesVisitor()); $newStmts = $traverser->traverse($newStmts); - return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $lexer->getTokens())); + return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $oldTokens)); } private function currentFullyQualifiedFacadesVisitor(): NodeVisitorAbstract @@ -111,7 +112,7 @@ public function enterNode(Node $node): Node|int|null return null; } - return new Use_([new UseUse(new Name($facades[$useStatement]))]); + return new Use_([new UseItem(new Name($facades[$useStatement]))]); } }; } diff --git a/src/Formatters/MailableMethodsInBuild.php b/src/Formatters/MailableMethodsInBuild.php index a052f18..b6146ea 100644 --- a/src/Formatters/MailableMethodsInBuild.php +++ b/src/Formatters/MailableMethodsInBuild.php @@ -2,7 +2,6 @@ namespace Tighten\TLint\Formatters; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\Node\Stmt\ClassMethod; use PhpParser\NodeTraverser; @@ -22,12 +21,14 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); $oldStmts = $parser->parse($this->code); + $oldTokens = $parser->getTokens(); + $newStmts = $traverser->traverse($oldStmts); $constructorVisitor = $this->constructorVisitor(); @@ -42,7 +43,7 @@ public function format(Parser $parser, Lexer $lexer): string $traverser->addVisitor($buildVisitor); $newStmts = $traverser->traverse($newStmts); - return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $lexer->getTokens())); + return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $oldTokens)); } private function constructorVisitor(): NodeVisitorAbstract diff --git a/src/Formatters/NoDatesPropertyOnModels.php b/src/Formatters/NoDatesPropertyOnModels.php index a2603ac..336bef8 100644 --- a/src/Formatters/NoDatesPropertyOnModels.php +++ b/src/Formatters/NoDatesPropertyOnModels.php @@ -3,14 +3,13 @@ namespace Tighten\TLint\Formatters; use Closure; -use PhpParser\Lexer; +use PhpParser\Modifiers; use PhpParser\Node; +use PhpParser\Node\ArrayItem; use PhpParser\Node\Expr\Array_; -use PhpParser\Node\Expr\ArrayItem; +use PhpParser\Node\PropertyItem; use PhpParser\Node\Scalar\String_; -use PhpParser\Node\Stmt\Class_; use PhpParser\Node\Stmt\Property; -use PhpParser\Node\Stmt\PropertyProperty; use PhpParser\NodeFinder; use PhpParser\NodeTraverser; use PhpParser\NodeVisitor\CloningVisitor; @@ -27,22 +26,24 @@ class NoDatesPropertyOnModels extends BaseFormatter protected bool $model = false; - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); - $originalStatements = $parser->parse($this->code); - $statements = $traverser->traverse($originalStatements); + $oldStmts = $parser->parse($this->code); + $oldTokens = $parser->getTokens(); + + $newStmts = $traverser->traverse($oldStmts); $nodeFinder = new NodeFinder; - $dates = $nodeFinder->findFirst($statements, $this->nodeFinderForModelProperty('dates')); - $casts = $nodeFinder->findFirst($statements, $this->nodeFinderForModelProperty('casts')); + $dates = $nodeFinder->findFirst($newStmts, $this->nodeFinderForModelProperty('dates')); + $casts = $nodeFinder->findFirst($newStmts, $this->nodeFinderForModelProperty('casts')); if ($dates) { $newCasts = $this->addDatesToCasts($dates, $casts); - $statements = array_map(function (Node $node) use ($newCasts) { + $newStmts = array_map(function (Node $node) use ($newCasts) { if ($this->extendsAny($node, ['Model', 'Pivot', 'Authenticatable'])) { // Replace the dates with the new casts and remove any existing casts (necessary so // that we know where to put the new casts if there weren't any already) @@ -58,10 +59,10 @@ public function format(Parser $parser, Lexer $lexer): string } return $node; - }, $statements); + }, $newStmts); } - return preg_replace('/\r?\n/', PHP_EOL, $this->printer()->printFormatPreserving($statements, $originalStatements, $lexer->getTokens())); + return preg_replace('/\r?\n/', PHP_EOL, $this->printer()->printFormatPreserving($newStmts, $oldStmts, $oldTokens)); } private function nodeFinderForModelProperty(string $attribute): Closure @@ -110,8 +111,8 @@ private function addDatesToCasts(Property $dates, ?Property $casts = null): Prop // We have to return a *new* Property node here (even if there was // already a casts property) so the printer formats it correctly - return new Property(Class_::MODIFIER_PROTECTED, [ - new PropertyProperty('casts', new Array_($newCasts, ['kind' => Array_::KIND_SHORT])), + return new Property(Modifiers::PROTECTED, [ + new PropertyItem('casts', new Array_($newCasts, ['kind' => Array_::KIND_SHORT])), ]); } @@ -120,7 +121,7 @@ private function printer(): Standard return new class extends Standard { // Force all arrays to be printed in multiline style - protected function pMaybeMultiline(array $nodes, bool $trailingComma = true) + protected function pMaybeMultiline(array $nodes, bool $trailingComma = true): string { return $this->pCommaSeparatedMultiline($nodes, $trailingComma) . $this->nl; } diff --git a/src/Formatters/NoDocBlocksForMigrationUpDown.php b/src/Formatters/NoDocBlocksForMigrationUpDown.php index eb13e6d..7aa3733 100644 --- a/src/Formatters/NoDocBlocksForMigrationUpDown.php +++ b/src/Formatters/NoDocBlocksForMigrationUpDown.php @@ -2,7 +2,6 @@ namespace Tighten\TLint\Formatters; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\NodeTraverser; use PhpParser\NodeVisitor\FindingVisitor; @@ -16,7 +15,7 @@ class NoDocBlocksForMigrationUpDown extends BaseFormatter public const DESCRIPTION = 'Removes doc blocks from the up and down method in migrations.'; - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $oldStmts = $parser->parse($this->code); diff --git a/src/Formatters/NoLeadingSlashesOnRoutePaths.php b/src/Formatters/NoLeadingSlashesOnRoutePaths.php index c339871..8ac2182 100644 --- a/src/Formatters/NoLeadingSlashesOnRoutePaths.php +++ b/src/Formatters/NoLeadingSlashesOnRoutePaths.php @@ -3,7 +3,6 @@ namespace Tighten\TLint\Formatters; use Illuminate\Support\Str; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\Node\Arg; use PhpParser\Node\Expr\StaticCall; @@ -25,12 +24,14 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); $oldStmts = $parser->parse($this->code); + $oldTokens = $parser->getTokens(); + $newStmts = $traverser->traverse($oldStmts); $traverser = new NodeTraverser; @@ -38,7 +39,7 @@ public function format(Parser $parser, Lexer $lexer): string $newStmts = $traverser->traverse($newStmts); - return (new Standard)->printFormatPreserving($newStmts, $oldStmts, $lexer->getTokens()); + return (new Standard)->printFormatPreserving($newStmts, $oldStmts, $oldTokens); } private function visitor(): NodeVisitorAbstract diff --git a/src/Formatters/NoSpaceAfterBladeDirectives.php b/src/Formatters/NoSpaceAfterBladeDirectives.php index aad637f..009b76f 100644 --- a/src/Formatters/NoSpaceAfterBladeDirectives.php +++ b/src/Formatters/NoSpaceAfterBladeDirectives.php @@ -3,7 +3,6 @@ namespace Tighten\TLint\Formatters; use Illuminate\Support\Str; -use PhpParser\Lexer; use PhpParser\Parser; use Tighten\TLint\BaseFormatter; use Tighten\TLint\Linters\NoSpaceAfterBladeDirectives as Linter; @@ -17,7 +16,7 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { foreach ($this->getCodeLines() as $index => $codeLine) { $matches = []; diff --git a/src/Formatters/OneLineBetweenClassVisibilityChanges.php b/src/Formatters/OneLineBetweenClassVisibilityChanges.php index 22f7772..65edb84 100644 --- a/src/Formatters/OneLineBetweenClassVisibilityChanges.php +++ b/src/Formatters/OneLineBetweenClassVisibilityChanges.php @@ -3,7 +3,6 @@ namespace Tighten\TLint\Formatters; use PhpParser\Comment; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\Node\Stmt\ClassConst; use PhpParser\Node\Stmt\Property; @@ -24,19 +23,21 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); $oldStmts = $parser->parse($this->code); + $oldTokens = $parser->getTokens(); + $newStmts = $traverser->traverse($oldStmts); $traverser = new NodeTraverser; $traverser->addVisitor($this->visitor()); $newStmts = $traverser->traverse($newStmts); - return preg_replace('/\ *\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $lexer->getTokens())); + return preg_replace('/\ *\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $oldTokens)); } private function visitor(): NodeVisitorAbstract @@ -103,7 +104,7 @@ public function enterNode(Node $node) } } - $node->setAttribute('comments', [new Comment("\n"), ...$node->getComments()]); + $node->setAttribute('comments', [new Comment(''), ...$node->getComments()]); return $node; } diff --git a/src/Formatters/RemoveLeadingSlashNamespaces.php b/src/Formatters/RemoveLeadingSlashNamespaces.php index 87ff8c5..9eac4d4 100644 --- a/src/Formatters/RemoveLeadingSlashNamespaces.php +++ b/src/Formatters/RemoveLeadingSlashNamespaces.php @@ -3,7 +3,6 @@ namespace Tighten\TLint\Formatters; use Illuminate\Support\Str; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\NodeTraverser; use PhpParser\NodeVisitor\CloningVisitor; @@ -21,7 +20,7 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); @@ -63,7 +62,7 @@ public function getReplacements() public function enterNode(Node $node): Node|int|null { - if (! $node instanceof Node\Stmt\UseUse) { + if (! $node instanceof Node\UseItem) { return null; } diff --git a/src/Formatters/RequestHelperFunctionWherePossible.php b/src/Formatters/RequestHelperFunctionWherePossible.php index d723279..314c0c5 100644 --- a/src/Formatters/RequestHelperFunctionWherePossible.php +++ b/src/Formatters/RequestHelperFunctionWherePossible.php @@ -3,7 +3,6 @@ namespace Tighten\TLint\Formatters; use Closure; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\Node\Expr\FuncCall; use PhpParser\Node\Name; @@ -24,12 +23,14 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); $oldStmts = $parser->parse($this->code); + $oldTokens = $parser->getTokens(); + $newStmts = $traverser->traverse($oldStmts); $visitor = $this->visitor(); @@ -38,7 +39,7 @@ public function format(Parser $parser, Lexer $lexer): string $traverser->addVisitor($visitor); $newStmts = $traverser->traverse($newStmts); - return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $lexer->getTokens())); + return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $oldTokens)); } private function visitor(): NodeVisitorAbstract diff --git a/src/Formatters/RequestValidation.php b/src/Formatters/RequestValidation.php index 46f29bf..2347e0a 100644 --- a/src/Formatters/RequestValidation.php +++ b/src/Formatters/RequestValidation.php @@ -2,7 +2,6 @@ namespace Tighten\TLint\Formatters; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\Node\Expr\FuncCall; use PhpParser\Node\Expr\MethodCall; @@ -24,19 +23,21 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); $oldStmts = $parser->parse($this->code); + $oldTokens = $parser->getTokens(); + $newStmts = $traverser->traverse($oldStmts); $traverser = new NodeTraverser; $traverser->addVisitor($this->visitor()); $newStmts = $traverser->traverse($newStmts); - return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $lexer->getTokens())); + return preg_replace('/\r?\n/', PHP_EOL, (new Standard)->printFormatPreserving($newStmts, $oldStmts, $oldTokens)); } private function visitor(): NodeVisitorAbstract diff --git a/src/Formatters/SpaceAfterBladeDirectives.php b/src/Formatters/SpaceAfterBladeDirectives.php index 0659c2b..a7701d4 100644 --- a/src/Formatters/SpaceAfterBladeDirectives.php +++ b/src/Formatters/SpaceAfterBladeDirectives.php @@ -2,7 +2,6 @@ namespace Tighten\TLint\Formatters; -use PhpParser\Lexer; use PhpParser\Parser; use Tighten\TLint\BaseFormatter; use Tighten\TLint\Linters\SpaceAfterBladeDirectives as Linter; @@ -16,7 +15,7 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { foreach ($this->getCodeLines() as $index => $codeLine) { $matches = []; diff --git a/src/Formatters/SpacesAroundBladeRenderContent.php b/src/Formatters/SpacesAroundBladeRenderContent.php index d833a66..c159c51 100644 --- a/src/Formatters/SpacesAroundBladeRenderContent.php +++ b/src/Formatters/SpacesAroundBladeRenderContent.php @@ -2,7 +2,6 @@ namespace Tighten\TLint\Formatters; -use PhpParser\Lexer; use PhpParser\Parser; use Tighten\TLint\BaseFormatter; use Tighten\TLint\Linters\SpacesAroundBladeRenderContent as Linter; @@ -16,7 +15,7 @@ public static function appliesToPath(string $path, array $configPaths): bool return Linter::appliesToPath($path, $configPaths); } - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { foreach ($this->getCodeLines() as $index => $codeLine) { $matchesNormal = []; diff --git a/src/Formatters/UseAnonymousMigrations.php b/src/Formatters/UseAnonymousMigrations.php index 41f4781..bcb2a41 100644 --- a/src/Formatters/UseAnonymousMigrations.php +++ b/src/Formatters/UseAnonymousMigrations.php @@ -2,7 +2,6 @@ namespace Tighten\TLint\Formatters; -use PhpParser\Lexer; use PhpParser\Node; use PhpParser\Node\Stmt\Class_; use PhpParser\NodeTraverser; @@ -17,7 +16,7 @@ class UseAnonymousMigrations extends BaseFormatter public const DESCRIPTION = 'Prefer anonymous class migrations.'; - public function format(Parser $parser, Lexer $lexer): string + public function format(Parser $parser): string { $traverser = new NodeTraverser; $traverser->addVisitor(new CloningVisitor); diff --git a/src/Linters/FullyQualifiedFacades.php b/src/Linters/FullyQualifiedFacades.php index c7afadc..576ccf1 100644 --- a/src/Linters/FullyQualifiedFacades.php +++ b/src/Linters/FullyQualifiedFacades.php @@ -32,7 +32,7 @@ protected function visitor(): Closure * Check if the node is a use statement and not a group use statement * Return if use statement is a facade or not */ - if ($node instanceof Node\Stmt\UseUse && ! in_array($node->name->toString(), $groupUse)) { + if ($node instanceof Node\UseItem && ! in_array($node->name->toString(), $groupUse)) { return in_array($node->name->toString(), array_keys(static::$aliases)); } diff --git a/src/Linters/RemoveLeadingSlashNamespaces.php b/src/Linters/RemoveLeadingSlashNamespaces.php index 5ab88d3..77e2ecf 100644 --- a/src/Linters/RemoveLeadingSlashNamespaces.php +++ b/src/Linters/RemoveLeadingSlashNamespaces.php @@ -40,7 +40,7 @@ public function lint(Parser $parser) }); $useStatementsVisitor = new FindingVisitor(function (Node $node) { - if (! $node instanceof Node\Stmt\UseUse) { + if (! $node instanceof Node\UseItem) { return false; } diff --git a/src/TFormat.php b/src/TFormat.php index ef93c9d..5ba41cb 100644 --- a/src/TFormat.php +++ b/src/TFormat.php @@ -2,28 +2,19 @@ namespace Tighten\TLint; -use PhpParser\Lexer\Emulative; -use PhpParser\Parser\Php7; +use PhpParser\ParserFactory; class TFormat { private $parser; - private $lexer; public function __construct() { - $this->lexer = new Emulative([ - 'usedAttributes' => [ - 'comments', - 'startLine', 'endLine', - 'startTokenPos', 'endTokenPos', - ], - ]); - $this->parser = new Php7($this->lexer); + $this->parser = (new ParserFactory)->createForHostVersion(); } public function format(BaseFormatter $formatter) { - return $formatter->format($this->parser, $this->lexer); + return $formatter->format($this->parser); } } diff --git a/src/TLint.php b/src/TLint.php index b09d4bd..620f5c8 100644 --- a/src/TLint.php +++ b/src/TLint.php @@ -11,7 +11,7 @@ class TLint public function __construct() { - $this->parser = (new ParserFactory)->create(ParserFactory::PREFER_PHP7); + $this->parser = (new ParserFactory)->createForHostVersion(); } public function lint(BaseLinter $linter)