betterNodeFinder = $betterNodeFinder; $this->exprAnalyzer = $exprAnalyzer; $this->reflectionResolver = $reflectionResolver; $this->nodeTypeResolver = $nodeTypeResolver; } /** * @param \PhpParser\Node\Expr\BinaryOp\BooleanAnd|\PhpParser\Node\Expr\BinaryOp\BooleanOr $booleanAnd */ public function isSafe($booleanAnd) : bool { $hasNonTypedFromParam = (bool) $this->betterNodeFinder->findFirst($booleanAnd->left, function (Node $node) : bool { return $node instanceof Variable && $this->exprAnalyzer->isNonTypedFromParam($node); }); if ($hasNonTypedFromParam) { return \false; } $hasPropertyFetchOrArrayDimFetch = (bool) $this->betterNodeFinder->findFirst($booleanAnd->left, static function (Node $node) : bool { return $node instanceof PropertyFetch || $node instanceof StaticPropertyFetch || $node instanceof ArrayDimFetch; }); // get type from Property and ArrayDimFetch is unreliable if ($hasPropertyFetchOrArrayDimFetch) { return \false; } // skip trait this $classReflection = $this->reflectionResolver->resolveClassReflection($booleanAnd); if ($classReflection instanceof ClassReflection && $classReflection->isTrait()) { return !(bool) $this->betterNodeFinder->findFirst($booleanAnd->left, function (Node $node) : bool { return $this->nodeTypeResolver->getType($node) instanceof ObjectType; }); } return \true; } }