Maven中同时使用CDH 的hive与ElasticSearch(ES) 内部依赖的netty jar冲突的问题

1、场景描述

因业务场景需要连接hive及ES,所以项目中需要整合这两项,那么在整合中遇到了jar包冲突的问题,项目是用的是Maven工程,hive 是用的CDH中的。

2、pom文件 中引用的hive及ES如下

 
	 
			org.springframework.data
			spring-data-hadoop
			2.5.0.RELEASE
		
		
		
		
			org.apache.hadoop
			hadoop-common
			2.6.0-cdh5.13.3
		
		
			org.apache.hadoop
			hadoop-core
			2.6.0-mr1-cdh5.13.3
		
		
		
			org.apache.hive
			hive-jdbc
			1.1.0-cdh5.13.3
		 


    
	
		org.elasticsearch.client
		transport
		6.3.0
		      
                      
                  com.fasterxml.jackson.core      
                  jackson-core      
                 
                      
                  com.fasterxml.jackson.dataformat      
                  jackson-dataformat-smile      
                 
            
	
	
	
		com.fasterxml.jackson.core
		jackson-core
		2.8.3
	    
	
	
		com.fasterxml.jackson.dataformat
		jackson-dataformat-smile
		2.8.3
	

3、测试一把吧
因为项目有使用spring,那么连接hive 使用的是JdbcTemplate, Junit测试代码如下:

@Autowired
private JdbcTemplate jdbcTemplate;

/**
 * 获取某个库下的所有表
 * ps: 
 * 		testdb 库
 * 
 */
@Test
public void queryTables(){
	List> queryForList = jdbcTemplate.queryForList("SHOW TABLES IN testdb  ");
	System.out.println(queryForList);
}

运行后:

Caused by: java.lang.NoSuchMethodError: io.netty.util.AttributeKey.newInstance(Ljava/lang/String;)Lio/netty/util/AttributeKey;
	at org.elasticsearch.transport.netty4.Netty4Transport.(Netty4Transport.java:232)
	at org.elasticsearch.transport.Netty4Plugin.getSettings(Netty4Plugin.java:56)
	at org.elasticsearch.plugins.PluginsService.lambda$getPluginSettings$0(PluginsService.java:89)
	at java.util.stream.ReferencePipeline$7$1.accept(ReferencePipeline.java:267)
	at java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1380)
	at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:481)
	at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471)
	at java.util.stream.ReduceOps$ReduceOp.evaluateSequential(ReduceOps.java:708)
	at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
	at java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:499)
	at org.elasticsearch.plugins.PluginsService.getPluginSettings(PluginsService.java:89)
	at org.elasticsearch.client.transport.TransportClient.buildTemplate(TransportClient.java:144)
	at org.elasticsearch.client.transport.TransportClient.(TransportClient.java:280)
	at org.elasticsearch.transport.client.PreBuiltTransportClient.(PreBuiltTransportClient.java:128)
	at org.elasticsearch.transport.client.PreBuiltTransportClient.(PreBuiltTransportClient.java:114)
	at org.elasticsearch.transport.client.PreBuiltTransportClient.(PreBuiltTransportClient.java:104)
	at com.perfect.lkt.dao.impl.ElasticSearchConnection.(ElasticSearchConnection.java:35)
	at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
	at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
	at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
	at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
	at org.springframework.beans.BeanUtils.instantiateClass(BeanUtils.java:148)
	... 44 more

呦呵…mmp呀,所谓没事不惹事,来事不怕事的原则,分析吧
4、错误分析
首先看错误类型是,找不到这个方法,难道是缺少netty的jar包?先去确认下依赖的netty jar 有没有下载下来或引用到吧。去maven 工程下的 maven Dependencies 目录下看下, 结果发现有多个版本的netty 包,发生了冲突,如下图:
Maven中同时使用CDH 的hive与ElasticSearch(ES) 内部依赖的netty jar冲突的问题_第1张图片

Maven中同时使用CDH 的hive与ElasticSearch(ES) 内部依赖的netty jar冲突的问题_第2张图片

我们都知道maven 引用jar时,它会把依赖的jar自动引进来,省去我们不少麻烦,但也会很容引起jar包冲突

5、bug解决
既然是jar包冲突的问题,就把冲突的jar 删除,保留一个就好,按照高版本兼容低版本的原则,我们保留高版本的。
那么怎么删除呢,那俩低版本的netty jar 到底是谁的依赖加载进来的呢,是hive 还是ES? 所以我们要先确定 这俩低版本的netty jar 是谁的依赖。
可使用maven的 mvn dependency:tree 命令查看下,他会生成一个jar 依赖的树层机构,执行这个命令有两点要素:
1) 你的maven 的环境变量已经配置了
2)你要到你工程的pom文件的目录下执行
执行成功后如下:
Maven中同时使用CDH 的hive与ElasticSearch(ES) 内部依赖的netty jar冲突的问题_第3张图片
最顶级的那个jar ,就是你在pom 中的引用,看来在spring-data-hadoop 引用中禁掉netty就OK了,可以使用exclusions标签,如下:


			org.springframework.data
			spring-data-hadoop
			2.5.0.RELEASE
		
			
				
					io.netty
					netty-all
				
				
					io.netty
					netty
				
			

再次运行测试,已完美解决,能够同时兼容hive和ES了。

你可能感兴趣的:(日常问题解决)