Elasticsearch-Hive
1 下载和安装ES-Hadoop
- 下载
- 上传jar到Hive客户端所在机器
解压下载的ZIP包,进入elasticsearch-hadoop/dist
,把elasticsearch-hadoop.jar
文件拷贝到Hive客户端所在机器。 - 安装
打开hive beeline后,执行:
ADD JAR /path/elasticsearch-hadoop.jar;
或者直接把elasticsearch-hadoop.jar传入$HIVE_HOME/auxlib
目录下。(没有调试成功)
2 创建Hive外表
所有相关配置请参考:
2.1 创建示例
创建存储在ES但由Hive管理的外表:
CREATE EXTERNAL TABLE artists (...)
STORED BY 'org.elasticsearch.hadoop.hive.EsStorageHandler'
TBLPROPERTIES('es.resource' = 'radio/artists',
'es.index.auto.create' = 'false',
'es.query' = '{ "query" : { "range" : { "time" : { "gte" : "now+8h-2d/d", "lt" : "now+8h-1d/d", "format" : "yyyy-MM-dd hh:mm:ss" } } } }',
'es.read.metadata' = 'true',
'es.mapping.names' = 'id:_metadata._id',
'es.mapping.date.rich' = 'false',
'es.nodes' = '192.168.10.1:9200,192.168.10.2:9200,192.168.10.3:9200');
- EsStorageHandler
使用EsStorageHandler - es.resource
ES index/type - es.index.auto.create
是否同时自动创建es index - es.query
默认为空,即查询index所有数据。还可以使用?uri_query、query dsl、外部资源描述 - es.read.metadata
默认false。设为true可使得查询结果包括ES doc的元数据,如id、version。 - es.mapping.names
Hive-ES字段映射,见2.2章节。我这里是将创建的Hive外表中的id字段映射为了ES doc中的那个id字段。这里可以只把需要映射的字段写出来,其他字段名字相同可以不写。 - es.mapping.date.rich
默认true,会创建富类型的Date。设为false则会返回为基本类型(String或long)。当使用Date类型且不是标准的 ISO 8601 格式时可能导致解析出错,可设为false解决。关于ES-Hadoop时间和字段映射请参阅Time/Date mapping - es.nodes
默认localhost。请填写部分ES节点地址,可自动发现集群中其它节点。
2.2 字段映射
默认,Elasticsearch-Hadoop使用Hive表的元数据(字段名和类型)来映射数据到ES。如果想改变映射可使用es.mapping.names
,如下:
Hive_field_name:Elasticsearch_field_name,Hive_field_name2:Elasticsearch_field_name2
示例如下:
CREATE EXTERNAL TABLE artists (...)
STORED BY 'org.elasticsearch.hadoop.hive.EsStorageHandler'
TBLPROPERTIES('es.resource' = 'radio/artists',
'es.mapping.names' = 'date:@timestamp, url:url_123');
注意:Hive不区分大小写,但ES区分,所以可能导致不正确的查询。为此,Elasticsearch-Hadoop总是将Hive列名转为小写。我们使用的时候必须都用小写,除了Hive命令本身以外。
还有一点就是如果查询错误或不存在的字段会展示为NULL
。
2.3 字段转换
未开启自动创建index功能时字段转换如下,如果开启则参考:
3 从Hive外表(ES)读取数据
3.1 创建Hive外表
CREATE EXTERNAL TABLE artists (
id BIGINT,
name STRING,
links STRUCT<url:STRING, picture:STRING>)
STORED BY 'org.elasticsearch.hadoop.hive.EsStorageHandler'
TBLPROPERTIES('es.resource' = 'radio/artists',
'es.query' = '?q=me*');
- es.query
3.2 读取表
-- stream data from Elasticsearch
SELECT * FROM artists;
3.3 数据从外表写入自己建的Hive表
不要直接使用该外表,应该将数据导入自己建的表后使用。导入方式可以用:
insert overwrite table dw.dwd_artist_data_1d partition (ds='20200303')
select id,regexp_replace(name, '\n|\r', '') from artists;
常见问题
- EsHadoopParsingException: Cannot parse value
- EsHadoopParsingException: Cannot parse value
- 自定义时间解析器来解决EsHadoopParsingException
- Hive连接ES问题汇总
- java.lang.NoClassDefFoundError: org/apache/commons/httpclient/URIException
少包问题都可以类似处理,即先将报错的jar包上传到hdfs,然后在执行sql前先执行add jar hdfs:///xxxx/xxx.jar
。这样就不会有问题了。
参考文档
- Elasticsearch for Apache Hadoop » Apache Hive
- Hive表导入Elasticsearch
- Elasticsearch与Hive的数据互导
- Hive如何添加第三方JAR
- hive中如何让addjar只执行一次