diff --git a/src/Type/Php/ReplaceFunctionsDynamicReturnTypeExtension.php b/src/Type/Php/ReplaceFunctionsDynamicReturnTypeExtension.php index 0c527c1a5c1..401200f4c5a 100644 --- a/src/Type/Php/ReplaceFunctionsDynamicReturnTypeExtension.php +++ b/src/Type/Php/ReplaceFunctionsDynamicReturnTypeExtension.php @@ -7,6 +7,7 @@ use PHPStan\Reflection\FunctionReflection; use PHPStan\Reflection\ParametersAcceptorSelector; use PHPStan\Type\Accessory\AccessoryNonEmptyStringType; +use PHPStan\Type\Accessory\AccessoryNonFalsyStringType; use PHPStan\Type\ArrayType; use PHPStan\Type\DynamicFunctionReturnTypeExtension; use PHPStan\Type\IntersectionType; @@ -84,6 +85,9 @@ private function getPreliminarilyResolvedTypeFromFunctionCall( if (count($functionCall->getArgs()) > $replaceArgumentPosition) { $replaceArgumentType = $scope->getType($functionCall->getArgs()[$replaceArgumentPosition]->value); + if ($replaceArgumentType->isNonFalsyString()->yes()) { + return new IntersectionType([new StringType(), new AccessoryNonFalsyStringType()]); + } if ($replaceArgumentType->isNonEmptyString()->yes()) { return new IntersectionType([new StringType(), new AccessoryNonEmptyStringType()]); } diff --git a/tests/PHPStan/Analyser/LegacyNodeScopeResolverTest.php b/tests/PHPStan/Analyser/LegacyNodeScopeResolverTest.php index cdc6492de97..b88b4f0fcd2 100644 --- a/tests/PHPStan/Analyser/LegacyNodeScopeResolverTest.php +++ b/tests/PHPStan/Analyser/LegacyNodeScopeResolverTest.php @@ -7344,7 +7344,7 @@ public function dataReplaceFunctions(): array { return [ [ - 'non-empty-string', + 'non-falsy-string', '$expectedString', ], [ @@ -7352,7 +7352,7 @@ public function dataReplaceFunctions(): array '$expectedString2', ], [ - 'non-empty-string|null', + 'non-falsy-string|null', '$anotherExpectedString', ], [