Find the best Rector rule to solve your problem


Configurable

ChangeMethodVisibilityRector

Change visibility of method from parent class.

 class FrameworkClass
 {
     protected function someMethod()
     {
     }
 }

 class MyClass extends FrameworkClass
 {
-    public function someMethod()
+    protected function someMethod()
     {
     }
 }
SETS:  symfony/* 4.2

Configurable

StaticCallToNewRector

Change static call to new instance

 class SomeClass
 {
     public function run()
     {
-        $dotenv = JsonResponse::create(['foo' => 'bar'], Response::HTTP_OK);
+        $dotenv = new JsonResponse(['foo' => 'bar'], Response::HTTP_OK);
     }
 }
SETS:  symfony/* 5.1

Configurable

NewToStaticCallRector

Change new Object to static call

 class SomeClass
 {
     public function run()
     {
-        new Cookie($name);
+        Cookie::create($name);
     }
 }
SETS:  symfony/* 4.2

Configurable

WrapReturnRector

Wrap return value of specific method

 final class SomeClass
 {
     public function getItem()
     {
-        return 1;
+        return [1];
     }
 }
SETS:  symfony/* 4.2

Configurable

ArgumentAdderRector

This Rector adds new default arguments in calls of defined methods and class types.

 $someObject = new SomeExampleClass;
-$someObject->someMethod();
+$someObject->someMethod(true);

 class MyCustomClass extends SomeExampleClass
 {
-    public function someMethod()
+    public function someMethod($value = true)
     {
     }
 }

Configurable

ReplaceArgumentDefaultValueRector

Replaces defined map of arguments in defined methods and their calls.

 $someObject = new SomeClass;
-$someObject->someMethod(SomeClass::OLD_CONSTANT);
+$someObject->someMethod(false);


Configurable

RenameFunctionRector

Turns defined function call new one.

-view("...", []);
+Laravel\Templating\render("...", []);

Configurable

RenameClassConstFetchRector

Replaces defined class constants in their calls.

-$value = SomeClass::OLD_CONSTANT;
-$value = SomeClass::OTHER_OLD_CONSTANT;
+$value = SomeClass::NEW_CONSTANT;
+$value = DifferentClass::NEW_CONSTANT;

Configurable

RenamePropertyRector

Replaces defined old properties by new ones.

-$someObject->someOldProperty;
+$someObject->someNewProperty;
SETS:  symfony/* 5.2

Configurable

RenameStringRector

Change string value

 class SomeClass
 {
     public function run()
     {
-        return 'ROLE_PREVIOUS_ADMIN';
+        return 'IS_IMPERSONATOR';
     }
 }
SETS:  symfony/* 5.1

Configurable

RenameClassRector

Replaces defined classes by new ones.

 namespace App;

-use SomeOldClass;
+use SomeNewClass;

-function someFunction(SomeOldClass $someOldClass): SomeOldClass
+function someFunction(SomeNewClass $someOldClass): SomeNewClass
 {
-    if ($someOldClass instanceof SomeOldClass) {
-        return new SomeOldClass;
+    if ($someOldClass instanceof SomeNewClass) {
+        return new SomeNewClass;
     }
 }

Configurable

RenameAttributeRector

Rename attribute class names

-#[SimpleRoute()]
+#[BasicRoute()]
 class SomeClass
 {
 }

Configurable

AnnotationToAttributeRector

Change annotation to attribute

 use Symfony\Component\Routing\Annotation\Route;

 class SymfonyRoute
 {
-    /**
-     * @Route("/path", name="action") api route
-     */
+    #[Route(path: '/path', name: 'action')] // api route
     public function action()
     {
     }
 }

Configurable

ArgumentRemoverRector

Removes defined arguments in defined methods and their calls.

 $someObject = new SomeClass;
-$someObject->someMethod(true);
+$someObject->someMethod();

Configurable

AddParamTypeDeclarationRector

Add param types where needed

 class SomeClass
 {
-    public function process($name)
+    public function process(string $name)
     {
     }
 }

Configurable

AddReturnTypeDeclarationRector

Changes defined return typehint of method and class.

 class SomeClass
 {
-    public function getData()
+    public function getData(): array
     {
     }
 }

GetToConstructorInjectionRector

Turns fetching of dependencies via $this->get() to constructor injection in Command and Controller

 use Symfony\Bundle\FrameworkBundle\Controller\Controller;

 final class SomeController extend Controller
 {
+    public function __construct(SomeService $someService)
+    {
+        $this->someService = $someService;
+    }
+
     public function someMethod()
     {
-        // ...
-        $this->get('some_service');
+        $this->someService;
     }
 }

ConsoleExceptionToErrorEventConstantRector

Turns old event name with EXCEPTION to ERROR constant in Console in Symfony

-"console.exception"
+Symfony\Component\Console\ConsoleEvents::ERROR
SETS:  symfony/* 3.3

DefinitionAliasSetPrivateToSetPublicRector

Migrates from deprecated Definition/Alias->setPrivate() to Definition/Alias->setPublic()

 use Symfony\Component\DependencyInjection\Alias;
 use Symfony\Component\DependencyInjection\Definition;

 class SomeClass
 {
     public function run()
     {
         $definition = new Definition('Example\Foo');
-        $definition->setPrivate(false);
+        $definition->setPublic(true);

         $alias = new Alias('Example\Foo');
-        $alias->setPrivate(false);
+        $alias->setPublic(true);
     }
 }
SETS:  symfony/* 5.2

ReflectionExtractorEnableMagicCallExtractorRector

Migrates from deprecated enable_magic_call_extraction context option in ReflectionExtractor

 use Symfony\Component\PropertyInfo\Extractor\ReflectionExtractor;

 class SomeClass
 {
     public function run()
     {
         $reflectionExtractor = new ReflectionExtractor();
         $readInfo = $reflectionExtractor->getReadInfo(Dummy::class, 'bar', [
-            'enable_magic_call_extraction' => true,
+            'enable_magic_methods_extraction' => ReflectionExtractor::MAGIC_CALL | ReflectionExtractor::MAGIC_GET | ReflectionExtractor::MAGIC_SET,
         ]);
     }
 }
SETS:  symfony/* 5.2

ValidatorBuilderEnableAnnotationMappingRector

Migrates from deprecated ValidatorBuilder->enableAnnotationMapping($reader) to ValidatorBuilder->enableAnnotationMapping(true)->setDoctrineAnnotationReader($reader)

 use Doctrine\Common\Annotations\Reader;
 use Symfony\Component\Validator\ValidatorBuilder;

 class SomeClass
 {
     public function run(ValidatorBuilder $builder, Reader $reader)
     {
-        $builder->enableAnnotationMapping($reader);
+        $builder->enableAnnotationMapping(true)->setDoctrineAnnotationReader($reader);
     }
 }
SETS:  symfony/* 5.2

FormBuilderSetDataMapperRector

Migrates from deprecated Form Builder->setDataMapper(new PropertyPathMapper()) to Builder->setDataMapper(new DataMapper(new PropertyPathAccessor()))

 use Symfony\Component\Form\Extension\Core\DataMapper\PropertyPathMapper;
 use Symfony\Component\Form\FormConfigBuilderInterface;
+use Symfony\Component\Form\Extension\Core\DataMapper\DataMapper;
+use Symfony\Component\Form\Extension\Core\DataAccessor\PropertyPathAccessor;

 class SomeClass
 {
     public function run(FormConfigBuilderInterface $builder)
     {
-        $builder->setDataMapper(new PropertyPathMapper());
+        $builder->setDataMapper(new DataMapper(new PropertyPathAccessor()));
     }
 }
SETS:  symfony/* 5.2

BinaryFileResponseCreateToNewInstanceRector

Change deprecated BinaryFileResponse::create() to use __construct() instead

 use Symfony\Component\HttpFoundation;

 class SomeClass
 {
     public function run()
     {
-        $binaryFile = BinaryFileResponse::create();
+        $binaryFile = new BinaryFileResponse(null);
     }
 }
SETS:  symfony/* 5.2

PropertyAccessorCreationBooleanToFlagsRector

Changes first argument of PropertyAccessor::__construct() to flags from boolean

 class SomeClass
 {
     public function run()
     {
-        $propertyAccessor = new PropertyAccessor(true);
+        $propertyAccessor = new PropertyAccessor(PropertyAccessor::MAGIC_CALL | PropertyAccessor::MAGIC_GET | PropertyAccessor::MAGIC_SET);
     }
 }
SETS:  symfony/* 5.2

PropertyPathMapperToDataMapperRector

Migrate from PropertyPathMapper to DataMapper and PropertyPathAccessor

 use Symfony\Component\Form\Extension\Core\DataMapper\PropertyPathMapper;

 class SomeClass
 {
     public function run()
     {
-        return new PropertyPathMapper();
+        return new \Symfony\Component\Form\Extension\Core\DataMapper\DataMapper(new \Symfony\Component\Form\Extension\Core\DataAccessor\PropertyPathAccessor());
     }
 }
SETS:  symfony/* 5.2

SimplifyFormRenderingRector

Symplify form rendering by not calling ->createView() on render function

 use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;

 class ReplaceFormCreateViewFunctionCall extends AbstractController
 {
     public function form(): Response
     {
         return $this->render('form.html.twig', [
-            'form' => $form->createView(),
+            'form' => $form,
         ]);
     }
 }
SETS:  symfony/* 6.2

SecurityAttributeToIsGrantedAttributeRector

Replaces #[Security] framework-bundle attribute with Symfony native #[IsGranted] one

-use Sensio\Bundle\FrameworkExtraBundle\Configuration\Security;
+use Symfony\Component\ExpressionLanguage\Expression;
+use Symfony\Component\Security\Http\Attribute\IsGranted;

 class PostController extends Controller
 {
-    #[Security("is_granted('ROLE_ADMIN')")]
+    #[IsGranted('ROLE_ADMIN')]
     public function index()
     {
     }

-    #[Security("is_granted('ROLE_ADMIN') and is_granted('ROLE_FRIENDLY_USER')")]
+    #[IsGranted(new Expression("is_granted('ROLE_ADMIN') and is_granted('ROLE_FRIENDLY_USER')"))]
     public function list()
     {
     }
 }
SETS:  symfony/* 6.2

MessageHandlerInterfaceToAttributeRector

Replaces MessageHandlerInterface with AsMessageHandler attribute

-use Symfony\Component\Messenger\Handler\MessageHandlerInterface;
+use Symfony\Component\Messenger\Attribute\AsMessageHandler;

-class SmsNotificationHandler implements MessageHandlerInterface
+#[AsMessageHandler]
+class SmsNotificationHandler
 {
     public function __invoke(SmsNotification $message)
     {
         // ... do some work - like sending an SMS message!
     }
 }
SETS:  symfony/* 6.2

MessageSubscriberInterfaceToAttributeRector

Replace MessageSubscriberInterface with AsMessageHandler attribute(s)

-use Symfony\Component\Messenger\Handler\MessageSubscriberInterface;
+use Symfony\Component\Messenger\Attribute\AsMessageHandler;

-class SmsNotificationHandler implements MessageSubscriberInterface
+class SmsNotificationHandler
 {
-    public function __invoke(SmsNotification $message)
+    #[AsMessageHandler]
+    public function handleSmsNotification(SmsNotification $message)
     {
         // ...
     }

+    #[AsMessageHandler(priority: 0, bus: 'messenger.bus.default']
     public function handleOtherSmsNotification(OtherSmsNotification $message)
     {
         // ...
-    }
-
-    public static function getHandledMessages(): iterable
-    {
-        // handle this message on __invoke
-        yield SmsNotification::class;
-
-        // also handle this message on handleOtherSmsNotification
-        yield OtherSmsNotification::class => [
-            'method' => 'handleOtherSmsNotification',
-            'priority' => 0,
-            'bus' => 'messenger.bus.default',
-        ];
     }
 }
SETS:  symfony/* 6.2

ParamConverterAttributeToMapEntityAttributeRector

Replace ParamConverter attribute with mappings with the MapEntity attribute

+use Symfony\Bridge\Doctrine\Attribute\MapEntity;
+
 class SomeController
 {
-    #[ParamConverter('post', options: ['mapping' => ['date' => 'date', 'slug' => 'slug']])]
-    #[ParamConverter('comment', options: ['mapping' => ['comment_slug' => 'slug']])]
     public function showComment(
+        #[MapEntity(mapping: ['date' => 'date', 'slug' => 'slug'])]
         Post $post,

+        #[MapEntity(mapping: ['comment_slug' => 'slug'])]
         Comment $comment
     ) {
     }
 }
SETS:  symfony/* 6.2

ArgumentValueResolverToValueResolverRector

Replaces ArgumentValueResolverInterface by ValueResolverInterface

-use Symfony\Component\HttpKernel\Controller\ArgumentValueResolverInterface;
+use Symfony\Component\HttpKernel\Controller\ValueResolverInterface;

-final class EntityValueResolver implements ArgumentValueResolverInterface
+final class EntityValueResolver implements ValueResolverInterface
 {
-    public function supports(Request $request, ArgumentMetadata $argument): bool
-    {
-    }
-
     public function resolve(Request $request, ArgumentMetadata $argument): iterable
     {
     }
 }
SETS:  symfony/* 6.2

ErrorNamesPropertyToConstantRector

Turns old Constraint::$errorNames properties to use Constraint::ERROR_NAMES instead

 use Symfony\Component\Validator\Constraints\NotBlank;

 class SomeClass
 {
-    NotBlank::$errorNames
+    NotBlank::ERROR_NAMES

 }
SETS:  symfony/* 6.1

CommandConfigureToAttributeRector

Add Symfony\Component\Console\Attribute\AsCommand to Symfony Commands from configure()

+use Symfony\Component\Console\Attribute\AsCommand;
 use Symfony\Component\Console\Command\Command;

+#[AsCommand(name: 'sunshine', description: 'Some description')]
 final class SunshineCommand extends Command
 {
-    public function configure()
-    {
-        $this->setName('sunshine');
-        $this->setDescription('Some description');
-
-    }
 }
SETS:  symfony/* 6.1

MagicClosureTwigExtensionToNativeMethodsRector

Change TwigExtension function/filter magic closures to inlined and clear callables

 use Twig\Extension\AbstractExtension;
 use Twig\TwigFunction;

 final class TerminologyExtension extends AbstractExtension
 {
     public function getFunctions(): array
     {
         return [
-            new TwigFunction('resolve', [$this, 'resolve']);
+            new TwigFunction('resolve', $this->resolve(...)),
         ];
     }

     private function resolve($value)
     {
         return $value + 100;
     }
 }
SETS:  symfony/* 6.1

CommandPropertyToAttributeRector

Add Symfony\Component\Console\Attribute\AsCommand to Symfony Commands and remove the deprecated properties

+use Symfony\Component\Console\Attribute\AsCommand;
 use Symfony\Component\Console\Command\Command;

+#[AsCommand(name: 'sunshine', description: 'some description')]
 final class SunshineCommand extends Command
 {
-    public static $defaultName = 'sunshine';
-
-    public static $defaultDescription = 'some description';
 }
SETS:  symfony/* 6.1

AuthorizationCheckerIsGrantedExtractorRector

Change $this->authorizationChecker->isGranted([$a, $b]) to $this->authorizationChecker->isGranted($a) || $this->authorizationChecker->isGranted($b), also updates AbstractController usages

-if ($this->authorizationChecker->isGranted(['ROLE_USER', 'ROLE_ADMIN'])) {
+if ($this->authorizationChecker->isGranted('ROLE_USER') || $this->authorizationChecker->isGranted('ROLE_ADMIN')) {
 }
SETS:  symfony/* 4.4

ConsoleExecuteReturnIntRector

Returns int from Command::execute() command

 use Symfony\Component\Console\Command\Command;

 class SomeCommand extends Command
 {
-    public function execute(InputInterface $input, OutputInterface $output)
+    public function execute(InputInterface $input, OutputInterface $output): int
     {
-        return null;
+        return 0;
     }
 }
SETS:  symfony/* 4.4

OptionNameRector

Turns old option names to new ones in FormTypes in Form in Symfony

 $builder = new FormBuilder;
-$builder->add("...", ["precision" => "...", "virtual" => "..."];
+$builder->add("...", ["scale" => "...", "inherit_data" => "..."];
SETS:  symfony/* 3.0

StringFormTypeToClassRector

Turns string Form Type references to their CONSTANT alternatives in FormTypes in Form in Symfony. To enable custom types, add link to your container XML dump in "$rectorConfig->symfonyContainerXml(...)"

 $formBuilder = new Symfony\Component\Form\FormBuilder;
-$formBuilder->add('name', 'form.type.text');
+$formBuilder->add('name', \Symfony\Component\Form\Extension\Core\Type\TextType::class);
SETS:  symfony/* 3.0

ChangeStringCollectionOptionToConstantRector

Change type in CollectionType from alias string to class reference

 use Symfony\Component\Form\AbstractType;
 use Symfony\Component\Form\FormBuilderInterface;
 use Symfony\Component\Form\Extension\Core\Type\CollectionType;

 class TaskType extends AbstractType
 {
     public function buildForm(FormBuilderInterface $builder, array $options)
     {
         $builder->add('tags', CollectionType::class, [
-            'type' => 'choice',
+            'type' => \Symfony\Component\Form\Extension\Core\Type\ChoiceType::class,
         ]);

         $builder->add('tags', 'collection', [
-            'type' => 'choice',
+            'type' => \Symfony\Component\Form\Extension\Core\Type\ChoiceType::class,
         ]);
     }
 }
SETS:  symfony/* 3.0

FormTypeInstanceToClassConstRector

Changes createForm(new FormType), add(new FormType) to ones with "FormType::class"

 use Symfony\Bundle\FrameworkBundle\Controller\Controller;

 final class SomeController extends Controller
 {
     public function action()
     {
-        $form = $this->createForm(new TeamType);
+        $form = $this->createForm(TeamType::class);
     }
 }
SETS:  symfony/* 3.0

ReadOnlyOptionToAttributeRector

Change "read_only" option in form to attribute

 use Symfony\Component\Form\FormBuilderInterface;

 function buildForm(FormBuilderInterface $builder, array $options)
 {
-    $builder->add('cuid', TextType::class, ['read_only' => true]);
+    $builder->add('cuid', TextType::class, ['attr' => ['read_only' => true]]);
 }
SETS:  symfony/* 3.0

RemoveDefaultGetBlockPrefixRector

Rename getBlockPrefix() if it returns the default value - class to underscore, e.g. UserFormType = user_form

 use Symfony\Component\Form\AbstractType;

 class TaskType extends AbstractType
 {
-    public function getBlockPrefix()
-    {
-        return 'task';
-    }
 }
SETS:  symfony/* 3.0

FormTypeGetParentRector

Turns string Form Type references to their CONSTANT alternatives in getParent() and getExtendedType() methods in Form in Symfony

 use Symfony\Component\Form\AbstractType;

 class SomeType extends AbstractType
 {
     public function getParent()
     {
-        return 'collection';
+        return \Symfony\Component\Form\Extension\Core\Type\CollectionType::class;
     }
 }
SETS:  symfony/* 3.0

GetRequestRector

Turns fetching of Request via $this->getRequest() to action injection

+use Symfony\Component\HttpFoundation\Request;
+
 class SomeController
 {
-    public function someAction()
+    public function someAction(Request $request)
     {
-        $this->getRequest()->...();
+        $request->...();
     }
 }
SETS:  symfony/* 3.0

ParamAndEnvAttributeRector

Make param/env use in #[Attribute] more precise

 namespace App\Service;

 use Symfony\Component\DependencyInjection\Attribute\Autowire;

 class MessageGenerator
 {
     public function __construct(
-        #[Autowire('%kernel.debug%')]
+        #[Autowire(param: 'kernel.debug')]
         bool $debugMode,

-        #[Autowire('%env(SOME_ENV_VAR)%')]
+        #[Autowire(env: 'SOME_ENV_VAR')]
         string $senderName,
     ) {
     }
 }
SETS:  symfony/* 6.3

SignalableCommandInterfaceReturnTypeRector

Return int or false from SignalableCommandInterface::handleSignal() instead of void

-public function handleSignal(int $signal): void
+public function handleSignal(int $signal): int|false
     {
+        return false;
     }
SETS:  symfony/* 6.3

ServiceArgsToServiceNamedArgRector

Converts order-dependent arguments args() to named arg() call

 use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator;

 return static function (ContainerConfigurator $containerConfigurator): void {
     $services = $containerConfigurator->services();

     $services->set(SomeClass::class)
-        ->args(['some_value']);
+        ->arg('$someCtorParameter', 'some_value');
 };
SETS:  Configs

MergeServiceNameTypeRector

Merge name === type service registration, $services->set(SomeType::class, SomeType::class)

 use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator;

 return static function (ContainerConfigurator $containerConfigurator): void {
     $services = $containerConfigurator->services();
-    $services->set(\App\SomeClass::class, \App\SomeClass::class);
+    $services->set(\App\SomeClass::class);
 };
SETS:  Configs

ServiceTagsToDefaultsAutoconfigureRector

Change $services->set(..., ...)->tag(...) to $services->defaults()->autodiscovery() where meaningful

 use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator;
 use App\Command\SomeCommand;

 return static function (ContainerConfigurator $containerConfigurator): void {
     $services = $containerConfigurator->services();
+    $services->defaults()
+        ->autoconfigure();

-    $services->set(SomeCommand::class)
-        ->tag('console.command');
+    $services->set(SomeCommand::class);
 };
SETS:  Configs

ServiceSetStringNameToClassNameRector

Change $service->set() string names to class-type-based names, to allow $container->get() by types in Symfony 2.8. Provide XML config via $rectorConfig->symfonyContainerXml(...);

 use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator;

 return static function (ContainerConfigurator $containerConfigurator): void {
     $services = $containerConfigurator->services();

-    $services->set('some_name', App\SomeClass::class);
+    $services->set('app\\someclass', App\SomeClass::class);
 };
SETS:  Configs

ServiceSettersToSettersAutodiscoveryRector

Change $services->set(..., ...) to $services->load(..., ...) where meaningful

 use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator;

-use App\Services\FistService;
-use App\Services\SecondService;
-
 return static function (ContainerConfigurator $containerConfigurator): void {
     $parameters = $containerConfigurator->parameters();

     $services = $containerConfigurator->services();

-    $services->set(FistService::class);
-    $services->set(SecondService::class);
+    $services->load('App\\Services\\', '../src/Services/*');
 };
SETS:  Configs

GetHelperControllerToServiceRector

Replace $this->getDoctrine() and $this->dispatchMessage() calls in AbstractController with direct service use

 use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
+use Doctrine\Persistence\ManagerRegistry;

 final class SomeController extends AbstractController
 {
+    public function __construct(
+        private ManagerRegistry $managerRegistry
+    ) {
+    }
+
     public function run()
     {
-        $productRepository = $this->getDoctrine()->getRepository(Product::class);
+        $productRepository = $this->managerRegistry->getRepository(Product::class);
     }
 }
SETS:  symfony/* 6.0

Configurable

ReplaceServiceArgumentRector

Replace defined service() argument in Symfony PHP config

 use function Symfony\Component\DependencyInjection\Loader\Configurator\service;

-return service(ContainerInterface::class);
+return service('service_container');
SETS:  symfony/* 6.0

LogoutHandlerToLogoutEventSubscriberRector

Change logout handler to an event listener that listens to LogoutEvent

-use Symfony\Component\Security\Http\Logout\LogoutHandlerInterface;
-use Symfony\Component\HttpFoundation\Request;
-use Symfony\Component\HttpFoundation\Response;
-use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
+use Symfony\Component\EventDispatcher\EventSubscriberInterface;
+use Symfony\Component\Security\Http\Event\LogoutEvent;

-final class SomeLogoutHandler implements LogoutHandlerInterface
+final class SomeLogoutHandler implements EventSubscriberInterface
 {
-    public function logout(Request $request, Response $response, TokenInterface $token)
+    public function onLogout(LogoutEvent $logoutEvent): void
     {
+        $request = $logoutEvent->getRequest();
+        $response = $logoutEvent->getResponse();
+        $token = $logoutEvent->getToken();
+    }
+
+    /**
+     * @return array<string, string[]>
+     */
+    public static function getSubscribedEvents(): array
+    {
+        return [
+            LogoutEvent::class => ['onLogout'],
+        ];
     }
 }
SETS:  symfony/* 5.1

LogoutSuccessHandlerToLogoutEventSubscriberRector

Change logout success handler to an event listener that listens to LogoutEvent

-use Symfony\Component\Security\Http\Logout\LogoutSuccessHandlerInterface;
-use Symfony\Component\HttpFoundation\Request;
-use Symfony\Component\HttpFoundation\Response;
-use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
+use Symfony\Component\EventDispatcher\EventSubscriberInterface;
+use Symfony\Component\Security\Http\Event\LogoutEvent;

-final class SomeLogoutHandler implements LogoutSuccessHandlerInterface
+final class SomeLogoutHandler implements EventSubscriberInterface
 {
     /**
       * @var HttpUtils
       */
     private $httpUtils;

-    public function __construct(HttpUtils $httpUtils)
+    public function onLogout(LogoutEvent $logoutEvent): void
     {
-        $this->httpUtils = $httpUtils;
+        if ($logoutEvent->getResponse() !== null) {
+            return;
+        }
+
+        $response = $this->httpUtils->createRedirectResponse($logoutEvent->getRequest(), 'some_url');
+        $logoutEvent->setResponse($response);
     }

-    public function onLogoutSuccess(Request $request)
+    /**
+     * @return array<string, mixed>
+     */
+    public static function getSubscribedEvents(): array
     {
-        $response = $this->httpUtils->createRedirectResponse($request, 'some_url');
-        return $response;
+        return [
+            LogoutEvent::class => [['onLogout', 64]],
+        ];
     }
 }
SETS:  symfony/* 5.1

RouteCollectionBuilderToRoutingConfiguratorRector

Change RouteCollectionBuilder to RoutingConfiguratorRector

 use Symfony\Bundle\FrameworkBundle\Kernel\MicroKernelTrait;
 use Symfony\Component\HttpKernel\Kernel;
-use Symfony\Component\Routing\RouteCollectionBuilder;
+use Symfony\Component\Routing\Loader\Configurator\RoutingConfigurator;

 final class ConcreteMicroKernel extends Kernel
 {
     use MicroKernelTrait;

-    protected function configureRoutes(RouteCollectionBuilder $routes)
+    protected function configureRouting(RoutingConfigurator $routes): void
     {
-        $routes->add('/admin', 'App\Controller\AdminController::dashboard', 'admin_dashboard');
-    }
-}
+        $routes->add('admin_dashboard', '/admin')
+            ->controller('App\Controller\AdminController::dashboard')
+    }}
SETS:  symfony/* 5.1

CommandConstantReturnCodeRector

Changes int return from execute to use Symfony Command constants.

 class SomeCommand extends Command
 {
     protected function execute(InputInterface $input, OutputInterface $output): int
     {
-        return 0;
+        return \Symfony\Component\Console\Command\Command::SUCCESS;
     }

 }
SETS:  symfony/* 5.1

ContainerGetToConstructorInjectionRector

Turns fetching of dependencies via $container->get() in ContainerAware to constructor injection in Command and Controller in Symfony

 final class SomeCommand extends ContainerAwareCommand
 {
+    public function __construct(SomeService $someService)
+    {
+        $this->someService = $someService;
+    }
+
     public function someMethod()
     {
         // ...
-        $this->getContainer()->get('some_service');
-        $this->container->get('some_service');
+        $this->someService;
+        $this->someService;
     }
 }

RootNodeTreeBuilderRector

Changes TreeBuilder with root() call to constructor passed root and getRootNode() call

 use Symfony\Component\Config\Definition\Builder\TreeBuilder;

-$treeBuilder = new TreeBuilder();
-$rootNode = $treeBuilder->root('acme_root');
+$treeBuilder = new TreeBuilder('acme_root');
+$rootNode = $treeBuilder->getRootNode();
 $rootNode->someCall();
SETS:  symfony/* 4.2

StringToArrayArgumentProcessRector

Changes Process string argument to an array

 use Symfony\Component\Process\Process;
-$process = new Process('ls -l');
+$process = new Process(['ls', '-l']);
SETS:  symfony/* 4.2

MakeDispatchFirstArgumentEventRector

Make event object a first argument of dispatch() method, event name as second

 use Symfony\Contracts\EventDispatcher\EventDispatcherInterface;

 class SomeClass
 {
     public function run(EventDispatcherInterface $eventDispatcher)
     {
-        $eventDispatcher->dispatch('event_name', new Event());
+        $eventDispatcher->dispatch(new Event(), 'event_name');
     }
 }
SETS:  symfony/* 4.3

WebTestCaseAssertIsSuccessfulRector

Simplify use of assertions in WebTestCase

 use PHPUnit\Framework\TestCase;

 class SomeClass extends TestCase
 {
     public function test()
     {
-        $this->assertSame(200, $this->client->getResponse()->getStatusCode());
+        $this->assertResponseIsSuccessful();
     }
 }
SETS:  symfony/* 4.3

WebTestCaseAssertResponseCodeRector

Simplify use of assertions in WebTestCase

 use Symfony\Bundle\FrameworkBundle\Test\WebTestCase;

 final class SomeClass extends WebTestCase
 {
     public function test()
     {
-        $response = self::getClient()->getResponse();
-
-        $this->assertSame(301, $response->getStatusCode());
-        $this->assertSame('https://example.com', $response->headers->get('Location'));
+        $this->assertResponseStatusCodeSame(301);
+        $this->assertResponseRedirects('https://example.com');
     }
 }
SETS:  symfony/* 4.3

ConvertRenderTemplateShortNotationToBundleSyntaxRector

Change Twig template short name to bundle syntax in render calls from controllers

 class BaseController extends Controller {
     function indexAction()
     {
-        $this->render('appBundle:Landing\Main:index.html.twig');
+        $this->render('@app/Landing/Main/index.html.twig');
     }
 }
SETS:  symfony/* 4.3

GetCurrencyBundleMethodCallsToIntlRector

Intl static bundle method were changed to direct static calls

-$currencyBundle = \Symfony\Component\Intl\Intl::getCurrencyBundle();
-
-$currencyNames = $currencyBundle->getCurrencyNames();
+$currencyNames = \Symfony\Component\Intl\Currencies::getNames();
SETS:  symfony/* 4.3

TwigBundleFilesystemLoaderToTwigRector

Change TwigBundle FilesystemLoader to native one

-use Symfony\Bundle\TwigBundle\Loader\FilesystemLoader;
-use Symfony\Bundle\FrameworkBundle\Templating\Loader\TemplateLocator;
-use Symfony\Bundle\FrameworkBundle\Templating\TemplateNameParser;
+use Twig\Loader\FilesystemLoader;

-$filesystemLoader = new FilesystemLoader(new TemplateLocator(), new TemplateParser());
-$filesystemLoader->addPath(__DIR__ . '/some-directory');
+$fileSystemLoader = new FilesystemLoader([__DIR__ . '/some-directory']);
SETS:  symfony/* 4.3

EventDispatcherParentConstructRector

Removes parent construct method call in EventDispatcher class

 use Symfony\Component\EventDispatcher\EventDispatcher;

 final class SomeEventDispatcher extends EventDispatcher
 {
     public function __construct()
     {
         $value = 1000;
+        parent::__construct();
     }
 }
SETS:  symfony/* 4.3

KernelTestCaseContainerPropertyDeprecationRector

Simplify use of assertions in WebTestCase

 use Symfony\Bundle\FrameworkBundle\Test\KernelTestCase;

 class SomeTest extends KernelTestCase
 {
     protected function setUp(): void
     {
-        $container = self::$container;
+        $container = self::getContainer();
     }
 }
SETS:  symfony/* 5.3

VarDumperTestTraitMethodArgsRector

Adds a new $filter argument in VarDumperTestTrait->assertDumpEquals() and VarDumperTestTrait->assertDumpMatchesFormat() in Validator in Symfony.

-$varDumperTestTrait->assertDumpEquals($dump, $data, $message = "");
+$varDumperTestTrait->assertDumpEquals($dump, $data, $filter = 0, $message = "");
SETS:  symfony/* 4.0

FormIsValidRector

Adds $form->isSubmitted() validation to all $form->isValid() calls in Form in Symfony

-if ($form->isValid()) {
+if ($form->isSubmitted() && $form->isValid()) {
 }
SETS:  symfony/* 4.0

ContainerBuilderCompileEnvArgumentRector

Turns old default value to parameter in ContainerBuilder->build() method in DI in Symfony

 use Symfony\Component\DependencyInjection\ContainerBuilder;

 $containerBuilder = new ContainerBuilder();
-$containerBuilder->compile();
+$containerBuilder->compile(true);
SETS:  symfony/* 4.0

ConstraintUrlOptionRector

Turns true value to Url::CHECK_DNS_TYPE_ANY in Validator in Symfony.

-$constraint = new Url(["checkDNS" => true]);
+$constraint = new Url(["checkDNS" => Url::CHECK_DNS_TYPE_ANY]);
SETS:  symfony/* 4.0

ChangeCollectionTypeOptionNameFromTypeToEntryTypeRector

Rename type option to entry_type in CollectionType

 use Symfony\Component\Form\AbstractType;
 use Symfony\Component\Form\FormBuilderInterface;
 use Symfony\Component\Form\Extension\Core\Type\CollectionType;
 use Symfony\Component\Form\Extension\Core\Type\ChoiceType;

 class TaskType extends AbstractType
 {
     public function buildForm(FormBuilderInterface $builder, array $options)
     {
         $builder->add('tags', CollectionType::class, [
-            'type' => ChoiceType::class,
-            'options' => [1, 2, 3],
+            'entry_type' => ChoiceType::class,
+            'entry_options' => [1, 2, 3],
         ]);
     }
 }
SETS:  symfony/* 2.7

AddViolationToBuildViolationRector

Change $context->addViolationAt to $context->buildViolation on Validator ExecutionContext

-$context->addViolationAt('property', 'The value {{ value }} is invalid.', array(
-    '{{ value }}' => $invalidValue,
-));
+$context->buildViolation('The value {{ value }} is invalid.')
+    ->atPath('property')
+    ->setParameter('{{ value }}', $invalidValue)
+    ->addViolation();
SETS:  symfony/* 2.5

MaxLengthSymfonyFormOptionToAttrRector

Change form option "max_length" to a form "attr" > "max_length"

 $formBuilder = new Symfony\Component\Form\FormBuilder();

 $form = $formBuilder->create('name', 'text', [
-    'max_length' => 123,
+    'attr' => ['maxlength' => 123],
 ]);
SETS:  symfony/* 2.5

ContainerGetNameToTypeInTestsRector

Change $container->get("some_name") to bare type, useful since Symfony 3.4

 use PHPUnit\Framework\TestCase;

 final class SomeTest extends TestCase
 {
     public function run()
     {
         $container = $this->getContainer();
-        $someClass = $container->get('some_name');
+        $someClass = $container->get(SomeType::class);
     }
 }

MergeMethodAnnotationToRouteAnnotationRector

Merge removed @Method annotation to @Route one

-use Sensio\Bundle\FrameworkExtraBundle\Configuration\Method;
 use Symfony\Component\Routing\Annotation\Route;

 class DefaultController extends Controller
 {
     /**
-     * @Route("/show/{id}")
-     * @Method({"GET", "HEAD"})
+     * @Route("/show/{id}", methods={"GET","HEAD"})
      */
     public function show($id)
     {
     }
 }
SETS:  symfony/* 3.4

ReplaceSensioRouteAnnotationWithSymfonyRector

Replace Sensio @Route annotation with Symfony one

-use Sensio\Bundle\FrameworkExtraBundle\Configuration\Route;
+use Symfony\Component\Routing\Annotation\Route;

 final class SomeClass
 {
     /**
      * @Route()
      */
     public function run()
     {
     }
 }
SETS:  symfony/* 3.4

RemoveServiceFromSensioRouteRector

Remove service from Sensio @Route

 use Sensio\Bundle\FrameworkExtraBundle\Configuration\Route;

 final class SomeClass
 {
     /**
-     * @Route(service="some_service")
+     * @Route()
      */
     public function run()
     {
     }
 }
SETS:  symfony/* 3.4

SwiftSetBodyToHtmlPlainMethodCallRector

Changes setBody() method call on Swift_Message into a html() or plain() based on second argument

 $message = new Swift_Message();

-$message->setBody('...', 'text/html');
+$message->html('...');

-$message->setBody('...', 'text/plain');
-$message->setBody('...');
+$message->text('...');
+$message->text('...');

SwiftCreateMessageToNewEmailRector

Changes createMessage() into a new Symfony\Component\Mime\Email

-$email = $this->swift->createMessage('message');
+$email = new \Symfony\Component\Mime\Email();

SwiftMessageToEmailRector

Convert \Swift_Message into an \Symfony\Component\Mime\Email

-$message = (new \Swift_Message('Hello Email'))
-        ->setFrom('send@example.com')
-        ->setTo(['recipient@example.com' => 'Recipient'])
-        ->setBody(
-            $this->renderView(
-                'emails/registration.html.twig',
-                ['name' => $name]
-            ),
-            'text/html'
-        )
+$message = (new Email())
+    ->from(new Address('send@example.com'))
+    ->to(new Address('recipient@example.com', 'Recipient'))
+    ->subject('Hello Email')
+    ->html($this->renderView(
+        'emails/registration.html.twig',
+        ['name' => $name]
+    ))
+;

LiteralGetToRequestClassConstantRector

Replace "GET" string by Symfony Request object class constants

 use Symfony\Component\Form\FormBuilderInterface;

 final class SomeClass
 {
     public function detail(FormBuilderInterface $formBuilder)
     {
-        $formBuilder->setMethod('GET');
+        $formBuilder->setMethod(\Symfony\Component\HttpFoundation\Request::GET);
     }
 }
SETS:  Code Quality

AssertSameResponseCodeWithDebugContentsRector

Make assertSame(200, $response->getStatusCode()) in tests comparing response code to include response contents for faster feedback

 use PHPUnit\Framework\TestCase;

 class SomeClass extends TestCase
 {
     public function run()
     {
         /** @var \Symfony\Component\HttpFoundation\Response $response */
         $response = $this->processResult();

-        $this->assertSame(200, $response->getStatusCode());
+        $this->assertSame(200, $response->getStatusCode(), $response->getContent());
     }
 }
SETS:  Code Quality

ResponseStatusCodeRector

Turns status code numbers to constants

 use Symfony\Component\HttpFoundation\Response;

 class SomeController
 {
     public function index()
     {
         $response = new Response();
-        $response->setStatusCode(200);
+        $response->setStatusCode(Response::HTTP_OK);

-        if ($response->getStatusCode() === 200) {
+        if ($response->getStatusCode() === Response::HTTP_OK) {
         }
     }
 }
SETS:  Code Quality

EventListenerToEventSubscriberRector

Change Symfony Event listener class to Event Subscriber based on configuration in service.yaml file

-class SomeListener
+use Symfony\Component\EventDispatcher\EventSubscriberInterface;
+
+class SomeEventSubscriber implements EventSubscriberInterface
 {
+     /**
+      * @return string[]
+      */
+     public static function getSubscribedEvents(): array
+     {
+         return ['some_event' => 'methodToBeCalled'];
+     }
+
      public function methodToBeCalled()
      {
      }
-}
-
-// in config.yaml
-services:
-    SomeListener:
-        tags:
-            - { name: kernel.event_listener, event: 'some_event', method: 'methodToBeCalled' }
+}
SETS:  Code Quality

LoadValidatorMetadataToAnnotationRector

Move metadata from loadValidatorMetadata() to property/getter/method annotations

 use Symfony\Component\Validator\Constraints as Assert;
 use Symfony\Component\Validator\Mapping\ClassMetadata;

 final class SomeClass
 {
+    /**
+     * @Assert\NotBlank(message="City can't be blank.")
+     */
     private $city;
-
-    public static function loadValidatorMetadata(ClassMetadata $metadata): void
-    {
-        $metadata->addPropertyConstraint('city', new Assert\NotBlank([
-            'message' => 'City can\'t be blank.',
-        ]));
-    }
 }
SETS:  Code Quality

ActionSuffixRemoverRector

Removes Action suffixes from methods in Symfony Controllers

 class SomeController
 {
-    public function indexAction()
+    public function index()
     {
     }
 }
SETS:  Code Quality

RemoveUnusedRequestParamRector

Remove unused $request parameter from controller action

 use Symfony\Component\HttpFoundation\Request;
 use Symfony\Bundle\FrameworkBundle\Controller\Controller;

 final class SomeController extends Controller
 {
-    public function run(Request $request, int $id)
+    public function run(int $id)
     {
         echo $id;
     }
 }
SETS:  Code Quality

ParamTypeFromRouteRequiredRegexRector

Complete strict param type declaration based on route annotation

 use Symfony\Bundle\FrameworkBundle\Controller\Controller;
 use Symfony\Component\Routing\Annotation\Route;

 final class SomeController extends Controller
 {
     /**
      * @Route(
      *     requirements={"number"="\d+"},
      * )
      */
-    public function detailAction($number)
+    public function detailAction(int $number)
     {
     }
 }
SETS:  Code Quality

ResponseReturnTypeControllerActionRector

Add Response object return type to controller actions

 use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
+use Symfony\Component\HttpFoundation\Response;
 use Symfony\Component\Routing\Annotation\Route;

 final class SomeController extends AbstractController
 {
     #[Route]
-    public function detail()
+    public function detail(): Response
     {
         return $this->render('some_template');
     }
 }

RedirectToRouteRector

Turns redirect to route to short helper method in Controller in Symfony

-$this->redirect($this->generateUrl("homepage"));
+$this->redirectToRoute("homepage");