44
55use PhpParser \Node ;
66use PhpParser \Node \Expr ;
7+ use PHPStan \Analyser \CollectedDataEmitter ;
8+ use PHPStan \Analyser \NodeCallbackInvoker ;
79use PHPStan \Analyser \Scope ;
810use PHPStan \DependencyInjection \AutowiredParameter ;
911use PHPStan \DependencyInjection \AutowiredService ;
1012use PHPStan \Node \Expr \PropertyInitializationExpr ;
13+ use PHPStan \Rules \Comparison \ConstantConditionInTraitHelper ;
1114use PHPStan \Rules \Properties \PropertyDescriptor ;
1215use PHPStan \Rules \Properties \PropertyReflectionFinder ;
1316use PHPStan \Type \NeverType ;
@@ -27,6 +30,7 @@ final class IssetCheck
2730 public function __construct (
2831 private PropertyDescriptor $ propertyDescriptor ,
2932 private PropertyReflectionFinder $ propertyReflectionFinder ,
33+ private ConstantConditionInTraitHelper $ constantConditionInTraitHelper ,
3034 #[AutowiredParameter]
3135 private bool $ checkAdvancedIsset ,
3236 #[AutowiredParameter]
@@ -36,10 +40,11 @@ public function __construct(
3640 }
3741
3842 /**
43+ * @param class-string<Rule<covariant Node>> $ruleName
3944 * @param ErrorIdentifier $identifier
4045 * @param callable(Type): ?string $typeMessageCallback
4146 */
42- public function check (Expr $ expr , Scope $ scope , string $ operatorDescription , string $ identifier , callable $ typeMessageCallback , ?IdentifierRuleError $ error = null ): ?IdentifierRuleError
47+ public function check (Expr $ expr , Scope & NodeCallbackInvoker & CollectedDataEmitter $ scope , string $ operatorDescription , string $ identifier , callable $ typeMessageCallback, string $ ruleName , Expr $ originalExpr , ?IdentifierRuleError $ error = null ): ?IdentifierRuleError
4348 {
4449 // mirrored in PHPStan\Analyser\MutatingScope::issetCheck()
4550 if ($ expr instanceof Node \Expr \Variable && is_string ($ expr ->name )) {
@@ -114,7 +119,7 @@ public function check(Expr $expr, Scope $scope, string $operatorDescription, str
114119 ), $ typeMessageCallback , $ identifier , 'offset ' );
115120
116121 if ($ error !== null ) {
117- return $ this ->check ($ expr ->var , $ scope , $ operatorDescription , $ identifier , $ typeMessageCallback , $ error );
122+ return $ this ->check ($ expr ->var , $ scope , $ operatorDescription , $ identifier , $ typeMessageCallback , $ ruleName , $ originalExpr , $ error );
118123 }
119124 }
120125
@@ -220,11 +225,11 @@ static function (Type $type) use ($typeMessageCallback): ?string {
220225
221226 if ($ error !== null ) {
222227 if ($ expr instanceof Node \Expr \PropertyFetch) {
223- return $ this ->check ($ expr ->var , $ scope , $ operatorDescription , $ identifier , $ typeMessageCallback , $ error );
228+ return $ this ->check ($ expr ->var , $ scope , $ operatorDescription , $ identifier , $ typeMessageCallback , $ ruleName , $ originalExpr , $ error );
224229 }
225230
226231 if ($ expr ->class instanceof Expr) {
227- return $ this ->check ($ expr ->class , $ scope , $ operatorDescription , $ identifier , $ typeMessageCallback , $ error );
232+ return $ this ->check ($ expr ->class , $ scope , $ operatorDescription , $ identifier , $ typeMessageCallback , $ ruleName , $ originalExpr , $ error );
228233 }
229234 }
230235
@@ -265,6 +270,27 @@ static function (Type $type) use ($typeMessageCallback): ?string {
265270 return null ;
266271 }
267272
273+ /**
274+ * @param class-string<Rule<covariant Node>> $ruleName
275+ * @param ErrorIdentifier $identifier
276+ * @param callable(Type): ?string $typeMessageCallback
277+ */
278+ public function checkWithTraitHandling (Expr $ expr , Scope &NodeCallbackInvoker &CollectedDataEmitter $ scope , string $ operatorDescription , string $ identifier , callable $ typeMessageCallback , string $ ruleName ): ?IdentifierRuleError
279+ {
280+ $ error = $ this ->check ($ expr , $ scope , $ operatorDescription , $ identifier , $ typeMessageCallback , $ ruleName , $ expr );
281+
282+ if ($ scope ->isInTrait ()) {
283+ if ($ error !== null ) {
284+ $ this ->constantConditionInTraitHelper ->emitError ($ ruleName , $ scope , $ expr , true , $ error );
285+ return null ;
286+ }
287+ $ this ->constantConditionInTraitHelper ->emitNoError ($ ruleName , $ scope , $ expr );
288+ return null ;
289+ }
290+
291+ return $ error ;
292+ }
293+
268294 /**
269295 * @param ErrorIdentifier $identifier
270296 */
0 commit comments