From 9d1ba4c36b0f72bdb53df6f59e45a61aabbab6af Mon Sep 17 00:00:00 2001 From: Jonathan Schneider Date: Tue, 13 Jul 2021 03:14:52 -0700 Subject: [PATCH] NoGuavaMapsNewLinkedHashMap --- .../guava/NoGuavaMapsNewLinkedHashMap.java | 77 ++++++++++++++ .../guava/NoGuavaListsNewLinkedHashMapTest.kt | 100 ++++++++++++++++++ 2 files changed, 177 insertions(+) create mode 100644 src/main/java/org/openrewrite/java/migrate/guava/NoGuavaMapsNewLinkedHashMap.java create mode 100644 src/test/kotlin/org/openrewrite/java/migrate/guava/NoGuavaListsNewLinkedHashMapTest.kt diff --git a/src/main/java/org/openrewrite/java/migrate/guava/NoGuavaMapsNewLinkedHashMap.java b/src/main/java/org/openrewrite/java/migrate/guava/NoGuavaMapsNewLinkedHashMap.java new file mode 100644 index 0000000000..342c6d76d5 --- /dev/null +++ b/src/main/java/org/openrewrite/java/migrate/guava/NoGuavaMapsNewLinkedHashMap.java @@ -0,0 +1,77 @@ +package org.openrewrite.java.migrate.guava; + +import org.openrewrite.ExecutionContext; +import org.openrewrite.Recipe; +import org.openrewrite.TreeVisitor; +import org.openrewrite.java.JavaIsoVisitor; +import org.openrewrite.java.JavaTemplate; +import org.openrewrite.java.JavaVisitor; +import org.openrewrite.java.MethodMatcher; +import org.openrewrite.java.search.UsesMethod; +import org.openrewrite.java.tree.J; + +public class NoGuavaMapsNewLinkedHashMap extends Recipe { + private static final MethodMatcher NEW_LINKED_HASH_MAP = new MethodMatcher("com.google.common.collect.Maps newLinkedHashMap()"); + private static final MethodMatcher NEW_LINKED_HASH_MAP_ITERABLE = new MethodMatcher("com.google.common.collect.Maps newLinkedHashMap(java.util.Map)"); + private static final MethodMatcher NEW_LINKED_HASH_MAP_CAPACITY = new MethodMatcher("com.google.common.collect.Maps newLinkedHashMapWithExpectedSize(int)"); + + @Override + public String getDisplayName() { + return "Use `new LinkedHashMap<>()` instead of Guava"; + } + + @Override + public String getDescription() { + return "Prefer the Java standard library over third-party usage of Guava in simple cases like this."; + } + + @Override + protected TreeVisitor getApplicableTest() { + return new JavaIsoVisitor() { + @Override + public J.CompilationUnit visitCompilationUnit(J.CompilationUnit cu, ExecutionContext executionContext) { + doAfterVisit(new UsesMethod<>(NEW_LINKED_HASH_MAP)); + doAfterVisit(new UsesMethod<>(NEW_LINKED_HASH_MAP_ITERABLE)); + doAfterVisit(new UsesMethod<>(NEW_LINKED_HASH_MAP_CAPACITY)); + return cu; + } + }; + } + + @Override + protected TreeVisitor getVisitor() { + return new JavaVisitor() { + private final JavaTemplate newLinkedHashMap = JavaTemplate.builder(this::getCursor, "new LinkedHashMap<>()") + .imports("java.util.LinkedHashMap") + .build(); + + private final JavaTemplate newLinkedHashMapIterable = JavaTemplate.builder(this::getCursor, "new LinkedHashMap<>(#{any(java.util.Map)})") + .imports("java.util.LinkedHashMap") + .build(); + + private final JavaTemplate newLinkedHashMapCapacity = JavaTemplate.builder(this::getCursor, "new LinkedHashMap<>(#{any(int)})") + .imports("java.util.LinkedHashMap") + .build(); + + @Override + public J visitMethodInvocation(J.MethodInvocation method, ExecutionContext executionContext) { + if (NEW_LINKED_HASH_MAP.matches(method)) { + maybeRemoveImport("com.google.common.collect.Maps"); + maybeAddImport("java.util.LinkedHashMap"); + return method.withTemplate(newLinkedHashMap, method.getCoordinates().replace()); + } else if (NEW_LINKED_HASH_MAP_ITERABLE.matches(method)) { + maybeRemoveImport("com.google.common.collect.Maps"); + maybeAddImport("java.util.LinkedHashMap"); + return method.withTemplate(newLinkedHashMapIterable, method.getCoordinates().replace(), + method.getArguments().get(0)); + } else if (NEW_LINKED_HASH_MAP_CAPACITY.matches(method)) { + maybeRemoveImport("com.google.common.collect.Maps"); + maybeAddImport("java.util.LinkedHashMap"); + return method.withTemplate(newLinkedHashMapCapacity, method.getCoordinates().replace(), + method.getArguments().get(0)); + } + return super.visitMethodInvocation(method, executionContext); + } + }; + } +} diff --git a/src/test/kotlin/org/openrewrite/java/migrate/guava/NoGuavaListsNewLinkedHashMapTest.kt b/src/test/kotlin/org/openrewrite/java/migrate/guava/NoGuavaListsNewLinkedHashMapTest.kt new file mode 100644 index 0000000000..ad0b79aa9a --- /dev/null +++ b/src/test/kotlin/org/openrewrite/java/migrate/guava/NoGuavaListsNewLinkedHashMapTest.kt @@ -0,0 +1,100 @@ +/* + * Copyright 2021 the original author or authors. + *

+ * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + *

+ * https://www.apache.org/licenses/LICENSE-2.0 + *

+ * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.openrewrite.java.migrate.guava + +import org.junit.jupiter.api.Test +import org.openrewrite.Recipe +import org.openrewrite.java.JavaParser +import org.openrewrite.java.JavaRecipeTest + +class NoGuavaListsNewLinkedHashMapTest: JavaRecipeTest { + override val parser: JavaParser + get() = JavaParser.fromJavaVersion() + .logCompilationWarningsAndErrors(true) + .classpath("guava") + .build() + + override val recipe: Recipe + get() = NoGuavaMapsNewLinkedHashMap() + + @Test + fun replaceWithNewLinkedHashMap() = assertChanged( + before = """ + import com.google.common.collect.*; + + import java.util.Map; + + class Test { + Map cardinalsWorldSeries = Maps.newLinkedHashMap(); + } + """, + after = """ + import java.util.LinkedHashMap; + import java.util.Map; + + class Test { + Map cardinalsWorldSeries = new LinkedHashMap<>(); + } + """ + ) + + @Test + fun replaceWithNewLinkedHashMapWithMap() = assertChanged( + before = """ + import com.google.common.collect.*; + + import java.util.Collections; + import java.util.Map; + + class Test { + Map m = Collections.emptyMap(); + Map cardinalsWorldSeries = Maps.newLinkedHashMap(m); + } + """, + after = """ + import java.util.Collections; + import java.util.LinkedHashMap; + import java.util.Map; + + class Test { + Map m = Collections.emptyMap(); + Map cardinalsWorldSeries = new LinkedHashMap<>(m); + } + """ + ) + + @Test + fun replaceWithNewLinkedHashMapWithCapacity() = assertChanged( + before = """ + import com.google.common.collect.*; + + import java.util.LinkedHashMap; + import java.util.Map; + + class Test { + Map cardinalsWorldSeries = Maps.newLinkedHashMapWithExpectedSize(2); + } + """, + after = """ + import java.util.LinkedHashMap; + import java.util.Map; + + class Test { + Map cardinalsWorldSeries = new LinkedHashMap<>(2); + } + """ + ) +}