我目前正在将一个应用程序从Spring Boot 1.X升级到2.X.应用程序中的一个测试是使用@SpringBootTest下的OpenEJB测试无状态远程EJB。由于在Spring 5中已经删除了对SpringBeanAutowiringInterceptor的支持,我现在面临着重写逻辑并测试它的任务,这就出现了问题:我们运行的是JDK 1.8和openejb(4.7.4,用于test来初始化jndiContext)无法处理多个版本的JAR,这些JAR是从升级到Spring Boot 2.X的依赖项(例如byte-buddy和其他)。 OpenEJB尝试加载META-INF / versions / 9 / module-info并在IllegalArgumentException上失败。我也尝试从OpenEJB切换到EJBcontainer以及glassfish作为加载器,但我面临着不同的问题(无状态bean未在jndContext中设置 - 在DEBUG中检查),我目前正在尝试解决这个问题。
我的问题是:是否有可能以某种方式强制classloader或openejb忽略module-info,以便能够在类路径上使用多版本jar在JDK 1.8下运行它?或者有没有办法使用EJBContainer和glassfish-embedded-all,它目前不加载EJB但至少加载上下文而没有错误?我需要避免错误或使用另一种方法如何在SpringBootTest中测试无状态Bean。
注意:我不想使用Arquillian
版本摘要:
使用openEJB时出错(module-info,多版本JAR问题):
ERROR OpenEJB [] []- FATAL ERROR: Unknown error in Assembler. Please send the following stack trace and this message to [email protected] :
java.lang.IllegalArgumentException
at org.apache.xbean.asm5.ClassReader.<init>(Unknown Source)
at org.apache.xbean.asm5.ClassReader.<init>(Unknown Source)
at org.apache.xbean.asm5.ClassReader.<init>(Unknown Source)
at org.apache.openejb.util.AnnotationFinder.readClassDef(AnnotationFinder.java:299)
at org.apache.openejb.util.AnnotationFinder.find(AnnotationFinder.java:164)
at org.apache.openejb.config.DeploymentLoader.checkAnnotations(DeploymentLoader.java:2008)
at org.apache.openejb.config.DeploymentLoader.discoverModuleType(DeploymentLoader.java:1891)
at org.apache.openejb.config.DeploymentsResolver.processUrls(DeploymentsResolver.java:389)
at org.apache.openejb.config.DeploymentsResolver.loadFromClasspath(DeploymentsResolver.java:302)
at org.apache.openejb.config.ConfigurationFactory.getModulesFromClassPath(ConfigurationFactory.java:664)
使用glassfish时出错(可能指定了错误的MODULES?):
ERROR embedded [] []- EJB6005:No EJB modules found
测试类的重要部分:
@RunWith(SpringRunner.class)
@SpringBootTest(classes = {
CommonTestConfiguration.class,
DatabaseTestConfiguration.class,
PropositionServiceConfiguration.class,
BeanUtils.class,
PropositionRemoteServiceImpl.class,
PropositionRemoteService.class})
@DirtiesContext
public class PropositionRemoteServiceImplTest {
@Autowired
private AdminFacade adminFacade;
private PropositionRemoteService remoteService;
@Before
public void setUp() throws NamingException {
Properties props = new Properties();
props.put(Context.INITIAL_CONTEXT_FACTORY, "org.apache.openejb.client.LocalInitialContextFactory");
//props.put("openejb.deployments.classpath.exclude", ".*?module-info.*?");
Context jndiContext = new InitialContext(props);
remoteService = (PropositionRemoteService) jndiContext.lookup("PropositionRemoteServiceImplRemote");
// Map<String, Object> properties = new HashMap<>();
// properties.put(EJBContainer.MODULES, new File("target/classes"));
// EJBContainer ejbContainer = EJBContainer.createEJBContainer(properties);
// Context ctx = ejbContainer.getContext();
// remoteService = (PropositionRemoteService) ctx.lookup("PropositionRemoteServiceImplRemote");
}
项目结构(简化 - 大项目,不能改变):
ude> root node module - pom
adapter> - node-module
ejb-adapter> node module
ejb-adapter-impl> node module containing Stateless bean used in test
test> node module
test-unit> node module where the Test class is defined and run
更新:目前尝试apache-tomee(1.7.5)而不是openejb-core sbut它也使用asm5并且发生相同的错误
问题解决了使用更新版本的openEJB - > Apache Tomee,它使用asm6并支持JDK 1.9,即使我使用的是JDK 1.8,但由于多版本JARS作为Spring Boot 2的依赖项,因此需要这种支持。使用的神器:
<dependency>
<groupId>org.apache.tomee</groupId>
<artifactId>apache-tomee</artifactId>
<version>8.0.0-M2</version>
<scope>test</scope>
</dependency>