diff --git a/src/Rule/Nette/RegularExpressionPatternRule.php b/src/Rule/Nette/RegularExpressionPatternRule.php index 324014b..35fea39 100644 --- a/src/Rule/Nette/RegularExpressionPatternRule.php +++ b/src/Rule/Nette/RegularExpressionPatternRule.php @@ -9,7 +9,6 @@ use PHPStan\Analyser\Scope; use PHPStan\Rules\Rule; use PHPStan\Rules\RuleErrorBuilder; -use PHPStan\Type\Constant\ConstantStringType; use function in_array; use function sprintf; use function strtolower; @@ -84,11 +83,9 @@ private function extractPatterns(StaticCall $staticCall, Scope $scope): array } foreach ($constantArrayType->getKeyTypes() as $arrayKeyType) { - if (!$arrayKeyType instanceof ConstantStringType) { - continue; + foreach ($arrayKeyType->getConstantStrings() as $constantString) { + $patternStrings[] = $constantString->getValue(); } - - $patternStrings[] = $arrayKeyType->getValue(); } } diff --git a/src/Type/Nette/ComponentModelArrayAccessDynamicReturnTypeExtension.php b/src/Type/Nette/ComponentModelArrayAccessDynamicReturnTypeExtension.php index b6fb610..c9b2ee3 100644 --- a/src/Type/Nette/ComponentModelArrayAccessDynamicReturnTypeExtension.php +++ b/src/Type/Nette/ComponentModelArrayAccessDynamicReturnTypeExtension.php @@ -6,10 +6,10 @@ use PHPStan\Analyser\Scope; use PHPStan\Reflection\MethodReflection; use PHPStan\Reflection\ParametersAcceptorSelector; -use PHPStan\Type\Constant\ConstantStringType; use PHPStan\Type\DynamicMethodReturnTypeExtension; use PHPStan\Type\MixedType; use PHPStan\Type\Type; +use PHPStan\Type\TypeCombinator; use function count; use function sprintf; use function ucfirst; @@ -43,20 +43,25 @@ public function getTypeFromMethodCall( } $argType = $scope->getType($args[0]->value); - if (!$argType instanceof ConstantStringType) { + if (count($argType->getConstantStrings()) === 0) { return $mixedType; } - $componentName = $argType->getValue(); + $types = []; + foreach ($argType->getConstantStrings() as $constantString) { + $componentName = $constantString->getValue(); - $methodName = sprintf('createComponent%s', ucfirst($componentName)); - if (!$calledOnType->hasMethod($methodName)->yes()) { - return $mixedType; - } + $methodName = sprintf('createComponent%s', ucfirst($componentName)); + if (!$calledOnType->hasMethod($methodName)->yes()) { + return $mixedType; + } - $method = $calledOnType->getMethod($methodName, $scope); + $method = $calledOnType->getMethod($methodName, $scope); + + $types[] = ParametersAcceptorSelector::selectSingle($method->getVariants())->getReturnType(); + } - return ParametersAcceptorSelector::selectSingle($method->getVariants())->getReturnType(); + return TypeCombinator::union(...$types); } } diff --git a/src/Type/Nette/ComponentModelDynamicReturnTypeExtension.php b/src/Type/Nette/ComponentModelDynamicReturnTypeExtension.php index 691dc97..86b1176 100644 --- a/src/Type/Nette/ComponentModelDynamicReturnTypeExtension.php +++ b/src/Type/Nette/ComponentModelDynamicReturnTypeExtension.php @@ -6,10 +6,10 @@ use PHPStan\Analyser\Scope; use PHPStan\Reflection\MethodReflection; use PHPStan\Reflection\ParametersAcceptorSelector; -use PHPStan\Type\Constant\ConstantStringType; use PHPStan\Type\DynamicMethodReturnTypeExtension; use PHPStan\Type\MixedType; use PHPStan\Type\Type; +use PHPStan\Type\TypeCombinator; use function count; use function sprintf; use function ucfirst; @@ -43,20 +43,25 @@ public function getTypeFromMethodCall( } $argType = $scope->getType($args[0]->value); - if (!$argType instanceof ConstantStringType) { + if (count($argType->getConstantStrings()) === 0) { return $mixedType; } - $componentName = $argType->getValue(); + $types = []; + foreach ($argType->getConstantStrings() as $constantString) { + $componentName = $constantString->getValue(); - $methodName = sprintf('createComponent%s', ucfirst($componentName)); - if (!$calledOnType->hasMethod($methodName)->yes()) { - return $mixedType; - } + $methodName = sprintf('createComponent%s', ucfirst($componentName)); + if (!$calledOnType->hasMethod($methodName)->yes()) { + return $mixedType; + } - $method = $calledOnType->getMethod($methodName, $scope); + $method = $calledOnType->getMethod($methodName, $scope); + + $types[] = ParametersAcceptorSelector::selectSingle($method->getVariants())->getReturnType(); + } - return ParametersAcceptorSelector::selectSingle($method->getVariants())->getReturnType(); + return TypeCombinator::union(...$types); } } diff --git a/src/Type/Nette/FormContainerUnsafeValuesDynamicReturnTypeExtension.php b/src/Type/Nette/FormContainerUnsafeValuesDynamicReturnTypeExtension.php index 8ba79a9..6ddb557 100644 --- a/src/Type/Nette/FormContainerUnsafeValuesDynamicReturnTypeExtension.php +++ b/src/Type/Nette/FormContainerUnsafeValuesDynamicReturnTypeExtension.php @@ -7,10 +7,8 @@ use PHPStan\Reflection\MethodReflection; use PHPStan\Reflection\ParametersAcceptorSelector; use PHPStan\Type\ArrayType; -use PHPStan\Type\Constant\ConstantStringType; use PHPStan\Type\DynamicMethodReturnTypeExtension; use PHPStan\Type\MixedType; -use PHPStan\Type\NullType; use PHPStan\Type\ObjectType; use PHPStan\Type\StringType; use PHPStan\Type\Type; @@ -37,11 +35,11 @@ public function getTypeFromMethodCall(MethodReflection $methodReflection, Method $arg = $methodCall->getArgs()[0]->value; $scopedType = $scope->getType($arg); - if ($scopedType instanceof NullType) { + if ($scopedType->isNull()->yes()) { return new ObjectType('Nette\Utils\ArrayHash'); } - if ($scopedType instanceof ConstantStringType && $scopedType->getValue() === 'array') { + if (count($scopedType->getConstantStrings()) === 1 && $scopedType->getConstantStrings()[0]->getValue() === 'array') { return new ArrayType(new StringType(), new MixedType()); } diff --git a/src/Type/Nette/PresenterGetSessionReturnTypeExtension.php b/src/Type/Nette/PresenterGetSessionReturnTypeExtension.php index 2101a73..b001cee 100644 --- a/src/Type/Nette/PresenterGetSessionReturnTypeExtension.php +++ b/src/Type/Nette/PresenterGetSessionReturnTypeExtension.php @@ -6,7 +6,6 @@ use PHPStan\Analyser\Scope; use PHPStan\Reflection\MethodReflection; use PHPStan\Type\DynamicMethodReturnTypeExtension; -use PHPStan\Type\NullType; use PHPStan\Type\ObjectType; use PHPStan\Type\Type; use function count; @@ -26,7 +25,7 @@ public function isMethodSupported(MethodReflection $methodReflection): bool public function getTypeFromMethodCall(MethodReflection $methodReflection, MethodCall $methodCall, Scope $scope): Type { - if (count($methodCall->getArgs()) === 0 || $scope->getType($methodCall->getArgs()[0]->value) instanceof NullType) { + if (count($methodCall->getArgs()) === 0 || $scope->getType($methodCall->getArgs()[0]->value)->isNull()->yes()) { return new ObjectType('Nette\Http\Session'); } diff --git a/src/Type/Nette/ServiceLocatorDynamicReturnTypeExtension.php b/src/Type/Nette/ServiceLocatorDynamicReturnTypeExtension.php index c201623..84c0449 100644 --- a/src/Type/Nette/ServiceLocatorDynamicReturnTypeExtension.php +++ b/src/Type/Nette/ServiceLocatorDynamicReturnTypeExtension.php @@ -6,7 +6,6 @@ use PHPStan\Analyser\Scope; use PHPStan\Reflection\MethodReflection; use PHPStan\Type\Constant\ConstantBooleanType; -use PHPStan\Type\Constant\ConstantStringType; use PHPStan\Type\DynamicMethodReturnTypeExtension; use PHPStan\Type\MixedType; use PHPStan\Type\ObjectType; @@ -46,25 +45,30 @@ public function getTypeFromMethodCall(MethodReflection $methodReflection, Method return $mixedType; } $argType = $scope->getType($methodCall->getArgs()[0]->value); - if (!$argType instanceof ConstantStringType) { + if (count($argType->getConstantStrings()) === 0) { return $mixedType; } - $type = new ObjectType($argType->getValue()); - if ( - $methodReflection->getName() === 'getByType' - && count($methodCall->getArgs()) >= 2 - ) { - $throwType = $scope->getType($methodCall->getArgs()[1]->value); + $types = []; + foreach ($argType->getConstantStrings() as $constantString) { + $type = new ObjectType($constantString->getValue()); if ( - !$throwType instanceof ConstantBooleanType - || !$throwType->getValue() + $methodReflection->getName() === 'getByType' + && count($methodCall->getArgs()) >= 2 ) { - $type = TypeCombinator::addNull($type); + $throwType = $scope->getType($methodCall->getArgs()[1]->value); + if ( + !$throwType instanceof ConstantBooleanType + || !$throwType->getValue() + ) { + $type = TypeCombinator::addNull($type); + } } + + $types[] = $type; } - return $type; + return TypeCombinator::union(...$types); } }