Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion src/Rules/NarrowPrivateClassMethodParamTypeRule.php
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
use PHPStan\Rules\Rule;
use PHPStan\Rules\RuleError;
use PHPStan\Rules\RuleErrorBuilder;
use PHPStan\Type\Generic\GenericObjectType;
use PHPStan\Type\Generic\TemplateType;
use PHPStan\Type\IntersectionType;
use PHPStan\Type\MixedType;
Expand Down Expand Up @@ -149,7 +150,7 @@ private function validateParam(Param $param, int $position, Expr $expr, Scope $s
return null;
}

if ($argType instanceof IntersectionType) {
if ($argType instanceof IntersectionType || $argType instanceof GenericObjectType) {
Copy link
Copy Markdown
Contributor Author

@staabm staabm Apr 17, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this false positives occur, because of the recent changes in ObjectType->equals() in PHPStan and the non-public-api compilant use of the PHPStan Type system ins this package (using instanceof on Type objects).

I don't think its worth our time to make this rule print meaningful results for generic objects. it would involve a very different approach to what this rule is doing today.

therefore I think just skipping generics is the way to go

return null;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
<?php

namespace Rector\TypePerfect\Tests\Rules\NarrowPrivateClassMethodParamTypeRule\Fixture;


use Rector\TypePerfect\Tests\Rules\NarrowPrivateClassMethodParamTypeRule\Source\MyIterator;
use Rector\TypePerfect\Tests\Rules\NarrowPrivateClassMethodParamTypeRule\Source\MyPreise;

final class SkipSameGeneric
{
protected function getPriceAndCalculateTableVM(): void
{

$prices = $this->getPricesForArticle();
$this->getAmounts($prices);
}

/**
* @param MyIterator<MyPreise> $prices
*/
private function getAmounts(MyIterator $prices): void
{
}

/**
* @return MyIterator<MyPreise>
*/
private function getPricesForArticle(): MyIterator
{
/** @var MyIterator<MyPreise> */
return new MyIterator();
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ public static function provideData(): Iterator
yield [__DIR__ . '/Fixture/SkipGenericType.php', []];
yield [__DIR__ . '/Fixture/SkipAbstractBase.php', []];
yield [__DIR__ . '/Fixture/SkipVariadics.php', []];
yield [__DIR__ . '/Fixture/SkipSameGeneric.php', []];
}

/**
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?php

declare(strict_types=1);

namespace Rector\TypePerfect\Tests\Rules\NarrowPrivateClassMethodParamTypeRule\Source;

/**
* @template T
*/
final class MyIterator
{
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<?php

declare(strict_types=1);

namespace Rector\TypePerfect\Tests\Rules\NarrowPrivateClassMethodParamTypeRule\Source;

class MyPreise
{
}
Loading