diff --git a/src/Type/Nette/FormContainerValuesDynamicReturnTypeExtension.php b/src/Type/Nette/FormContainerValuesDynamicReturnTypeExtension.php index 10501d4..a62b2af 100644 --- a/src/Type/Nette/FormContainerValuesDynamicReturnTypeExtension.php +++ b/src/Type/Nette/FormContainerValuesDynamicReturnTypeExtension.php @@ -45,10 +45,18 @@ public function isMethodSupported(MethodReflection $methodReflection): bool } // nette/forms 3.2.9+ and methods overriding it can describe a more precise return type in PHPDoc, - // older versions state just object|array - return $returnTag->getType()->isSuperTypeOf( + // older versions state just object|array (3.0 - 3.2.8) or ArrayHash|array (2.x) + $returnType = $returnTag->getType(); + if ($returnType->isSuperTypeOf( TypeCombinator::union(new ArrayType(new MixedType(), new MixedType()), new ObjectWithoutClassType()), - )->yes(); + )->yes()) { + return true; + } + + $arrayHashOrArray = TypeCombinator::union(new ArrayType(new MixedType(), new MixedType()), new ObjectType('Nette\Utils\ArrayHash')); + + return $returnType->isSuperTypeOf($arrayHashOrArray)->yes() + && $arrayHashOrArray->isSuperTypeOf($returnType)->yes(); } public function getTypeFromMethodCall(MethodReflection $methodReflection, MethodCall $methodCall, Scope $scope): Type diff --git a/tests/Type/Nette/FormContainerValuesDynamicReturnTypeExtensionTest.php b/tests/Type/Nette/FormContainerValuesDynamicReturnTypeExtensionTest.php index 778295b..57becf2 100644 --- a/tests/Type/Nette/FormContainerValuesDynamicReturnTypeExtensionTest.php +++ b/tests/Type/Nette/FormContainerValuesDynamicReturnTypeExtensionTest.php @@ -14,6 +14,7 @@ final class FormContainerValuesDynamicReturnTypeExtensionTest extends TypeInfere public static function dataFileAsserts(): iterable { yield from self::gatherAssertTypes(__DIR__ . '/data/FormContainerOverriddenValues.php'); + yield from self::gatherAssertTypes(__DIR__ . '/data/FormContainerArrayHashOrArrayValues.php'); try { $formsVersion = class_exists(InstalledVersions::class) diff --git a/tests/Type/Nette/data/FormContainerArrayHashOrArrayValues.php b/tests/Type/Nette/data/FormContainerArrayHashOrArrayValues.php new file mode 100644 index 0000000..0a9e24b --- /dev/null +++ b/tests/Type/Nette/data/FormContainerArrayHashOrArrayValues.php @@ -0,0 +1,53 @@ + + */ + public function getValues($returnType = null, ?array $controls = null) + { + return parent::getValues($returnType, $controls); + } + +} + +function (FormWithArrayHashOrArrayValues $form): void { + assertType('array', $form->getValues(true)); + assertType('array', $form->getValues('array')); + assertType(ArrayHash::class, $form->getValues()); + assertType(ArrayHash::class, $form->getValues(null)); +}; + +function (FormWithNarrowerValues $form): void { + assertType('array|' . CustomValues::class, $form->getValues(true)); + assertType('array|' . CustomValues::class, $form->getValues()); +};