Last active
March 15, 2022 15:39
-
-
Save jkschneider/9da81566d82ed98dd018924769822750 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
testImplementation("javax:javaee-api:7.0") |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package org.openrewrite.java; | |
import lombok.SneakyThrows; | |
import org.openrewrite.ExecutionContext; | |
import org.openrewrite.Recipe; | |
import org.openrewrite.SourceFile; | |
import org.openrewrite.TreeVisitor; | |
import org.openrewrite.internal.ListUtils; | |
import org.openrewrite.java.search.FindAnnotations; | |
import org.openrewrite.java.search.UsesType; | |
import org.openrewrite.java.tree.J; | |
import org.openrewrite.java.tree.JavaSourceFile; | |
import org.openrewrite.java.tree.JavaType; | |
import java.text.RuleBasedCollator; | |
import java.util.Comparator; | |
import java.util.List; | |
public class EjbToBean extends Recipe { | |
@Override | |
public String getDisplayName() { | |
return "Begin conversion from EJB to Spring `@Bean`"; | |
} | |
@Override | |
public String getDescription() { | |
return "Extract an interface from the EJB, removing EJB lifecycle methods in the extracted interface. " + | |
"The new interface should have a static builder instantiating the existing EJB implementation class."; | |
} | |
@Override | |
protected TreeVisitor<?, ExecutionContext> getApplicableTest() { | |
return new UsesType<>("javax.ejb..*"); | |
} | |
@Override | |
protected List<SourceFile> visit(List<SourceFile> before, ExecutionContext ctx) { | |
return ListUtils.flatMap(before, sourceFile -> { | |
if (sourceFile instanceof JavaSourceFile) { | |
JavaSourceFile cu = (JavaSourceFile) sourceFile; | |
for (J.ClassDeclaration aClass : cu.getClasses()) { | |
JavaType.FullyQualified type = aClass.getType(); | |
assert type != null; | |
if (!FindAnnotations.find(aClass, "@javax.ejb.Stateless").isEmpty()) { | |
String interfaceName = type.getPackageName().replace(".ejb", "") + "." + type.getClassName(); | |
List<JavaSourceFile> interfaceAndImpl = ExtractInterface.extract(cu, interfaceName); | |
return ListUtils.map(interfaceAndImpl, (i, interfaceOrImpl) -> { | |
if (i == 0) { | |
J anInterface = new DeimplementInterface<>("javax.ejb.EnterpriseBean") | |
.visitNonNull(interfaceOrImpl, ctx); | |
anInterface = new DeimplementInterface<>("javax.ejb.SessionBean") | |
.visitNonNull(anInterface, ctx); | |
anInterface = new DeimplementInterface<>("javax.ejb.MessageBean") | |
.visitNonNull(anInterface, ctx); | |
anInterface = new DeimplementInterface<>("javax.ejb.EntityBean") | |
.visitNonNull(anInterface, ctx); | |
anInterface = new RemoveAnnotationVisitor(new AnnotationMatcher("@javax.ejb..*")) | |
.visitNonNull(anInterface, ctx); | |
anInterface = new JavaVisitor<ExecutionContext>() { | |
@SneakyThrows | |
@Override | |
public J visitClassDeclaration(J.ClassDeclaration classDecl, ExecutionContext ctx) { | |
JavaTemplate template = JavaTemplate.builder(this::getCursor, "" + | |
"static " + type.getClassName() + " getInstance() {\n" + | |
" return new " + type.getFullyQualifiedName() + "();" + | |
"}" | |
).build(); | |
return autoFormat( | |
classDecl.withTemplate( | |
template, | |
classDecl.getBody().getCoordinates().addMethodDeclaration( | |
Comparator.comparing( | |
J.MethodDeclaration::getSimpleName, | |
new RuleBasedCollator("< getInstance") | |
) | |
) | |
), | |
ctx | |
); | |
} | |
}.visitNonNull(anInterface, ctx); | |
return (JavaSourceFile) anInterface; | |
} | |
return (JavaSourceFile) new ImplementInterface<ExecutionContext>(interfaceOrImpl.getClasses().get(0), interfaceName) | |
.visitNonNull(interfaceOrImpl, ctx); | |
}); | |
} | |
} | |
} | |
return sourceFile; | |
}); | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package org.openrewrite.java | |
import org.assertj.core.api.Assertions.assertThat | |
import org.junit.jupiter.api.Test | |
class EjbToBeanTest : JavaRecipeTest { | |
override val parser: JavaParser | |
get() = JavaParser.fromJavaVersion() | |
.classpath("javaee-api") | |
.build() | |
@Test | |
fun ejbToBean() { | |
val cu = parser.parse( | |
""" | |
package org.openrewrite.ejb; | |
import javax.ejb.EntityBean; | |
import javax.ejb.Stateless; | |
@Stateless | |
public class MyBean implements EntityBean { | |
public final void businessMethod() { | |
} | |
private void test() {} | |
@Override | |
public void ejbActivate() { | |
} | |
} | |
""".trimIndent() | |
) | |
val results = EjbToBean().run(cu) | |
//language=java | |
assertThat(results[0].after!!.printAll()).isEqualTo(""" | |
package org.openrewrite; | |
public interface MyBean { | |
static MyBean getInstance() { | |
return new org.openrewrite.ejb.MyBean(); | |
} | |
void businessMethod(); | |
} | |
""".trimIndent()) | |
//language=java | |
assertThat(results[1].after!!.printAll()).isEqualTo(""" | |
package org.openrewrite.ejb; | |
import javax.ejb.EntityBean; | |
import javax.ejb.Stateless; | |
@Stateless | |
public class MyBean implements EntityBean, org.openrewrite.MyBean { | |
@Override | |
public final void businessMethod() { | |
} | |
private void test() {} | |
@Override | |
public void ejbActivate() { | |
} | |
} | |
""".trimIndent()) | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment