@@ -91,7 +91,7 @@ public function checkProperty(
9191
9292 if (!$ phpDocPropertyType instanceof MixedType || $ phpDocPropertyType ->isExplicitMixed ()) {
9393 $ phpDocPropertyType = TypeUtils::resolveLateResolvableTypes (TypehintHelper::decideType ($ nativePropertyType , $ phpDocPropertyType ));
94- $ narrowedPhpDocType = $ this ->narrowType ($ phpDocPropertyType , $ assignedType , $ scope , false );
94+ $ narrowedPhpDocType = $ this ->narrowType ($ phpDocPropertyType , $ assignedType , $ scope , false , false );
9595 if (!$ narrowedPhpDocType ->equals ($ phpDocPropertyType )) {
9696 $ phpDocPropertyTypeDescription = $ phpDocPropertyType ->describe (VerbosityLevel::getRecommendedLevelByType ($ phpDocPropertyType ));
9797 return $ this ->createErrors (
@@ -110,7 +110,7 @@ public function checkProperty(
110110 }
111111
112112 $ narrowedPhpDocType = SimultaneousTypeTraverser::map ($ phpDocPropertyType , $ assignedType , function (Type $ declaredType , Type $ actualType , callable $ traverse ) use ($ scope ) {
113- $ narrowed = $ this ->narrowType ($ declaredType , $ actualType , $ scope , false );
113+ $ narrowed = $ this ->narrowType ($ declaredType , $ actualType , $ scope , false , false );
114114 if (!$ narrowed ->equals ($ declaredType )) {
115115 return $ narrowed ;
116116 }
@@ -132,7 +132,7 @@ public function checkProperty(
132132 ];
133133 }
134134
135- $ narrowedNativeType = $ this ->narrowType ($ nativePropertyType , $ assignedType , $ scope , true );
135+ $ narrowedNativeType = $ this ->narrowType ($ nativePropertyType , $ assignedType , $ scope , false , true );
136136 if (!$ narrowedNativeType ->equals ($ nativePropertyType )) {
137137 $ propertyTypeDescription = $ nativePropertyType ->describe (VerbosityLevel::getRecommendedLevelByType ($ nativePropertyType ));
138138 return $ this ->createErrors (
@@ -213,7 +213,7 @@ public function checkFunctionReturnType(
213213 if (!$ phpDocFunctionReturnType instanceof MixedType || $ phpDocFunctionReturnType ->isExplicitMixed ()) {
214214 $ phpDocFunctionReturnType = TypeUtils::resolveLateResolvableTypes (TypehintHelper::decideType ($ nativeFunctionReturnType , $ phpDocFunctionReturnType ));
215215
216- $ narrowedPhpDocType = $ this ->narrowType ($ phpDocFunctionReturnType , $ returnType , $ scope , false );
216+ $ narrowedPhpDocType = $ this ->narrowType ($ phpDocFunctionReturnType , $ returnType , $ scope , false , false );
217217 if (!$ narrowedPhpDocType ->equals ($ phpDocFunctionReturnType )) {
218218 return $ this ->createErrors (
219219 $ narrowedPhpDocType ,
@@ -230,8 +230,8 @@ public function checkFunctionReturnType(
230230 return [];
231231 }
232232
233- $ narrowedPhpDocType = SimultaneousTypeTraverser::map ($ phpDocFunctionReturnType , $ returnType , function (Type $ declaredType , Type $ actualReturnType , callable $ traverse ) use ($ scope ) {
234- $ narrowed = $ this ->narrowType ($ declaredType , $ actualReturnType , $ scope , false );
233+ $ narrowedPhpDocType = SimultaneousTypeTraverser::map ($ phpDocFunctionReturnType , $ returnType , function (Type $ declaredType , Type $ actualReturnType , callable $ traverse ) use ($ scope, $ checkDescendantClass ) {
234+ $ narrowed = $ this ->narrowType ($ declaredType , $ actualReturnType , $ scope , $ checkDescendantClass , false );
235235 if (!$ narrowed ->equals ($ declaredType )) {
236236 return $ narrowed ;
237237 }
@@ -253,7 +253,7 @@ public function checkFunctionReturnType(
253253 ];
254254 }
255255
256- $ narrowedNativeType = $ this ->narrowType ($ nativeFunctionReturnType , $ returnType , $ scope , true );
256+ $ narrowedNativeType = $ this ->narrowType ($ nativeFunctionReturnType , $ returnType , $ scope , false , true );
257257 if (!$ narrowedNativeType ->equals ($ nativeFunctionReturnType )) {
258258 return $ this ->createErrors (
259259 $ narrowedNativeType ,
@@ -286,14 +286,14 @@ public function checkParameterOutType(
286286 ): array
287287 {
288288 $ parameterOutType = TypeUtils::resolveLateResolvableTypes ($ parameterOutType );
289- $ narrowedType = $ this ->narrowType ($ parameterOutType , $ actualVariableType , $ scope , false );
289+ $ narrowedType = $ this ->narrowType ($ parameterOutType , $ actualVariableType , $ scope , false , false );
290290 if ($ narrowedType ->equals ($ parameterOutType )) {
291291 if (!$ this ->reportTooWideBool ) {
292292 return [];
293293 }
294294
295295 $ narrowedType = SimultaneousTypeTraverser::map ($ parameterOutType , $ actualVariableType , function (Type $ declaredType , Type $ actualType , callable $ traverse ) use ($ scope ) {
296- $ narrowed = $ this ->narrowType ($ declaredType , $ actualType , $ scope , false );
296+ $ narrowed = $ this ->narrowType ($ declaredType , $ actualType , $ scope , false , false );
297297 if (!$ narrowed ->equals ($ declaredType )) {
298298 return $ narrowed ;
299299 }
@@ -408,6 +408,7 @@ private function narrowType(
408408 Type $ declaredType ,
409409 Type $ actualReturnType ,
410410 Scope $ scope ,
411+ bool $ checkDescendantClass ,
411412 bool $ native ,
412413 ): Type
413414 {
@@ -421,7 +422,20 @@ private function narrowType(
421422 $ usedTypes = [];
422423 foreach ($ declaredType ->getTypes () as $ innerType ) {
423424 if ($ innerType ->isSuperTypeOf ($ actualReturnType )->no ()) {
424- continue ;
425+ if (!$ checkDescendantClass ) {
426+ continue ;
427+ }
428+ if ($ innerType ->isNull ()->yes ()) {
429+ $ usedTypes [] = $ innerType ;
430+ continue ;
431+ }
432+ if (
433+ !$ actualReturnType ->isTrue ()->yes ()
434+ && !$ actualReturnType ->isFalse ()->yes ()
435+ && !$ actualReturnType ->isNull ()->yes ()
436+ ) {
437+ continue ;
438+ }
425439 }
426440
427441 $ usedTypes [] = $ innerType ;
0 commit comments