From b73a0298fdeb795dede7ac2a55fef40b0153e645 Mon Sep 17 00:00:00 2001 From: Stephan Schroevers Date: Sat, 3 Dec 2022 11:37:26 +0100 Subject: [PATCH 1/2] Improve mutation testing setup Summary of changes: - Enable Pitest's built-in `STRONGER` mutator group. - Enable Arcmutate's `EXTENDED` mutator group. - Enable Arcmutate's JUnit 5 Accelerator Plugin. - Modify `MoreTypesTest` such that it is impacted by mutations to the `MoreTypes` class. See: - https://pitest.org/quickstart/mutators/ - https://docs.arcmutate.com/docs/extended-operators.html - https://docs.arcmutate.com/docs/accelerator.html --- .../bugpatterns/util/MoreTypesTest.java | 93 ++++++++++--------- pom.xml | 14 +++ 2 files changed, 64 insertions(+), 43 deletions(-) diff --git a/error-prone-contrib/src/test/java/tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java b/error-prone-contrib/src/test/java/tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java index 48d003fa20..8774bea235 100644 --- a/error-prone-contrib/src/test/java/tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java +++ b/error-prone-contrib/src/test/java/tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java @@ -25,46 +25,6 @@ import org.junit.jupiter.api.Test; final class MoreTypesTest { - private static final ImmutableSet> TYPES = - ImmutableSet.of( - // Invalid types. - type("java.lang.Nonexistent"), - generic(type("java.util.Integer"), unbound()), - // Valid types. - type("java.lang.String"), - type("java.lang.Number"), - superOf(type("java.lang.Number")), - subOf(type("java.lang.Number")), - type("java.lang.Integer"), - superOf(type("java.lang.Integer")), - subOf(type("java.lang.Integer")), - type("java.util.Optional"), - raw(type("java.util.Optional")), - generic(type("java.util.Optional"), unbound()), - generic(type("java.util.Optional"), type("java.lang.Number")), - type("java.util.Collection"), - raw(type("java.util.Collection")), - generic(type("java.util.Collection"), unbound()), - generic(type("java.util.Collection"), type("java.lang.Number")), - generic(type("java.util.Collection"), superOf(type("java.lang.Number"))), - generic(type("java.util.Collection"), subOf(type("java.lang.Number"))), - generic(type("java.util.Collection"), type("java.lang.Integer")), - generic(type("java.util.Collection"), superOf(type("java.lang.Integer"))), - generic(type("java.util.Collection"), subOf(type("java.lang.Integer"))), - type("java.util.List"), - raw(type("java.util.List")), - generic(type("java.util.List"), unbound()), - generic(type("java.util.List"), type("java.lang.Number")), - generic(type("java.util.List"), superOf(type("java.lang.Number"))), - generic(type("java.util.List"), subOf(type("java.lang.Number"))), - generic(type("java.util.List"), type("java.lang.Integer")), - generic(type("java.util.List"), superOf(type("java.lang.Integer"))), - generic(type("java.util.List"), subOf(type("java.lang.Integer"))), - generic( - type("java.util.Map"), - type("java.lang.String"), - subOf(generic(type("java.util.Collection"), superOf(type("java.lang.Short")))))); - @Test void matcher() { CompilationTestHelper.newInstance(SubtypeFlagger.class, getClass()) @@ -159,8 +119,8 @@ void matcher() { } /** - * A {@link BugChecker} that flags method invocations that are a subtype of any type contained in - * {@link #TYPES}. + * A {@link BugChecker} that flags method invocations that are a subtype of any type defined by + * {@link #getTestTypes()}. */ @BugPattern(summary = "Flags invocations of methods with select return types", severity = ERROR) public static final class SubtypeFlagger extends BugChecker @@ -173,7 +133,7 @@ public Description matchMethodInvocation(MethodInvocationTree tree, VisitorState List matches = new ArrayList<>(); - for (Supplier type : TYPES) { + for (Supplier type : getTestTypes()) { Type testType = type.get(state); if (testType != null && state.getTypes().isSubtype(treeType, testType)) { matches.add(Signatures.prettyType(testType)); @@ -184,5 +144,52 @@ public Description matchMethodInvocation(MethodInvocationTree tree, VisitorState ? Description.NO_MATCH : buildDescription(tree).setMessage(matches.toString()).build(); } + + /** + * Returns the type suppliers under test. + * + * @implNote The return value of this method should not be assigned to a field, as that would + * prevent mutations introduced by Pitest from being killed. + */ + private ImmutableSet> getTestTypes() { + return ImmutableSet.of( + // Invalid types. + type("java.lang.Nonexistent"), + generic(type("java.util.Integer"), unbound()), + // Valid types. + type("java.lang.String"), + type("java.lang.Number"), + superOf(type("java.lang.Number")), + subOf(type("java.lang.Number")), + type("java.lang.Integer"), + superOf(type("java.lang.Integer")), + subOf(type("java.lang.Integer")), + type("java.util.Optional"), + raw(type("java.util.Optional")), + generic(type("java.util.Optional"), unbound()), + generic(type("java.util.Optional"), type("java.lang.Number")), + type("java.util.Collection"), + raw(type("java.util.Collection")), + generic(type("java.util.Collection"), unbound()), + generic(type("java.util.Collection"), type("java.lang.Number")), + generic(type("java.util.Collection"), superOf(type("java.lang.Number"))), + generic(type("java.util.Collection"), subOf(type("java.lang.Number"))), + generic(type("java.util.Collection"), type("java.lang.Integer")), + generic(type("java.util.Collection"), superOf(type("java.lang.Integer"))), + generic(type("java.util.Collection"), subOf(type("java.lang.Integer"))), + type("java.util.List"), + raw(type("java.util.List")), + generic(type("java.util.List"), unbound()), + generic(type("java.util.List"), type("java.lang.Number")), + generic(type("java.util.List"), superOf(type("java.lang.Number"))), + generic(type("java.util.List"), subOf(type("java.lang.Number"))), + generic(type("java.util.List"), type("java.lang.Integer")), + generic(type("java.util.List"), superOf(type("java.lang.Integer"))), + generic(type("java.util.List"), subOf(type("java.lang.Integer"))), + generic( + type("java.util.Map"), + type("java.lang.String"), + subOf(generic(type("java.util.Collection"), superOf(type("java.lang.Short")))))); + } } } diff --git a/pom.xml b/pom.xml index 392fe02065..bfda0bd0d7 100644 --- a/pom.xml +++ b/pom.xml @@ -1248,6 +1248,10 @@ *.refaster*.*Rules* false + + EXTENDED + STRONGER + @@ -1261,6 +1265,16 @@ pitest-git-plugin ${version.pitest-git} + + com.groupcdg.arcmutate + base + 1.0.1 + + + com.groupcdg.pitest + pitest-accelerator-junit5 + 1.0.4 + org.pitest pitest-junit5-plugin From 29b4f3b56c869d2f2a5d3e971495264de193695a Mon Sep 17 00:00:00 2001 From: Stephan Schroevers Date: Sat, 3 Dec 2022 13:23:03 +0100 Subject: [PATCH 2/2] Doh --- .../tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/error-prone-contrib/src/test/java/tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java b/error-prone-contrib/src/test/java/tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java index 8774bea235..29b6fed550 100644 --- a/error-prone-contrib/src/test/java/tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java +++ b/error-prone-contrib/src/test/java/tech/picnic/errorprone/bugpatterns/util/MoreTypesTest.java @@ -151,7 +151,7 @@ public Description matchMethodInvocation(MethodInvocationTree tree, VisitorState * @implNote The return value of this method should not be assigned to a field, as that would * prevent mutations introduced by Pitest from being killed. */ - private ImmutableSet> getTestTypes() { + private static ImmutableSet> getTestTypes() { return ImmutableSet.of( // Invalid types. type("java.lang.Nonexistent"),