Skip to content

Commit dcb8a88

Browse files
authored
[CodeQuality] Concat name annotation/attribute on InlineClassRoutePrefixRector (#704)
1 parent c02c255 commit dcb8a88

File tree

4 files changed

+136
-1
lines changed

4 files changed

+136
-1
lines changed

config/sets/symfony/symfony60.php

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@
55
use PhpParser\Node\Scalar\String_;
66
use PHPStan\Type\MixedType;
77
use PHPStan\Type\ObjectType;
8-
use PHPStan\Type\StringType;
98
use Rector\Config\RectorConfig;
109
use Rector\Renaming\Rector\MethodCall\RenameMethodRector;
1110
use Rector\Renaming\Rector\Name\RenameClassRector;
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
<?php
2+
3+
namespace Rector\Symfony\Tests\CodeQuality\Rector\Class_\InlineClassRoutePrefixRector\Fixture;
4+
5+
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
6+
use Symfony\Component\Routing\Annotation\Route;
7+
8+
/**
9+
* @Route(path="/city", name="some_org.")
10+
*/
11+
final class WithExistingName extends Controller
12+
{
13+
/**
14+
* @Route("/street", name="some")
15+
*/
16+
public function some()
17+
{
18+
}
19+
}
20+
21+
?>
22+
-----
23+
<?php
24+
25+
namespace Rector\Symfony\Tests\CodeQuality\Rector\Class_\InlineClassRoutePrefixRector\Fixture;
26+
27+
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
28+
use Symfony\Component\Routing\Annotation\Route;
29+
30+
final class WithExistingName extends Controller
31+
{
32+
/**
33+
* @Route("/city/street", name="some_org.some")
34+
*/
35+
public function some()
36+
{
37+
}
38+
}
39+
40+
?>
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
<?php
2+
3+
namespace Rector\Symfony\Tests\CodeQuality\Rector\Class_\InlineClassRoutePrefixRector\Fixture;
4+
5+
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
6+
use Symfony\Component\Routing\Annotation\Route;
7+
8+
#[\Symfony\Component\Routing\Attribute\Route("/city", name: "some_org.")]
9+
final class WithExistingName2 extends Controller
10+
{
11+
#[\Symfony\Component\Routing\Attribute\Route("/street", name: "some")]
12+
public function some()
13+
{
14+
}
15+
}
16+
17+
?>
18+
-----
19+
<?php
20+
21+
namespace Rector\Symfony\Tests\CodeQuality\Rector\Class_\InlineClassRoutePrefixRector\Fixture;
22+
23+
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
24+
use Symfony\Component\Routing\Annotation\Route;
25+
26+
final class WithExistingName2 extends Controller
27+
{
28+
#[\Symfony\Component\Routing\Attribute\Route('/city/street', name: 'some_org.some')]
29+
public function some()
30+
{
31+
}
32+
}
33+
34+
?>

rules/CodeQuality/Rector/Class_/InlineClassRoutePrefixRector.php

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,7 @@ public function refactor(Node $node): ?Class_
107107
}
108108

109109
$classRoutePath = null;
110+
$classRouteName = null;
110111

111112
// 1. detect attribute
112113
$routeAttributeOrAnnotation = $this->attrinationFinder->getByMany(
@@ -116,8 +117,10 @@ public function refactor(Node $node): ?Class_
116117

117118
if ($routeAttributeOrAnnotation instanceof DoctrineAnnotationTagValueNode) {
118119
$classRoutePath = $this->resolveRoutePath($routeAttributeOrAnnotation);
120+
$classRouteName = $this->resolveRouteName($routeAttributeOrAnnotation);
119121
} elseif ($routeAttributeOrAnnotation instanceof Attribute) {
120122
$classRoutePath = $this->resolveRoutePathFromAttribute($routeAttributeOrAnnotation);
123+
$classRouteName = $this->resolveRouteNameFromAttribute($routeAttributeOrAnnotation);
121124
}
122125

123126
if ($classRoutePath === null) {
@@ -155,6 +158,15 @@ public function refactor(Node $node): ?Class_
155158
$newMethodPath = $classRoutePath . $methodPrefix->value;
156159

157160
$routePathArrayItemNode->value = new StringNode($newMethodPath);
161+
162+
foreach ($methodRouteAnnotationOrAttribute->values as $value) {
163+
if ($value->key === 'name' && $value->value instanceof StringNode && is_string(
164+
$classRouteName
165+
)) {
166+
$value->value->value = $classRouteName . $value->value->value;
167+
}
168+
}
169+
158170
$this->docBlockUpdater->updateRefactoredNodeWithPhpDocInfo($classMethod);
159171

160172
$hasChanged = true;
@@ -173,6 +185,23 @@ public function refactor(Node $node): ?Class_
173185
));
174186

175187
$hasChanged = true;
188+
189+
continue;
190+
}
191+
192+
if ($methodRouteArg->name->toString() === 'name') {
193+
if (! $methodRouteArg->value instanceof String_) {
194+
continue;
195+
}
196+
197+
$methodRouteString = $methodRouteArg->value;
198+
$methodRouteArg->value = new String_(sprintf(
199+
'%s%s',
200+
$classRouteName,
201+
$methodRouteString->value
202+
));
203+
204+
$hasChanged = true;
176205
}
177206
}
178207
}
@@ -238,6 +267,21 @@ private function resolveRoutePath(DoctrineAnnotationTagValueNode $doctrineAnnota
238267
return $classRoutePathNode->value->value;
239268
}
240269

270+
private function resolveRouteName(DoctrineAnnotationTagValueNode $doctrineAnnotationTagValueNode): ?string
271+
{
272+
$classRouteNameNode = $doctrineAnnotationTagValueNode->getValue('name');
273+
274+
if (! $classRouteNameNode instanceof ArrayItemNode) {
275+
return null;
276+
}
277+
278+
if (! $classRouteNameNode->value instanceof StringNode) {
279+
return null;
280+
}
281+
282+
return $classRouteNameNode->value->value;
283+
}
284+
241285
private function resolveRoutePathFromAttribute(Attribute $attribute): ?string
242286
{
243287
foreach ($attribute->args as $arg) {
@@ -252,4 +296,22 @@ private function resolveRoutePathFromAttribute(Attribute $attribute): ?string
252296

253297
return null;
254298
}
299+
300+
private function resolveRouteNameFromAttribute(Attribute $attribute): ?string
301+
{
302+
foreach ($attribute->args as $arg) {
303+
if ($arg->name === null) {
304+
continue;
305+
}
306+
307+
if ($arg->name->toString() === 'name') {
308+
$routeExpr = $arg->value;
309+
if ($routeExpr instanceof String_) {
310+
return $routeExpr->value;
311+
}
312+
}
313+
}
314+
315+
return null;
316+
}
255317
}

0 commit comments

Comments
 (0)