Search in sources :

Example 1 with OpenapiTypesUtil

use of com.kalessil.phpStorm.phpInspectionsEA.utils.OpenapiTypesUtil in project phpinspectionsea by kalessil.

the class SummerTimeUnsafeTimeManipulationInspector method buildVisitor.

@Override
@NotNull
public PsiElementVisitor buildVisitor(@NotNull final ProblemsHolder holder, boolean isOnTheFly) {
    return new BasePhpElementVisitor() {

        @Override
        public void visitPhpBinaryExpression(@NotNull BinaryExpression expression) {
            if (targetOperations.contains(expression.getOperationType())) {
                final PsiElement left = expression.getLeftOperand();
                final PsiElement right = expression.getRightOperand();
                if (right != null && this.isTargetMagicNumber(right) && this.isTargetContext(right)) {
                    if (!this.isTestContext(expression)) {
                        holder.registerProblem(expression, message);
                    }
                } else if (left != null && this.isTargetMagicNumber(left) && this.isTargetContext(left)) {
                    if (!this.isTestContext(expression)) {
                        holder.registerProblem(expression, message);
                    }
                }
            }
        }

        @Override
        public void visitPhpSelfAssignmentExpression(@NotNull SelfAssignmentExpression expression) {
            if (targetAssignments.contains(expression.getOperationType())) {
                final PsiElement value = expression.getValue();
                if (value != null && this.isTargetMagicNumber(value) && !this.isTestContext(expression)) {
                    holder.registerProblem(expression, message);
                }
            }
        }

        private boolean isTargetContext(@NotNull PsiElement magicNumber) {
            boolean result = magicNumber.textMatches("86400");
            if (!result) {
                PsiElement expression = magicNumber.getParent();
                while (expression instanceof ParenthesizedExpression || expression instanceof BinaryExpression) {
                    expression = expression.getParent();
                }
                result = PsiTreeUtil.findChildrenOfType(expression, PhpExpression.class).stream().filter(OpenapiTypesUtil::isNumber).anyMatch(candidate -> {
                    final String text = candidate.getText();
                    return text.equals("60") || text.endsWith("3600");
                });
            }
            return result;
        }

        private boolean isTargetMagicNumber(@NotNull PsiElement candidate) {
            boolean result = false;
            if (OpenapiTypesUtil.isNumber(candidate)) {
                result = candidate.textMatches("24") || candidate.textMatches("86400");
            }
            return result;
        }
    };
}
Also used : SelfAssignmentExpression(com.jetbrains.php.lang.psi.elements.SelfAssignmentExpression) ParenthesizedExpression(com.jetbrains.php.lang.psi.elements.ParenthesizedExpression) BasePhpInspection(com.kalessil.phpStorm.phpInspectionsEA.openApi.BasePhpInspection) IElementType(com.intellij.psi.tree.IElementType) PhpTokenTypes(com.jetbrains.php.lang.lexer.PhpTokenTypes) Set(java.util.Set) SelfAssignmentExpression(com.jetbrains.php.lang.psi.elements.SelfAssignmentExpression) HashSet(java.util.HashSet) PsiTreeUtil(com.intellij.psi.util.PsiTreeUtil) ParenthesizedExpression(com.jetbrains.php.lang.psi.elements.ParenthesizedExpression) BasePhpElementVisitor(com.kalessil.phpStorm.phpInspectionsEA.openApi.BasePhpElementVisitor) OpenapiTypesUtil(com.kalessil.phpStorm.phpInspectionsEA.utils.OpenapiTypesUtil) BinaryExpression(com.jetbrains.php.lang.psi.elements.BinaryExpression) PhpExpression(com.jetbrains.php.lang.psi.elements.PhpExpression) PsiElement(com.intellij.psi.PsiElement) NotNull(org.jetbrains.annotations.NotNull) PsiElementVisitor(com.intellij.psi.PsiElementVisitor) ProblemsHolder(com.intellij.codeInspection.ProblemsHolder) BasePhpElementVisitor(com.kalessil.phpStorm.phpInspectionsEA.openApi.BasePhpElementVisitor) BinaryExpression(com.jetbrains.php.lang.psi.elements.BinaryExpression) OpenapiTypesUtil(com.kalessil.phpStorm.phpInspectionsEA.utils.OpenapiTypesUtil) NotNull(org.jetbrains.annotations.NotNull) PsiElement(com.intellij.psi.PsiElement) NotNull(org.jetbrains.annotations.NotNull)

Example 2 with OpenapiTypesUtil

use of com.kalessil.phpStorm.phpInspectionsEA.utils.OpenapiTypesUtil in project phpinspectionsea by kalessil.

the class SlowArrayOperationsInLoopInspector method buildVisitor.

@Override
@NotNull
public PsiElementVisitor buildVisitor(@NotNull final ProblemsHolder holder, boolean isOnTheFly) {
    return new BasePhpElementVisitor() {

        @Override
        public void visitPhpFunctionCall(@NotNull FunctionReference reference) {
            final String functionName = reference.getName();
            if (functionName != null && greedyFunctions.contains(functionName)) {
                final PsiElement[] arguments = reference.getParameters();
                if (arguments.length > 1 && !(arguments[0] instanceof ArrayAccessExpression)) {
                    PsiElement parent = reference.getParent();
                    if (parent instanceof AssignmentExpression) {
                        /* false-positives: return/break as last group statement expression */
                        boolean canLoop = true;
                        if (OpenapiTypesUtil.isStatementImpl(parent = parent.getParent())) {
                            final PsiElement grandParent = parent.getParent();
                            if (grandParent instanceof GroupStatement) {
                                final PsiElement last = ExpressionSemanticUtil.getLastStatement((GroupStatement) grandParent);
                                canLoop = !(last instanceof PhpBreak) && !(last instanceof PhpReturn);
                            }
                        }
                        while (canLoop && parent != null && !(parent instanceof PhpFile) && !(parent instanceof Function)) {
                            if (OpenapiTypesUtil.isLoop(parent)) {
                                final PsiElement container = ((AssignmentExpression) reference.getParent()).getVariable();
                                if (container != null) {
                                    for (final PsiElement argument : arguments) {
                                        if (OpenapiEquivalenceUtil.areEqual(container, argument)) {
                                            holder.registerProblem(reference, String.format(MessagesPresentationUtil.prefixWithEa(messageGreedyPattern), functionName));
                                            return;
                                        }
                                    }
                                }
                            }
                            parent = parent.getParent();
                        }
                    }
                }
            }
        }

        @Override
        public void visitPhpFor(@NotNull For forStatement) {
            final Set<FunctionReference> references = new HashSet<>();
            Arrays.stream(forStatement.getConditionalExpressions()).forEach(c -> {
                if (c instanceof BinaryExpression) {
                    final BinaryExpression binary = (BinaryExpression) c;
                    Stream.of(binary.getLeftOperand(), binary.getRightOperand()).filter(p -> p instanceof FunctionReference).forEach(p -> references.add((FunctionReference) p));
                }
            });
            references.stream().filter(OpenapiTypesUtil::isFunctionReference).forEach(r -> {
                final String functionName = r.getName();
                if (functionName != null && slowFunctions.contains(functionName)) {
                    final BinaryExpression condition = (BinaryExpression) r.getParent();
                    holder.registerProblem(condition, String.format(MessagesPresentationUtil.prefixWithEa(messageSlowPattern), functionName), ProblemHighlightType.GENERIC_ERROR, new ReduceRepetitiveCallsInForFix(holder.getProject(), forStatement, condition));
                }
            });
            references.clear();
        }
    };
}
Also used : Arrays(java.util.Arrays) com.jetbrains.php.lang.psi.elements(com.jetbrains.php.lang.psi.elements) PhpTokenTypes(com.jetbrains.php.lang.lexer.PhpTokenTypes) HashSet(java.util.HashSet) PsiTreeUtil(com.intellij.psi.util.PsiTreeUtil) OpenapiTypesUtil(com.kalessil.phpStorm.phpInspectionsEA.utils.OpenapiTypesUtil) ProblemDescriptor(com.intellij.codeInspection.ProblemDescriptor) MessagesPresentationUtil(com.kalessil.phpStorm.phpInspectionsEA.utils.MessagesPresentationUtil) OpenapiEquivalenceUtil(com.kalessil.phpStorm.phpInspectionsEA.utils.OpenapiEquivalenceUtil) PsiElement(com.intellij.psi.PsiElement) Project(com.intellij.openapi.project.Project) LocalQuickFix(com.intellij.codeInspection.LocalQuickFix) PsiElementVisitor(com.intellij.psi.PsiElementVisitor) ProblemsHolder(com.intellij.codeInspection.ProblemsHolder) PhpPsiElementFactory(com.jetbrains.php.lang.psi.PhpPsiElementFactory) BasePhpInspection(com.kalessil.phpStorm.phpInspectionsEA.openApi.BasePhpInspection) ExpressionSemanticUtil(com.kalessil.phpStorm.phpInspectionsEA.utils.ExpressionSemanticUtil) LeafPsiElement(com.intellij.psi.impl.source.tree.LeafPsiElement) Set(java.util.Set) SmartPointerManager(com.intellij.psi.SmartPointerManager) BasePhpElementVisitor(com.kalessil.phpStorm.phpInspectionsEA.openApi.BasePhpElementVisitor) Stream(java.util.stream.Stream) PhpFile(com.jetbrains.php.lang.psi.PhpFile) SmartPsiElementPointer(com.intellij.psi.SmartPsiElementPointer) ProblemHighlightType(com.intellij.codeInspection.ProblemHighlightType) NotNull(org.jetbrains.annotations.NotNull) PhpFile(com.jetbrains.php.lang.psi.PhpFile) NotNull(org.jetbrains.annotations.NotNull) BasePhpElementVisitor(com.kalessil.phpStorm.phpInspectionsEA.openApi.BasePhpElementVisitor) PsiElement(com.intellij.psi.PsiElement) LeafPsiElement(com.intellij.psi.impl.source.tree.LeafPsiElement) HashSet(java.util.HashSet) NotNull(org.jetbrains.annotations.NotNull)

Aggregations

ProblemsHolder (com.intellij.codeInspection.ProblemsHolder)2 PsiElement (com.intellij.psi.PsiElement)2 PsiElementVisitor (com.intellij.psi.PsiElementVisitor)2 PsiTreeUtil (com.intellij.psi.util.PsiTreeUtil)2 PhpTokenTypes (com.jetbrains.php.lang.lexer.PhpTokenTypes)2 BasePhpElementVisitor (com.kalessil.phpStorm.phpInspectionsEA.openApi.BasePhpElementVisitor)2 BasePhpInspection (com.kalessil.phpStorm.phpInspectionsEA.openApi.BasePhpInspection)2 OpenapiTypesUtil (com.kalessil.phpStorm.phpInspectionsEA.utils.OpenapiTypesUtil)2 HashSet (java.util.HashSet)2 Set (java.util.Set)2 NotNull (org.jetbrains.annotations.NotNull)2 LocalQuickFix (com.intellij.codeInspection.LocalQuickFix)1 ProblemDescriptor (com.intellij.codeInspection.ProblemDescriptor)1 ProblemHighlightType (com.intellij.codeInspection.ProblemHighlightType)1 Project (com.intellij.openapi.project.Project)1 SmartPointerManager (com.intellij.psi.SmartPointerManager)1 SmartPsiElementPointer (com.intellij.psi.SmartPsiElementPointer)1 LeafPsiElement (com.intellij.psi.impl.source.tree.LeafPsiElement)1 IElementType (com.intellij.psi.tree.IElementType)1 PhpFile (com.jetbrains.php.lang.psi.PhpFile)1