From 8f56de3dbb5afed3937594ccc9e150487e6512d2 Mon Sep 17 00:00:00 2001 From: Vincent Langlet Date: Sat, 27 Sep 2025 21:38:22 +0200 Subject: [PATCH] WIP --- src/Php/PhpVersion.php | 10 ++++++++++ src/Rules/Arrays/AllowedArrayKeysTypes.php | 18 +++++++++++++----- .../Arrays/InvalidKeyInArrayDimFetchRule.php | 7 +++++-- .../InvalidKeyInArrayDimFetchRuleTest.php | 7 ++++++- 4 files changed, 34 insertions(+), 8 deletions(-) diff --git a/src/Php/PhpVersion.php b/src/Php/PhpVersion.php index 2a151b58ae..fc741647a8 100644 --- a/src/Php/PhpVersion.php +++ b/src/Php/PhpVersion.php @@ -414,4 +414,14 @@ public function hasPDOSubclasses(): bool return $this->versionId >= 80400; } + public function deprecatesImplicitlyFloatConversionToInt(): bool + { + return $this->versionId >= 80100; + } + + public function deprecatesNullArrayOffset(): bool + { + return $this->versionId >= 80500; + } + } diff --git a/src/Rules/Arrays/AllowedArrayKeysTypes.php b/src/Rules/Arrays/AllowedArrayKeysTypes.php index 7d920e167c..8cbde156dd 100644 --- a/src/Rules/Arrays/AllowedArrayKeysTypes.php +++ b/src/Rules/Arrays/AllowedArrayKeysTypes.php @@ -2,6 +2,7 @@ namespace PHPStan\Rules\Arrays; +use PHPStan\Php\PhpVersion; use PHPStan\Type\ArrayType; use PHPStan\Type\BooleanType; use PHPStan\Type\Constant\ConstantBooleanType; @@ -21,15 +22,22 @@ final class AllowedArrayKeysTypes { - public static function getType(): Type + public static function getType(PhpVersion $phpVersion): Type { - return new UnionType([ + $allowedTypes = [ new IntegerType(), new StringType(), - new FloatType(), new BooleanType(), - new NullType(), - ]); + ]; + + if (!$phpVersion->deprecatesImplicitlyFloatConversionToInt()) { + $allowedTypes[] = new FloatType(); + } + if (!$phpVersion->deprecatesNullArrayOffset()) { + $allowedTypes[] = new NullType(); + } + + return new UnionType($allowedTypes); } public static function narrowOffsetKeyType(Type $varType, Type $keyType): ?Type diff --git a/src/Rules/Arrays/InvalidKeyInArrayDimFetchRule.php b/src/Rules/Arrays/InvalidKeyInArrayDimFetchRule.php index 5ba1a88009..50e74ca81a 100644 --- a/src/Rules/Arrays/InvalidKeyInArrayDimFetchRule.php +++ b/src/Rules/Arrays/InvalidKeyInArrayDimFetchRule.php @@ -6,6 +6,7 @@ use PHPStan\Analyser\Scope; use PHPStan\DependencyInjection\AutowiredParameter; use PHPStan\DependencyInjection\RegisteredRule; +use PHPStan\Php\PhpVersion; use PHPStan\Rules\Rule; use PHPStan\Rules\RuleErrorBuilder; use PHPStan\Rules\RuleLevelHelper; @@ -23,6 +24,7 @@ final class InvalidKeyInArrayDimFetchRule implements Rule public function __construct( private RuleLevelHelper $ruleLevelHelper, + private PhpVersion $phpVersion, #[AutowiredParameter] private bool $reportMaybes, ) @@ -56,17 +58,18 @@ public function processNode(Node $node, Scope $scope): array return []; } + $phpVersion = $this->phpVersion; $dimensionType = $this->ruleLevelHelper->findTypeToCheck( $scope, $node->dim, '', - static fn (Type $dimType): bool => AllowedArrayKeysTypes::getType()->isSuperTypeOf($dimType)->yes(), + static fn (Type $dimType): bool => AllowedArrayKeysTypes::getType($phpVersion)->isSuperTypeOf($dimType)->yes(), )->getType(); if ($dimensionType instanceof ErrorType) { return []; } - $isSuperType = AllowedArrayKeysTypes::getType()->isSuperTypeOf($dimensionType); + $isSuperType = AllowedArrayKeysTypes::getType($phpVersion)->isSuperTypeOf($dimensionType); if ($isSuperType->yes() || ($isSuperType->maybe() && !$this->reportMaybes)) { return []; } diff --git a/tests/PHPStan/Rules/Arrays/InvalidKeyInArrayDimFetchRuleTest.php b/tests/PHPStan/Rules/Arrays/InvalidKeyInArrayDimFetchRuleTest.php index 22716afcd4..6b3d965dc3 100644 --- a/tests/PHPStan/Rules/Arrays/InvalidKeyInArrayDimFetchRuleTest.php +++ b/tests/PHPStan/Rules/Arrays/InvalidKeyInArrayDimFetchRuleTest.php @@ -2,6 +2,7 @@ namespace PHPStan\Rules\Arrays; +use PHPStan\Php\PhpVersion; use PHPStan\Rules\Rule; use PHPStan\Rules\RuleLevelHelper; use PHPStan\Testing\RuleTestCase; @@ -16,7 +17,11 @@ class InvalidKeyInArrayDimFetchRuleTest extends RuleTestCase protected function getRule(): Rule { $ruleLevelHelper = new RuleLevelHelper(self::createReflectionProvider(), true, false, true, true, true, false, true); - return new InvalidKeyInArrayDimFetchRule($ruleLevelHelper, true); + return new InvalidKeyInArrayDimFetchRule( + $ruleLevelHelper, + self::getContainer()->getByType(PhpVersion::class), + true + ); } public function testInvalidKey(): void