向Payara部署SpringFramework应用时出现CDI不可用异常
解决Payara部署Spring Web 6.0.0时的ASM与CDI错误
问题根源分析
- ASM8异常:Spring 6.0.0依赖的ASM版本(通常为ASM9)与Payara自带的低版本ASM冲突,Payara默认的
PARENT_FIRST类加载策略优先加载容器自带的旧版ASM,导致Spring无法使用ASM8+特性。 - CDI不可用错误:Spring Web 6的初始化流程与Payara的CDI容器触发冲突,导致Payara无法正确识别CDI运行环境。
具体解决步骤
1. 调整类加载顺序解决ASM冲突
将应用的类加载策略改为PARENT_LAST,让应用优先加载自身依赖的ASM版本:
- 部署时在Payara管理控制台进入应用的配置 > 类加载器,将策略改为
PARENT_LAST。 - 或在
glassfish-web.xml中添加配置:
<glassfish-web-app> <class-loader delegate="false"/> <!-- delegate=false对应PARENT_LAST策略 --> </glassfish-web-app>
2. 修复CDI不可用问题
方案一:禁用Payara默认CDI(适用于纯Spring应用)
在glassfish-web.xml中添加禁用配置:
<glassfish-web-app> <disable-default-cdi>true</disable-default-cdi> </glassfish-web-app>
也可以在web.xml中配置参数:
<context-param> <param-name>fish.payara.cdi.disable</param-name> <param-value>true</param-value> </context-param>
方案二:兼容Spring与Payara CDI(适用于需同时使用两者的场景)
- 显式配置Spring上下文初始化逻辑,避免自动触发冲突:
public class SpringWebInitializer implements WebApplicationInitializer { @Override public void onStartup(ServletContext servletContext) throws ServletException { AnnotationConfigWebApplicationContext context = new AnnotationConfigWebApplicationContext(); context.register(AppConfig.class); servletContext.addListener(new ContextLoaderListener(context)); ServletRegistration.Dynamic dispatcher = servletContext.addServlet("dispatcher", new DispatcherServlet(context)); dispatcher.setLoadOnStartup(1); dispatcher.addMapping("/"); } }
- 在pom.xml中排除Spring Web中不必要的CDI相关依赖:
<dependency> <groupId>org.springframework</groupId> <artifactId>spring-web</artifactId> <version>6.0.0</version> <exclusions> <exclusion> <groupId>javax.enterprise</groupId> <artifactId>cdi-api</artifactId> </exclusion> </exclusions> </dependency>
3. 验证版本兼容性
确保项目依赖与Payara的Java版本一致(Java 17),在pom.xml中指定:
<properties> <maven.compiler.source>17</maven.compiler.source> <maven.compiler.target>17</maven.compiler.target> </properties>
同时确认使用的Payara版本为6.x系列(Payara 6完全兼容Java 17与Spring 6,若使用Payara 5需升级至6.x)。
内容的提问来源于stack exchange,提问作者Bernie 1411
相关产品推荐
相关产品推荐

