Skip to content

Commit ac52ca9

Browse files
graememorganError Prone Team
authored and
Error Prone Team
committed
AutoValueFinalMethods: support method-level suppression.
And streamify the implementation a bit. PiperOrigin-RevId: 589088083
1 parent 336323a commit ac52ca9

File tree

2 files changed

+46
-33
lines changed

2 files changed

+46
-33
lines changed

core/src/main/java/com/google/errorprone/bugpatterns/AutoValueFinalMethods.java

Lines changed: 27 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -16,13 +16,14 @@
1616

1717
package com.google.errorprone.bugpatterns;
1818

19+
import static com.google.common.collect.ImmutableList.toImmutableList;
1920
import static com.google.errorprone.BugPattern.SeverityLevel.WARNING;
2021
import static com.google.errorprone.matchers.Description.NO_MATCH;
2122
import static com.google.errorprone.matchers.Matchers.allOf;
2223
import static com.google.errorprone.matchers.Matchers.anyOf;
2324
import static com.google.errorprone.matchers.Matchers.not;
25+
import static java.util.stream.Collectors.joining;
2426

25-
import com.google.common.base.Joiner;
2627
import com.google.errorprone.BugPattern;
2728
import com.google.errorprone.VisitorState;
2829
import com.google.errorprone.bugpatterns.BugChecker.ClassTreeMatcher;
@@ -34,10 +35,6 @@
3435
import com.google.errorprone.util.ASTHelpers;
3536
import com.sun.source.tree.ClassTree;
3637
import com.sun.source.tree.MethodTree;
37-
import com.sun.source.tree.Tree;
38-
import java.util.ArrayList;
39-
import java.util.List;
40-
import java.util.Optional;
4138
import javax.lang.model.element.Modifier;
4239

4340
/**
@@ -71,34 +68,31 @@ public Description matchClass(ClassTree tree, VisitorState state) {
7168
if (!ASTHelpers.hasAnnotation(tree, "com.google.auto.value.AutoValue", state)) {
7269
return NO_MATCH;
7370
}
74-
SuggestedFix.Builder fix = SuggestedFix.builder();
75-
List<String> matchedMethods = new ArrayList<>();
76-
MethodTree firstMatchedMethod = null;
77-
for (Tree memberTree : tree.getMembers()) {
78-
if (!(memberTree instanceof MethodTree)) {
79-
continue;
80-
}
81-
MethodTree method = (MethodTree) memberTree;
82-
if (METHOD_MATCHER.matches(method, state)) {
83-
Optional<SuggestedFix> optionalSuggestedFix =
84-
SuggestedFixes.addModifiers(method, state, Modifier.FINAL);
85-
if (optionalSuggestedFix.isPresent()) {
86-
matchedMethods.add(method.getName().toString());
87-
fix.merge(optionalSuggestedFix.get());
88-
if (firstMatchedMethod == null) {
89-
firstMatchedMethod = method;
90-
}
91-
}
92-
}
93-
}
94-
if (!fix.isEmpty()) {
95-
String message =
96-
String.format(
97-
"Make %s final in AutoValue classes, "
98-
+ "so it is clear to readers that AutoValue is not overriding them",
99-
Joiner.on(", ").join(matchedMethods));
100-
return buildDescription(firstMatchedMethod).setMessage(message).addFix(fix.build()).build();
71+
var candidateMethods =
72+
tree.getMembers().stream()
73+
.filter(
74+
t ->
75+
t instanceof MethodTree
76+
&& METHOD_MATCHER.matches((MethodTree) t, state)
77+
&& !isSuppressed(t, state))
78+
.map(t -> (MethodTree) t)
79+
.collect(toImmutableList());
80+
81+
var fix =
82+
candidateMethods.stream()
83+
.flatMap(t -> SuggestedFixes.addModifiers(t, state, Modifier.FINAL).stream())
84+
.reduce(SuggestedFix.emptyFix(), SuggestedFix::merge);
85+
86+
if (fix.isEmpty()) {
87+
return NO_MATCH;
10188
}
102-
return NO_MATCH;
89+
return buildDescription(candidateMethods.get(0))
90+
.setMessage(
91+
String.format(
92+
"Make %s final in AutoValue classes, "
93+
+ "so it is clear to readers that AutoValue is not overriding them",
94+
candidateMethods.stream().map(t -> t.getName().toString()).collect(joining(", "))))
95+
.addFix(fix)
96+
.build();
10397
}
10498
}

core/src/test/java/com/google/errorprone/bugpatterns/AutoValueFinalMethodsTest.java

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,25 @@ public void finalAdditionToEqHcTs() {
8686
.doTest();
8787
}
8888

89+
@Test
90+
public void suppression() {
91+
compilationHelper
92+
.addSourceLines(
93+
"in/Test.java",
94+
"import com.google.auto.value.AutoValue;",
95+
"@AutoValue",
96+
"abstract class Test {",
97+
" abstract String valueOne();",
98+
" abstract String valueTwo();",
99+
" @SuppressWarnings(\"AutoValueFinalMethods\")",
100+
" @Override",
101+
" public int hashCode() {",
102+
" return 1;",
103+
" }",
104+
"}")
105+
.doTest();
106+
}
107+
89108
@Test
90109
public void negativeCases() {
91110
compilationHelper

0 commit comments

Comments
 (0)