diff --git a/src/main/java/com/intellij/plugins/bodhi/pmd/core/UselessSuppressionsHelper.java b/src/main/java/com/intellij/plugins/bodhi/pmd/core/UselessSuppressionsHelper.java index 23e6c8c..6ae8182 100644 --- a/src/main/java/com/intellij/plugins/bodhi/pmd/core/UselessSuppressionsHelper.java +++ b/src/main/java/com/intellij/plugins/bodhi/pmd/core/UselessSuppressionsHelper.java @@ -23,8 +23,6 @@ import java.util.List; import java.util.Map; import java.util.Set; -import java.util.regex.Matcher; -import java.util.regex.Pattern; import static net.sourceforge.pmd.reporting.RuleViolation.*; @@ -36,9 +34,6 @@ * @author jborgers */ public class UselessSuppressionsHelper { - static final Pattern NEXT_METHOD_NAME_PATTERN = Pattern.compile("\\R*^\\s*[\\w\\s<>]+\\s+(\\w+)\\("); - static final Pattern NEXT_FIELD_NAME_PATTERN = Pattern.compile("\\R*\\s*[\\w\\s<>,?]+\\s+(\\w+)\\s*[=;]"); - static final Pattern COMMENT_PATTERN = Pattern.compile("(//.*|/\\*(?s:.)*?\\*/)"); // Matches single-line and multi-line comments static final String NO_METHOD = ""; final Map> classMethodToRuleNameOfSuppressedViolationsMap = new HashMap<>(); final Map> classMethodToRuleNameOfViolationsMap = new HashMap<>(); @@ -57,9 +52,10 @@ public class UselessSuppressionsHelper { void storeRuleNameForMethod(Report.SuppressedViolation suppressed) { RuleViolation violation = suppressed.getRuleViolation(); - var packageName = violation.getAdditionalInfo().get(PACKAGE_NAME); - var className = violation.getAdditionalInfo().get(CLASS_NAME); - var methodName = violation.getAdditionalInfo().get(METHOD_NAME); + Map addInfo = violation.getAdditionalInfo(); + var packageName = addInfo.get(PACKAGE_NAME); + var className = addInfo.get(CLASS_NAME); + var methodName = addInfo.get(METHOD_NAME); if (methodName != null && !methodName.isEmpty()) { // store for method String methodKey = packageName + "-" + className + "-" + methodName; @@ -81,9 +77,10 @@ void storeRuleNameForMethod(Report.SuppressedViolation suppressed) { } void storeRuleNameForMethod(RuleViolation violation) { - var packageName = violation.getAdditionalInfo().get(PACKAGE_NAME); - var className = violation.getAdditionalInfo().get(CLASS_NAME); - var methodName = violation.getAdditionalInfo().get(METHOD_NAME); + Map addInfo = violation.getAdditionalInfo(); + var packageName = addInfo.get(PACKAGE_NAME); + var className = addInfo.get(CLASS_NAME); + var methodName = addInfo.get(METHOD_NAME); if (methodName != null && !methodName.isEmpty()) { // store for method @@ -188,14 +185,11 @@ ViolatingAnnotationHolder getAnnotationContext(PMDViolation annotationViolation) if (doc != null) { int startOffset = doc.getLineStartOffset(annotationViolation.getBeginLine() - 1) + annotationViolation.getBeginColumn(); int endOffset = doc.getLineStartOffset(annotationViolation.getEndLine() - 1) + annotationViolation.getEndColumn() - 1; - String violatingAnnotation = doc.getText(new TextRange(startOffset, endOffset)); - String methodName; - if (!annotationViolation.getMethodName().isEmpty()) { // an annotation inside a method - methodName = annotationViolation.getMethodName(); - } else { - int startAfter = doc.getLineStartOffset(annotationViolation.getEndLine()); - String after = doc.getText(new TextRange(startAfter, doc.getTextLength() - 1)); - methodName = findMethodName(after); + String violatingAnnotation = doc.getText(new TextRange(startOffset, endOffset - 1)); // -1 to remove the quote (") + String methodName = annotationViolation.getMethodName(); + if (methodName == null || methodName.isEmpty()) { // not an annotation on a method + methodName = NO_METHOD; + // pmd7 fixes the method name of a violation, we don't have to find it in the code anymore } annotationContextResult = new ViolatingAnnotationHolder(violatingAnnotation, methodName); } @@ -204,46 +198,6 @@ ViolatingAnnotationHolder getAnnotationContext(PMDViolation annotationViolation) return annotationContextResult; } - /** - * Find out name of method following annotation, from the document. Implemented with text matching. - * Limitation: Cannot deal with comments containing code, and not with all cases. - * TODO use proper parsing with PSIDocumentManager - * - * @param code document after the annotation - * @return name of the method, or NO_METHOD when annotation is on class or field - */ - String findMethodName(String code) { - code = removeComments(code); - int classIndex = code.indexOf(" class "); - if (classIndex > 0) { // on class or has a subclass, remove code it - code = code.substring(0, classIndex); - } - String methodName = NO_METHOD; // for class level annotations - Matcher methodMatcher = NEXT_METHOD_NAME_PATTERN.matcher(code); - if (methodMatcher.find()) { - if (methodMatcher.groupCount() > 0) { - methodName = methodMatcher.group(1); - // it may be on a field - String afterAnnoBeforeMethod = ""; - int methodPos = code.indexOf(methodName + "("); - if (methodPos >= 0) { - afterAnnoBeforeMethod = code.substring(0, methodPos); - } - Matcher fieldMatcher = NEXT_FIELD_NAME_PATTERN.matcher(afterAnnoBeforeMethod); - if (fieldMatcher.find()) { - methodName = NO_METHOD; // on field, map to class for now - } - } - } - return methodName; - } - - private String removeComments(String code) { - Matcher matcher = COMMENT_PATTERN.matcher(code); - // Remove the comments from the code string - return matcher.replaceAll(""); - } - static class ViolatingAnnotationHolder { ViolatingAnnotationHolder(String annotationValue, String method) { this.annotationValue = annotationValue;