Skip to content

Commit c6fda38

Browse files
committed
Allow Traversable in PHPDoc and Iterator in native type to cooperate
1 parent f658b3c commit c6fda38

File tree

2 files changed

+23
-1
lines changed

2 files changed

+23
-1
lines changed

phpstan-baseline.neon

+6
Original file line numberDiff line numberDiff line change
@@ -1854,6 +1854,12 @@ parameters:
18541854
count: 1
18551855
path: src/Type/TypehintHelper.php
18561856

1857+
-
1858+
message: '#^Doing instanceof PHPStan\\Type\\TypeWithClassName is error\-prone and deprecated\. Use Type\:\:getObjectClassNames\(\) or Type\:\:getObjectClassReflections\(\) instead\.$#'
1859+
identifier: phpstanApi.instanceofType
1860+
count: 1
1861+
path: src/Type/TypehintHelper.php
1862+
18571863
-
18581864
message: '#^Doing instanceof PHPStan\\Type\\CallableType is error\-prone and deprecated\. Use Type\:\:isCallable\(\) and Type\:\:getCallableParametersAcceptors\(\) instead\.$#'
18591865
identifier: phpstanApi.instanceofType

src/Type/TypehintHelper.php

+17-1
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
use PHPStan\Type\Constant\ConstantArrayType;
1313
use PHPStan\Type\Generic\TemplateTypeHelper;
1414
use ReflectionType;
15+
use Traversable;
1516
use function array_map;
1617
use function count;
1718
use function get_class;
@@ -118,9 +119,24 @@ public static function decideType(
118119
}
119120
}
120121

122+
$resolvedPhpDocTypeToBounds = TemplateTypeHelper::resolveToBounds($phpDocType);
123+
$isSuperType = $type->isSuperTypeOf($resolvedPhpDocTypeToBounds);
124+
if (
125+
!$isSuperType->yes()
126+
&& (new ObjectType(Traversable::class))->isSuperTypeOf($phpDocType)->yes()
127+
&& $type instanceof TypeWithClassName
128+
) {
129+
// if native type is Iterator and PHPDoc type is Traversable
130+
// Allow PHPDoc type to win
131+
$traversableAncestor = $type->getAncestorWithClassName(Traversable::class);
132+
if ($traversableAncestor !== null) {
133+
$isSuperType = $traversableAncestor->isSuperTypeOf($resolvedPhpDocTypeToBounds);
134+
}
135+
}
136+
121137
if (
122138
(!$phpDocType instanceof NeverType || ($type instanceof MixedType && !$type->isExplicitMixed()))
123-
&& $type->isSuperTypeOf(TemplateTypeHelper::resolveToBounds($phpDocType))->yes()
139+
&& $isSuperType->yes()
124140
) {
125141
$resultType = $phpDocType;
126142
} else {

0 commit comments

Comments
 (0)