Skip to content

Commit

Permalink
[#3716] Test for an IllegalArgumentException in JavaTemplateJava… (#3717
Browse files Browse the repository at this point in the history
)

* [#3716] WIP: Test for an IllegalArgumentException in JavaTemplateJavaExtension; not running

* [#3716] Fix for the case the placeholder is generic with unknown type; tests for the case

* [#3716] Put more context in the exception message

* Fix some formatting in tests

---------

Co-authored-by: Knut Wannheden <[email protected]>
  • Loading branch information
api-from-the-ion and knutwannheden authored Nov 27, 2023
1 parent 83b2f77 commit 50f38d5
Show file tree
Hide file tree
Showing 4 changed files with 162 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -424,4 +424,37 @@ void test(boolean condition) {
)
);
}

@Test
void testAnyIsGenericWithUnknownType() {
rewriteRun(
spec -> spec.recipe(toRecipe(() -> new JavaVisitor<>() {
@Override
public J visitMethodInvocation(J.MethodInvocation method, ExecutionContext ctx) {
return JavaTemplate.builder("System.out.println(#{any()})")
.contextSensitive()
.build()
.apply(getCursor(), method.getCoordinates().replace(), method);
}
})).cycles(1).expectedCyclesThatMakeChanges(1),
java(
"""
import java.util.Map;
class Test {
void test(Map<String, ?> map) {
map.get("test");
}
}
""",
"""
import java.util.Map;
class Test {
void test(Map<String, ?> map) {
System.out.println(map.get("test"));
}
}
"""
)
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@
import org.openrewrite.java.tree.*;
import org.openrewrite.test.RewriteTest;

import java.util.List;

import static org.assertj.core.api.Assertions.assertThat;
import static org.openrewrite.java.Assertions.java;
import static org.openrewrite.test.RewriteTest.toRecipe;
Expand Down Expand Up @@ -995,7 +997,9 @@ class T {
void addStatementInIfBlock() {
rewriteRun(
spec -> spec.recipe(toRecipe(() -> new JavaIsoVisitor<>() {
final MethodMatcher lowerCaseMatcher = new MethodMatcher("java.lang.String toLowerCase()"); @Override
final MethodMatcher lowerCaseMatcher = new MethodMatcher("java.lang.String toLowerCase()");

@Override
public J.Block visitBlock(J.Block block, ExecutionContext ctx) {
J.Block newBlock = super.visitBlock(block, ctx);
if (newBlock.getStatements().stream().noneMatch(J.VariableDeclarations.class::isInstance)) {
Expand Down Expand Up @@ -1041,4 +1045,124 @@ void test() {
)
);
}

@Test
void replaceMethodCallWithGenericParameterWithUnknownType() {
rewriteRun(
spec -> spec.parser(JavaParser.fromJavaVersion().classpath("junit-jupiter-api"))
.recipe(toRecipe(() -> new JavaIsoVisitor<>() {
private final JavaParser.Builder<?, ?> assertionsParser = JavaParser.fromJavaVersion()
.classpath("assertj-core");

private static final MethodMatcher JUNIT_ASSERT_EQUALS = new MethodMatcher("org.junit.jupiter.api.Assertions assertEquals(..)");

@Override
public J.MethodInvocation visitMethodInvocation(J.MethodInvocation method, ExecutionContext ctx) {
if (!JUNIT_ASSERT_EQUALS.matches(method)) {
return method;
}

List<Expression> args = method.getArguments();
Expression expected = args.get(0);
Expression actual = args.get(1);

maybeAddImport("org.assertj.core.api.Assertions", "assertThat");
maybeRemoveImport("org.junit.jupiter.api.Assertions");

if (args.size() == 2) {
return JavaTemplate.builder("assertThat(#{any()}).isEqualTo(#{any()});")
.staticImports("org.assertj.core.api.Assertions.assertThat")
.javaParser(assertionsParser)
.build()
.apply(getCursor(), method.getCoordinates().replace(), actual, expected);
} else {
return super.visitMethodInvocation(method, ctx);
}
}
})),
java(
"""
import java.util.Map;
import org.junit.jupiter.api.Assertions;
class T {
void m(String one, Map<String, ?> map) {
Assertions.assertEquals(one, map.get("one"));
}
}
""",
"""
import java.util.Map;
import static org.assertj.core.api.Assertions.assertThat;
class T {
void m(String one, Map<String, ?> map) {
assertThat(map.get("one")).isEqualTo(one);
}
}
"""
)
);
}

@Test
void replaceCallWithUnknownGenericReturnValue() {
rewriteRun(
spec -> spec.recipe(toRecipe(() -> new JavaIsoVisitor<>() {
private static final MethodMatcher OBJECTS_EQUALS = new MethodMatcher("java.util.Objects equals(..)");

@Override
public J.MethodInvocation visitMethodInvocation(J.MethodInvocation method, ExecutionContext ctx) {
if (!OBJECTS_EQUALS.matches(method)) {
return method;
}

List<Expression> args = method.getArguments();
Expression expected = args.get(0);
Expression actual = args.get(1);

maybeAddImport("java.util.Objects", "requireNonNull");

if (args.size() == 2) {
return JavaTemplate.builder("requireNonNull(#{any()}).equals(#{any()});")
.staticImports("java.util.Objects.requireNonNull")
.javaParser(JavaParser.fromJavaVersion())
.build()
.apply(getCursor(), method.getCoordinates().replace(), actual, expected);
} else {
return super.visitMethodInvocation(method, ctx);
}
}
})),
java(
"""
import java.util.Objects;
import java.util.Map;
import java.util.HashMap;
class T {
void m() {
Map<String, ?> map = new HashMap<>();
Objects.equals("", map.get("one"));
}
}
""",
"""
import java.util.Objects;
import java.util.Map;
import static java.util.Objects.requireNonNull;
import java.util.HashMap;
class T {
void m() {
Map<String, ?> map = new HashMap<>();
requireNonNull(map.get("one")).equals("");
}
}
"""
)
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -474,7 +474,8 @@ private <J3 extends J> J3 maybeReplaceStatement(Statement statement, Class<J3> e
}
throw new IllegalArgumentException("Expected a template that would generate exactly one " +
"statement to replace one statement, but generated " + gen.size() +
". Template:\n" + substitutedTemplate);
". Template:\n" + substitutedTemplate + "\nSubstitutions:\n" + substitutions +
"\nStatement:\n" + statement);
}

return autoFormat(gen.get(0).withPrefix(statement.getPrefix()), p);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -175,7 +175,8 @@ private String getTypeName(@Nullable JavaType type) {
}
return ((JavaType.Parameterized) type).getFullyQualifiedName() + joiner;
} else if (type instanceof JavaType.GenericTypeVariable) {
return ((JavaType.GenericTypeVariable) type).getName();
String name = ((JavaType.GenericTypeVariable) type).getName();
return "?".equals(name) ? "Object" : name;
} else if (type instanceof JavaType.FullyQualified) {
return ((JavaType.FullyQualified) type).getFullyQualifiedName();
} else if (type instanceof JavaType.Primitive) {
Expand Down

0 comments on commit 50f38d5

Please sign in to comment.