Skip to content

Commit 0f9c992

Browse files
committed
Updated Rector to commit 4997962de1f53c449dadbef7025bffe5ca41e63c
rectorphp/rector-src@4997962 Bump PHPStan to 2.1.38 (#7879)
1 parent ab4fad0 commit 0f9c992

8 files changed

Lines changed: 205 additions & 6 deletions

File tree

vendor/composer/autoload_classmap.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1969,6 +1969,7 @@
19691969
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\PreferPHPUnitSelfCallRector' => $vendorDir . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/PreferPHPUnitSelfCallRector.php',
19701970
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\PreferPHPUnitThisCallRector' => $vendorDir . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/PreferPHPUnitThisCallRector.php',
19711971
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\RemoveDataProviderParamKeysRector' => $vendorDir . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/RemoveDataProviderParamKeysRector.php',
1972+
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\RemoveNeverUsedMockPropertyRector' => $vendorDir . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/RemoveNeverUsedMockPropertyRector.php',
19721973
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\SetUpBeforeClassToSetUpRector' => $vendorDir . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/SetUpBeforeClassToSetUpRector.php',
19731974
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\SingleMockPropertyTypeRector' => $vendorDir . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/SingleMockPropertyTypeRector.php',
19741975
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\SuffixMockObjectPropertyRector' => $vendorDir . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/SuffixMockObjectPropertyRector.php',

vendor/composer/autoload_static.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2229,6 +2229,7 @@ class ComposerStaticInit6374fd21a3f525a40760d79e3596b56b
22292229
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\PreferPHPUnitSelfCallRector' => __DIR__ . '/..' . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/PreferPHPUnitSelfCallRector.php',
22302230
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\PreferPHPUnitThisCallRector' => __DIR__ . '/..' . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/PreferPHPUnitThisCallRector.php',
22312231
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\RemoveDataProviderParamKeysRector' => __DIR__ . '/..' . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/RemoveDataProviderParamKeysRector.php',
2232+
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\RemoveNeverUsedMockPropertyRector' => __DIR__ . '/..' . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/RemoveNeverUsedMockPropertyRector.php',
22322233
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\SetUpBeforeClassToSetUpRector' => __DIR__ . '/..' . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/SetUpBeforeClassToSetUpRector.php',
22332234
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\SingleMockPropertyTypeRector' => __DIR__ . '/..' . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/SingleMockPropertyTypeRector.php',
22342235
'Rector\\PHPUnit\\CodeQuality\\Rector\\Class_\\SuffixMockObjectPropertyRector' => __DIR__ . '/..' . '/rector/rector-phpunit/rules/CodeQuality/Rector/Class_/SuffixMockObjectPropertyRector.php',

vendor/composer/installed.json

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1818,12 +1818,12 @@
18181818
"source": {
18191819
"type": "git",
18201820
"url": "https:\/\/github.com\/rectorphp\/rector-phpunit.git",
1821-
"reference": "1993f6b70c1e8ee8241c56c3876a13f52facfb13"
1821+
"reference": "2f2e3dfd57626f31a1ec6d2ba76e11952d158282"
18221822
},
18231823
"dist": {
18241824
"type": "zip",
1825-
"url": "https:\/\/api.github.com\/repos\/rectorphp\/rector-phpunit\/zipball\/1993f6b70c1e8ee8241c56c3876a13f52facfb13",
1826-
"reference": "1993f6b70c1e8ee8241c56c3876a13f52facfb13",
1825+
"url": "https:\/\/api.github.com\/repos\/rectorphp\/rector-phpunit\/zipball\/2f2e3dfd57626f31a1ec6d2ba76e11952d158282",
1826+
"reference": "2f2e3dfd57626f31a1ec6d2ba76e11952d158282",
18271827
"shasum": ""
18281828
},
18291829
"require": {
@@ -1850,7 +1850,7 @@
18501850
"tomasvotruba\/unused-public": "^2.2",
18511851
"tracy\/tracy": "^2.11"
18521852
},
1853-
"time": "2026-02-04T12:33:44+00:00",
1853+
"time": "2026-02-04T15:33:06+00:00",
18541854
"default-branch": true,
18551855
"type": "rector-extension",
18561856
"extra": {

vendor/composer/installed.php

Lines changed: 1 addition & 1 deletion
Large diffs are not rendered by default.

vendor/rector/extension-installer/src/GeneratedConfig.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99
*/
1010
final class GeneratedConfig
1111
{
12-
public const EXTENSIONS = array('rector/rector-doctrine' => array('install_path' => '/home/runner/work/rector-src/rector-src/rector-build/vendor/rector/rector-doctrine', 'relative_install_path' => '../../rector-doctrine', 'extra' => NULL, 'version' => 'dev-main 46e4f77'), 'rector/rector-downgrade-php' => array('install_path' => '/home/runner/work/rector-src/rector-src/rector-build/vendor/rector/rector-downgrade-php', 'relative_install_path' => '../../rector-downgrade-php', 'extra' => NULL, 'version' => 'dev-main a110e2f'), 'rector/rector-phpunit' => array('install_path' => '/home/runner/work/rector-src/rector-src/rector-build/vendor/rector/rector-phpunit', 'relative_install_path' => '../../rector-phpunit', 'extra' => NULL, 'version' => 'dev-main 1993f6b'), 'rector/rector-symfony' => array('install_path' => '/home/runner/work/rector-src/rector-src/rector-build/vendor/rector/rector-symfony', 'relative_install_path' => '../../rector-symfony', 'extra' => NULL, 'version' => 'dev-main eadb590'));
12+
public const EXTENSIONS = array('rector/rector-doctrine' => array('install_path' => '/home/runner/work/rector-src/rector-src/rector-build/vendor/rector/rector-doctrine', 'relative_install_path' => '../../rector-doctrine', 'extra' => NULL, 'version' => 'dev-main 46e4f77'), 'rector/rector-downgrade-php' => array('install_path' => '/home/runner/work/rector-src/rector-src/rector-build/vendor/rector/rector-downgrade-php', 'relative_install_path' => '../../rector-downgrade-php', 'extra' => NULL, 'version' => 'dev-main a110e2f'), 'rector/rector-phpunit' => array('install_path' => '/home/runner/work/rector-src/rector-src/rector-build/vendor/rector/rector-phpunit', 'relative_install_path' => '../../rector-phpunit', 'extra' => NULL, 'version' => 'dev-main 2f2e3df'), 'rector/rector-symfony' => array('install_path' => '/home/runner/work/rector-src/rector-src/rector-build/vendor/rector/rector-symfony', 'relative_install_path' => '../../rector-symfony', 'extra' => NULL, 'version' => 'dev-main eadb590'));
1313
private function __construct()
1414
{
1515
}

vendor/rector/rector-phpunit/config/sets/phpunit-code-quality.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
use Rector\PHPUnit\CodeQuality\Rector\Class_\InlineStubPropertyToCreateStubMethodCallRector;
1212
use Rector\PHPUnit\CodeQuality\Rector\Class_\NarrowUnusedSetUpDefinedPropertyRector;
1313
use Rector\PHPUnit\CodeQuality\Rector\Class_\PreferPHPUnitThisCallRector;
14+
use Rector\PHPUnit\CodeQuality\Rector\Class_\RemoveNeverUsedMockPropertyRector;
1415
use Rector\PHPUnit\CodeQuality\Rector\Class_\SingleMockPropertyTypeRector;
1516
use Rector\PHPUnit\CodeQuality\Rector\Class_\TestWithToDataProviderRector;
1617
use Rector\PHPUnit\CodeQuality\Rector\Class_\TypeWillReturnCallableArrowFunctionRector;
@@ -133,6 +134,7 @@
133134
EntityDocumentCreateMockToDirectNewRector::class,
134135
ReplaceAtMethodWithDesiredMatcherRector::class,
135136
BareCreateMockAssignToDirectUseRector::class,
137+
RemoveNeverUsedMockPropertyRector::class,
136138
// readability
137139
NoSetupWithParentCallOverrideRector::class,
138140
]);

vendor/rector/rector-phpunit/rules/CodeQuality/NodeAnalyser/MockObjectExprDetector.php

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
namespace Rector\PHPUnit\CodeQuality\NodeAnalyser;
55

66
use PhpParser\Node\Expr;
7+
use PhpParser\Node\Expr\CallLike;
78
use PhpParser\Node\Expr\MethodCall;
89
use PhpParser\Node\Expr\PropertyFetch;
910
use PhpParser\Node\Expr\Variable;
@@ -93,4 +94,25 @@ public function isPropertyUsedForMocking(Class_ $class, string $propertyName): b
9394
}
9495
return \false;
9596
}
97+
public function isPropertyMockObjectPassedAsArgument(Class_ $class, string $propertyName): bool
98+
{
99+
/** @var array<Expr\CallLike> $callLikes */
100+
$callLikes = $this->betterNodeFinder->findInstancesOfScoped($class->getMethods(), [CallLike::class]);
101+
foreach ($callLikes as $callLike) {
102+
if ($callLike->isFirstClassCallable()) {
103+
continue;
104+
}
105+
foreach ($callLike->getArgs() as $arg) {
106+
if (!$arg->value instanceof PropertyFetch) {
107+
continue;
108+
}
109+
$propertyFetch = $arg->value;
110+
// its used in arg
111+
if ($this->nodeNameResolver->isName($propertyFetch->name, $propertyName)) {
112+
return \true;
113+
}
114+
}
115+
}
116+
return \false;
117+
}
96118
}
Lines changed: 173 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,173 @@
1+
<?php
2+
3+
declare (strict_types=1);
4+
namespace Rector\PHPUnit\CodeQuality\Rector\Class_;
5+
6+
use PhpParser\Node;
7+
use PhpParser\Node\Expr\Assign;
8+
use PhpParser\Node\Expr\MethodCall;
9+
use PhpParser\Node\Expr\PropertyFetch;
10+
use PhpParser\Node\Stmt\Class_;
11+
use PhpParser\Node\Stmt\ClassMethod;
12+
use PhpParser\Node\Stmt\Expression;
13+
use PhpParser\Node\Stmt\Property;
14+
use Rector\PHPUnit\CodeQuality\NodeAnalyser\MockObjectExprDetector;
15+
use Rector\PHPUnit\CodeQuality\NodeAnalyser\MockObjectPropertyDetector;
16+
use Rector\PHPUnit\NodeAnalyzer\TestsNodeAnalyzer;
17+
use Rector\Rector\AbstractRector;
18+
use Rector\ValueObject\MethodName;
19+
use Symplify\RuleDocGenerator\ValueObject\CodeSample\CodeSample;
20+
use Symplify\RuleDocGenerator\ValueObject\RuleDefinition;
21+
/**
22+
* @see \Rector\PHPUnit\Tests\CodeQuality\Rector\Class_\RemoveNeverUsedMockPropertyRector\RemoveNeverUsedMockPropertyRectorTest
23+
*/
24+
final class RemoveNeverUsedMockPropertyRector extends AbstractRector
25+
{
26+
/**
27+
* @readonly
28+
*/
29+
private TestsNodeAnalyzer $testsNodeAnalyzer;
30+
/**
31+
* @readonly
32+
*/
33+
private MockObjectPropertyDetector $mockObjectPropertyDetector;
34+
/**
35+
* @readonly
36+
*/
37+
private MockObjectExprDetector $mockObjectExprDetector;
38+
public function __construct(TestsNodeAnalyzer $testsNodeAnalyzer, MockObjectPropertyDetector $mockObjectPropertyDetector, MockObjectExprDetector $mockObjectExprDetector)
39+
{
40+
$this->testsNodeAnalyzer = $testsNodeAnalyzer;
41+
$this->mockObjectPropertyDetector = $mockObjectPropertyDetector;
42+
$this->mockObjectExprDetector = $mockObjectExprDetector;
43+
}
44+
public function getRuleDefinition(): RuleDefinition
45+
{
46+
return new RuleDefinition('Remove never used property mock, only to set expectations', [new CodeSample(<<<'CODE_SAMPLE'
47+
use PHPUnit\Framework\TestCase;
48+
49+
final class SomeTest extends TestCase
50+
{
51+
private $mockProperty = null;
52+
53+
protected function setUp(): void
54+
{
55+
$this->mockProperty = $this->createMock(SomeClass::class);
56+
$this->mockProperty->expects($this->once())
57+
->method('someMethod')
58+
->willReturn('someValue');
59+
}
60+
}
61+
CODE_SAMPLE
62+
, <<<'CODE_SAMPLE'
63+
use PHPUnit\Framework\TestCase;
64+
65+
final class SomeTest extends TestCase
66+
{
67+
protected function setUp(): void
68+
{
69+
}
70+
}
71+
CODE_SAMPLE
72+
)]);
73+
}
74+
/**
75+
* @return array<class-string<Node>>
76+
*/
77+
public function getNodeTypes(): array
78+
{
79+
return [Class_::class];
80+
}
81+
/**
82+
* @param Class_ $node
83+
*/
84+
public function refactor(Node $node): ?Node
85+
{
86+
if (!$this->testsNodeAnalyzer->isInTestClass($node)) {
87+
return null;
88+
}
89+
$setUpClassMethod = $node->getMethod(MethodName::SET_UP);
90+
if (!$setUpClassMethod instanceof ClassMethod) {
91+
return null;
92+
}
93+
$propertyNamesToCreateMockMethodCalls = $this->mockObjectPropertyDetector->collectFromClassMethod($setUpClassMethod);
94+
if ($propertyNamesToCreateMockMethodCalls === []) {
95+
return null;
96+
}
97+
$propertyNamesToRemove = [];
98+
foreach (array_keys($propertyNamesToCreateMockMethodCalls) as $propertyName) {
99+
if ($this->mockObjectExprDetector->isPropertyMockObjectPassedAsArgument($node, $propertyName)) {
100+
continue;
101+
}
102+
$propertyNamesToRemove[] = $propertyName;
103+
}
104+
if ($propertyNamesToRemove === []) {
105+
return null;
106+
}
107+
// remove never used mock properties
108+
foreach ($propertyNamesToRemove as $propertyNameToRemove) {
109+
// 1. remove property
110+
$this->removePropertyFromClass($node, $propertyNameToRemove);
111+
// 2. remove assign from setUp()
112+
$this->removeMockPropertyFromSetUpMethod($setUpClassMethod, $propertyNameToRemove);
113+
// 3. remove expression method calls on this property
114+
foreach ($node->getMethods() as $classMethod) {
115+
foreach ((array) $classMethod->stmts as $key => $classMethodStmt) {
116+
if (!$classMethodStmt instanceof Expression) {
117+
continue;
118+
}
119+
if (!$classMethodStmt->expr instanceof MethodCall) {
120+
continue;
121+
}
122+
$methodCall = $classMethodStmt->expr;
123+
$currentMethodCall = $methodCall;
124+
while ($currentMethodCall->var instanceof MethodCall) {
125+
$currentMethodCall = $currentMethodCall->var;
126+
}
127+
if (!$currentMethodCall->var instanceof PropertyFetch) {
128+
continue;
129+
}
130+
$propertyFetch = $currentMethodCall->var;
131+
if (!$this->isName($propertyFetch->name, $propertyNameToRemove)) {
132+
continue;
133+
}
134+
unset($classMethod->stmts[$key]);
135+
}
136+
}
137+
}
138+
return $node;
139+
}
140+
private function removeMockPropertyFromSetUpMethod(ClassMethod $setUpClassMethod, string $propertyName): void
141+
{
142+
foreach ((array) $setUpClassMethod->stmts as $key => $classStmt) {
143+
if (!$classStmt instanceof Expression) {
144+
continue;
145+
}
146+
if (!$classStmt->expr instanceof Assign) {
147+
continue;
148+
}
149+
$assign = $classStmt->expr;
150+
if (!$assign->var instanceof PropertyFetch) {
151+
continue;
152+
}
153+
$assignedPropertyFetch = $assign->var;
154+
if (!$this->isName($assignedPropertyFetch->name, $propertyName)) {
155+
continue;
156+
}
157+
unset($setUpClassMethod->stmts[$key]);
158+
return;
159+
}
160+
}
161+
private function removePropertyFromClass(Class_ $class, string $propertyNameToRemove): void
162+
{
163+
foreach ($class->stmts as $key => $stmt) {
164+
if (!$stmt instanceof Property) {
165+
continue;
166+
}
167+
if (!$this->isName($stmt, $propertyNameToRemove)) {
168+
continue;
169+
}
170+
unset($class->stmts[$key]);
171+
}
172+
}
173+
}

0 commit comments

Comments
 (0)