提交Jar包到Flink执行时出现Log4j NoSuchMethodError错误的排查与解决
问题描述
提交Jar包到Flink集群执行时出现以下错误:
Caused by: java.lang.NoSuchMethodError: 'void org.apache.logging.log4j.util.PropertiesUtil.addPropertySource(org.apache.logging.log4j.util.PropertySource)'
本地运行代码正常,通过mvn dependency:tree确认项目依赖的Log4j版本统一为2.20.0:
$ mvn dependency:tree | grep log4j [INFO] | | +- org.apache.logging.log4j:log4j-to-slf4j:jar:2.20.0:compile [INFO] | | | \- org.apache.logging.log4j:log4j-api:jar:2.20.0:compile
错误原因
Flink集群自身携带的Log4j版本与Jar包中依赖的版本不一致,引发类加载冲突:
- 本地运行时,JVM优先加载项目依赖的Log4j 2.20.0类,其中
PropertiesUtil包含addPropertySource方法; - 提交到Flink集群后,集群类加载器会优先加载自身
lib目录下的Log4j类,如果集群的Log4j版本低于2.20.0,该类中不存在目标方法,就会抛出NoSuchMethodError。
修复方案
方案1:标记Log4j依赖为provided
修改项目pom.xml,将Log4j相关依赖的scope设为provided,打包时不将这些依赖打进Jar包,直接使用Flink集群提供的版本:
<dependency> <groupId>org.apache.logging.log4j</groupId> <artifactId>log4j-api</artifactId> <version>2.20.0</version> <scope>provided</scope> </dependency> <dependency> <groupId>org.apache.logging.log4j</groupId> <artifactId>log4j-to-slf4j</artifactId> <version>2.20.0</version> <scope>provided</scope> </dependency>
注意:如果集群的Log4j版本低于2.20.0,需同步降级项目中的Log4j版本,确保与集群版本一致。
方案2:替换集群的Log4j版本
- 查看Flink集群
lib目录下的Log4j JAR包,确认当前版本; - 下载Log4j 2.20.0对应JAR包(
log4j-api-2.20.0.jar、log4j-to-slf4j-2.20.0.jar等); - 替换集群
lib目录中旧版本的Log4j JAR,重启Flink集群。
方案3:使用Maven Shade插件重命名Log4j包
通过Shade插件重命名项目依赖的Log4j包路径,避免与集群的Log4j类冲突。在pom.xml中添加以下配置:
<build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-shade-plugin</artifactId> <version>3.4.1</version> <executions> <execution> <phase>package</phase> <goals> <goal>shade</goal> </goals> <configuration> <relocations> <relocation> <pattern>org.apache.logging.log4j</pattern> <shadedPattern>com.yourcompany.log4j</shadedPattern> </relocation> </relocations> </configuration> </execution> </executions> </plugin> </plugins> </build>
重新打包Jar包后提交到集群即可。
内容的提问来源于stack exchange,提问作者ritratt
相关产品推荐
相关产品推荐

