工程启动报java.lang.NoClassDefFoundError错,解决!

最近在开发过程中遇到了一个“棘手”的问题,说它棘手是因为经过了多方的排查还是定位不到问题所在,后面还是根据同事一个不经意的提醒,才搞定的。接下来还原整个问题处理的经过

一、背景描述
我是Springboot2 + JDK1.8的工程,在配置文件里面数据库连接串使用了加密的密码:

db.spring.datasource.url=jdbc:oracle:thin:@************
db.spring.datasource.username=****_adm
#db.spring.datasource.password=***_864
db.spring.datasource.password=ENC(rb5a3YJ*******cHMJ3OD)

程序正常编译通过,本地启动正常,如果使用明文密码,部署一切正常。如果是采用加密的密码,则打镜像部署到k8s容器上报下面的异常。详细报错信息如下:

Error starting ApplicationContext. To display the conditions report re-run your application with 'debug' enabled. 
[/]  2025-02-27 17:01:17 [main]  o.s.b.diagnostics.LoggingFailureAnalysisReporter - 
 
*************************** 
APPLICATION FAILED TO START 
*************************** 
 
Description: 
 
Failed to bind properties under 'db.spring.datasource.password' to java.lang.String: 
 
    Reason: java.lang.NoClassDefFoundError: Could not initialize class com.ibm.icu.impl.NormalizerImpl 
 
Action: 
 
Update your application's configuration 

二、原因分析
根据网上找的资料,以及通过大模型寻找解决方案,首先是在依赖中添加下面的依赖:

<dependency>
    <groupId>com.ibm.icu</groupId>
    <artifactId>icu4j</artifactId>
    <version>72.1</version> <!-- 检查最新版本 -->
</dependency>

然后剔除项目中原本有包含com.ibm.icu.impl.NormalizerImpl的依赖。

一开始找不到哪个依赖中有包含上面的包,还怀疑是升级了基础镜像的问题,后面发现和基础镜像完全没啥关系。然后就怀疑本地JDK版本和容器版本是否不一致,排查了发现两边的版本都是JDK1.8。这下又毫无头绪了……

然后问了许多同事都说不清楚,后面经一个同事的提醒,才找到那个顽固的依赖所在:

先在工程里面import报错的包,然后反向找到依赖的所在:

三、解决方案 

找到依赖所在后,将该包给exclusion掉:

<dependency>
    <groupId>org.apache.pdfbox</groupId>
    <artifactId>pdfbox-app</artifactId>
    <version>1.8.10</version>
    <exclusions>
        <exclusion>
            <groupId>com.ibm.icu</groupId>
            <artifactId>icu4j</artifactId>
        </exclusion>
    </exclusions>
</dependency>

剔除掉重新打镜像部署,还是发现启动不起来,报同样的错。

后面发现是pdfbox-app依赖本身版本和JDK版本的冲突导致的,所以将依赖进行升级:

<dependency>
    <groupId>org.apache.pdfbox</groupId>
    <artifactId>pdfbox-app</artifactId>
    <version>3.0.0</version>
</dependency>

升级完对原来引用到的代码也进行升级后,重新打包部署,成功!!!

撒花完结!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值