Updated Rector to commit d09ae7400a75f7694a11c2d8353c2fd14b6419e3

d09ae7400a Add "custom-rule" command to make creating rules easy (#5498)
This commit is contained in:
Tomas Votruba 2024-01-25 00:06:40 +00:00
parent 744ab2e38b
commit dd875cd0c9
14 changed files with 196 additions and 30 deletions

View File

@ -19,12 +19,12 @@ final class VersionResolver
* @api
* @var string
*/
public const PACKAGE_VERSION = '955a5de414501f77b80b321a90ee35d4fe49e9e2';
public const PACKAGE_VERSION = 'd09ae7400a75f7694a11c2d8353c2fd14b6419e3';
/**
* @api
* @var string
*/
public const RELEASE_DATE = '2024-01-24 21:24:18';
public const RELEASE_DATE = '2024-01-25 00:04:31';
/**
* @var int
*/

View File

@ -4,7 +4,6 @@ declare (strict_types=1);
namespace Rector\Config;
use RectorPrefix202401\Illuminate\Container\Container;
use PHPStan\Collectors\Collector;
use Rector\Caching\Contract\ValueObject\Storage\CacheStorageInterface;
use Rector\Configuration\Option;
use Rector\Configuration\Parameter\SimpleParameterProvider;
@ -168,22 +167,6 @@ final class RectorConfig extends Container
// for cache invalidation in case of change
SimpleParameterProvider::addParameter(Option::REGISTERED_RECTOR_RULES, $rectorClass);
}
/**
* @param array<class-string<Collector>> $collectorClasses
*/
public function collectors(array $collectorClasses) : void
{
foreach ($collectorClasses as $collectorClass) {
$this->collector($collectorClass);
}
}
/**
* @param class-string<Collector> $collectorClass
*/
public function collector(string $collectorClass) : void
{
\trigger_error('collector have been deprecated as performance costly and not valuable');
}
/**
* @param class-string<Command> $commandClass
*/

View File

@ -0,0 +1,75 @@
<?php
declare (strict_types=1);
namespace Rector\Console\Command;
use RectorPrefix202401\Nette\Utils\FileSystem;
use Rector\Exception\ShouldNotHappenException;
use Rector\FileSystem\JsonFileSystem;
use RectorPrefix202401\Symfony\Component\Console\Command\Command;
use RectorPrefix202401\Symfony\Component\Console\Input\InputInterface;
use RectorPrefix202401\Symfony\Component\Console\Output\OutputInterface;
use RectorPrefix202401\Symfony\Component\Console\Style\SymfonyStyle;
use RectorPrefix202401\Symfony\Component\Finder\Finder;
final class CustomRuleCommand extends Command
{
/**
* @readonly
* @var \Symfony\Component\Console\Style\SymfonyStyle
*/
private $symfonyStyle;
public function __construct(SymfonyStyle $symfonyStyle)
{
$this->symfonyStyle = $symfonyStyle;
parent::__construct();
}
protected function configure() : void
{
$this->setName('custom-rule');
$this->setDescription('Create base of local custom rule with tests');
}
protected function execute(InputInterface $input, OutputInterface $output) : int
{
// ask for rule name
$rectorName = $this->symfonyStyle->ask('What is the name of the rule class (e.g. "LegacyCallToDbalMethodCall")?', null, static function (string $answer) : string {
if ($answer === '') {
throw new ShouldNotHappenException('Rector name cannot be empty');
}
return $answer;
});
// suffix with Rector by convention
if (\substr_compare((string) $rectorName, 'Rector', -\strlen('Rector')) !== 0) {
$rectorName .= 'Rector';
}
$rectorName = \ucfirst((string) $rectorName);
// find all files in templates directory
$fileInfos = Finder::create()->files()->in(__DIR__ . '/../../../templates/custom-rule')->getIterator();
$generatedFilePaths = [];
foreach ($fileInfos as $fileInfo) {
// replace __Name__ with $rectorName
$newContent = \str_replace('__Name__', $rectorName, $fileInfo->getContents());
$newFilePath = \str_replace('__Name__', $rectorName, $fileInfo->getRelativePathname());
FileSystem::write(\getcwd() . '/' . $newFilePath, $newContent);
$generatedFilePaths[] = $newFilePath;
}
$this->symfonyStyle->title('Generated files');
$this->symfonyStyle->listing($generatedFilePaths);
$this->symfonyStyle->success(\sprintf('Base for the "%s" rule was created. Now you can fill the missing parts', $rectorName));
// 2. update autoload-dev in composer.json
$composerJsonFilePath = \getcwd() . '/composer.json';
if (\file_exists($composerJsonFilePath)) {
$hasChanged = \false;
$composerJson = JsonFileSystem::readFilePath($composerJsonFilePath);
if (!isset($composerJson['autoload-dev']['psr-4']['Utils\\Rector\\'])) {
$composerJson['autoload-dev']['psr-4']['Utils\\Rector\\'] = 'utils/rector/src';
$composerJson['autoload-dev']['psr-4']['Utils\\Rector\\Tests\\'] = 'utils/rector/tests';
$hasChanged = \true;
}
if ($hasChanged) {
$this->symfonyStyle->success('We also update composer.json autoload-dev, to load Rector rules. Now run "composer dump-autoload" to update paths');
JsonFileSystem::writeFile($composerJsonFilePath, $composerJson);
}
}
return Command::SUCCESS;
}
}

View File

@ -48,6 +48,7 @@ use Rector\CodingStyle\Contract\ClassNameImport\ClassNameImportSkipVoterInterfac
use Rector\Config\RectorConfig;
use Rector\Configuration\ConfigInitializer;
use Rector\Configuration\RenamedClassesDataCollector;
use Rector\Console\Command\CustomRuleCommand;
use Rector\Console\Command\ListRulesCommand;
use Rector\Console\Command\ProcessCommand;
use Rector\Console\Command\SetupCICommand;
@ -257,6 +258,7 @@ final class LazyContainerFactory
$rectorConfig->singleton(WorkerCommand::class);
$rectorConfig->singleton(SetupCICommand::class);
$rectorConfig->singleton(ListRulesCommand::class);
$rectorConfig->singleton(CustomRuleCommand::class);
$rectorConfig->when(ListRulesCommand::class)->needs('$rectors')->giveTagged(RectorInterface::class);
// dev
if (\class_exists(MissingInSetCommand::class)) {

View File

@ -15,4 +15,12 @@ final class JsonFileSystem
$fileContents = FileSystem::read($filePath);
return Json::decode($fileContents, Json::FORCE_ARRAY);
}
/**
* @param array<string, mixed> $data
*/
public static function writeFile(string $filePath, array $data) : void
{
$json = Json::encode($data, Json::PRETTY);
FileSystem::write($filePath, $json);
}
}

View File

@ -0,0 +1,45 @@
<?php
declare(strict_types=1);
namespace Utils\Rector\Rector;
use PhpParser\Node;
use Rector\Rector\AbstractRector;
use Symplify\RuleDocGenerator\ValueObject\CodeSample\CodeSample;
use Symplify\RuleDocGenerator\ValueObject\RuleDefinition;
/**
* @see \Utils\Rector\Tests\Rector\__Name__Test
*/
final class __Name__ extends AbstractRector
{
public function getRuleDefinition(): RuleDefinition
{
return new RuleDefinition('// @todo fill the description', [
new CodeSample(
'// @todo fill code before',
'// @todo fill code after'
)
]);
}
/**
* @return array<class-string<Node>>
*/
public function getNodeTypes(): array
{
// @todo select node type
return [\PhpParser\Node\Stmt\Class_::class];
}
/**
* @param \PhpParser\Node\Stmt\Class_ $node
*/
public function refactor(Node $node): ?Node
{
// @todo change the node
return $node;
}
}

View File

@ -0,0 +1,15 @@
<?php
namespace Utils\Rector\Tests\Rector\__Name__Test\Fixture;
// @todo fill code before
?>
-----
<?php
namespace Utils\Rector\Tests\Rector\__Name__Test\Fixture;
// @todo fill code before
?>

View File

@ -0,0 +1,27 @@
<?php
declare(strict_types=1);
namespace Utils\Rector\Tests\Rector;
use PHPUnit\Framework\Attributes\DataProvider;
use Rector\Testing\PHPUnit\AbstractRectorTestCase;
final class __Name__Test extends AbstractRectorTestCase
{
#[DataProvider('provideData')]
public function test(string $filePath): void
{
$this->doTestFile($filePath);
}
public static function provideData(): \Iterator
{
return self::yieldFilesFromDirectory(__DIR__ . '/Fixture');
}
public function provideConfigFilePath(): string
{
return __DIR__ . '/config/configured_rule.php';
}
}

View File

@ -0,0 +1,9 @@
<?php
declare(strict_types=1);
use Rector\Config\RectorConfig;
return static function (RectorConfig $rectorConfig): void {
$rectorConfig->rule(\Utils\Rector\Rector\__Name__::class);
};

2
vendor/autoload.php vendored
View File

@ -22,4 +22,4 @@ if (PHP_VERSION_ID < 50600) {
require_once __DIR__ . '/composer/autoload_real.php';
return ComposerAutoloaderInit0408599c96f445821212bfb9798860ca::getLoader();
return ComposerAutoloaderInitf637847380e2ddf55dcae18dded1d2b3::getLoader();

View File

@ -1176,6 +1176,7 @@ return array(
'Rector\\Configuration\\Option' => $baseDir . '/src/Configuration/Option.php',
'Rector\\Configuration\\Parameter\\SimpleParameterProvider' => $baseDir . '/src/Configuration/Parameter/SimpleParameterProvider.php',
'Rector\\Configuration\\RenamedClassesDataCollector' => $baseDir . '/src/Configuration/RenamedClassesDataCollector.php',
'Rector\\Console\\Command\\CustomRuleCommand' => $baseDir . '/src/Console/Command/CustomRuleCommand.php',
'Rector\\Console\\Command\\ListRulesCommand' => $baseDir . '/src/Console/Command/ListRulesCommand.php',
'Rector\\Console\\Command\\ProcessCommand' => $baseDir . '/src/Console/Command/ProcessCommand.php',
'Rector\\Console\\Command\\SetupCICommand' => $baseDir . '/src/Console/Command/SetupCICommand.php',

View File

@ -2,7 +2,7 @@
// autoload_real.php @generated by Composer
class ComposerAutoloaderInit0408599c96f445821212bfb9798860ca
class ComposerAutoloaderInitf637847380e2ddf55dcae18dded1d2b3
{
private static $loader;
@ -22,17 +22,17 @@ class ComposerAutoloaderInit0408599c96f445821212bfb9798860ca
return self::$loader;
}
spl_autoload_register(array('ComposerAutoloaderInit0408599c96f445821212bfb9798860ca', 'loadClassLoader'), true, true);
spl_autoload_register(array('ComposerAutoloaderInitf637847380e2ddf55dcae18dded1d2b3', 'loadClassLoader'), true, true);
self::$loader = $loader = new \Composer\Autoload\ClassLoader(\dirname(__DIR__));
spl_autoload_unregister(array('ComposerAutoloaderInit0408599c96f445821212bfb9798860ca', 'loadClassLoader'));
spl_autoload_unregister(array('ComposerAutoloaderInitf637847380e2ddf55dcae18dded1d2b3', 'loadClassLoader'));
require __DIR__ . '/autoload_static.php';
call_user_func(\Composer\Autoload\ComposerStaticInit0408599c96f445821212bfb9798860ca::getInitializer($loader));
call_user_func(\Composer\Autoload\ComposerStaticInitf637847380e2ddf55dcae18dded1d2b3::getInitializer($loader));
$loader->setClassMapAuthoritative(true);
$loader->register(true);
$filesToLoad = \Composer\Autoload\ComposerStaticInit0408599c96f445821212bfb9798860ca::$files;
$filesToLoad = \Composer\Autoload\ComposerStaticInitf637847380e2ddf55dcae18dded1d2b3::$files;
$requireFile = \Closure::bind(static function ($fileIdentifier, $file) {
if (empty($GLOBALS['__composer_autoload_files'][$fileIdentifier])) {
$GLOBALS['__composer_autoload_files'][$fileIdentifier] = true;

View File

@ -4,7 +4,7 @@
namespace Composer\Autoload;
class ComposerStaticInit0408599c96f445821212bfb9798860ca
class ComposerStaticInitf637847380e2ddf55dcae18dded1d2b3
{
public static $files = array (
'ad155f8f1cf0d418fe49e248db8c661b' => __DIR__ . '/..' . '/react/promise/src/functions_include.php',
@ -1390,6 +1390,7 @@ class ComposerStaticInit0408599c96f445821212bfb9798860ca
'Rector\\Configuration\\Option' => __DIR__ . '/../..' . '/src/Configuration/Option.php',
'Rector\\Configuration\\Parameter\\SimpleParameterProvider' => __DIR__ . '/../..' . '/src/Configuration/Parameter/SimpleParameterProvider.php',
'Rector\\Configuration\\RenamedClassesDataCollector' => __DIR__ . '/../..' . '/src/Configuration/RenamedClassesDataCollector.php',
'Rector\\Console\\Command\\CustomRuleCommand' => __DIR__ . '/../..' . '/src/Console/Command/CustomRuleCommand.php',
'Rector\\Console\\Command\\ListRulesCommand' => __DIR__ . '/../..' . '/src/Console/Command/ListRulesCommand.php',
'Rector\\Console\\Command\\ProcessCommand' => __DIR__ . '/../..' . '/src/Console/Command/ProcessCommand.php',
'Rector\\Console\\Command\\SetupCICommand' => __DIR__ . '/../..' . '/src/Console/Command/SetupCICommand.php',
@ -2649,9 +2650,9 @@ class ComposerStaticInit0408599c96f445821212bfb9798860ca
public static function getInitializer(ClassLoader $loader)
{
return \Closure::bind(function () use ($loader) {
$loader->prefixLengthsPsr4 = ComposerStaticInit0408599c96f445821212bfb9798860ca::$prefixLengthsPsr4;
$loader->prefixDirsPsr4 = ComposerStaticInit0408599c96f445821212bfb9798860ca::$prefixDirsPsr4;
$loader->classMap = ComposerStaticInit0408599c96f445821212bfb9798860ca::$classMap;
$loader->prefixLengthsPsr4 = ComposerStaticInitf637847380e2ddf55dcae18dded1d2b3::$prefixLengthsPsr4;
$loader->prefixDirsPsr4 = ComposerStaticInitf637847380e2ddf55dcae18dded1d2b3::$prefixDirsPsr4;
$loader->classMap = ComposerStaticInitf637847380e2ddf55dcae18dded1d2b3::$classMap;
}, null, ClassLoader::class);
}

View File

@ -30,7 +30,7 @@ if (!function_exists('humbug_phpscoper_expose_class')) {
}
}
humbug_phpscoper_expose_class('AutoloadIncluder', 'RectorPrefix202401\AutoloadIncluder');
humbug_phpscoper_expose_class('ComposerAutoloaderInit0408599c96f445821212bfb9798860ca', 'RectorPrefix202401\ComposerAutoloaderInit0408599c96f445821212bfb9798860ca');
humbug_phpscoper_expose_class('ComposerAutoloaderInitf637847380e2ddf55dcae18dded1d2b3', 'RectorPrefix202401\ComposerAutoloaderInitf637847380e2ddf55dcae18dded1d2b3');
humbug_phpscoper_expose_class('Product', 'RectorPrefix202401\Product');
// Function aliases. For more information see: