Sqoop将数据从oracle导入到hive时,数据错位的问题解决

36 篇文章 0 订阅
7 篇文章 0 订阅

问题一:导入的列有换行符等其他字符如何解决

在使用sqoop将数据从oracle导入hive时,对数据进行验证,发现hive中的数据比oracle的多,然后发现多出来的数据严重错位,大量字段为null

怀疑是某些字段含有了hive默认的分隔符,如“\n”,“\r”,“\01”

解决办法是增加参数--hive-drop-import-delims来解决

Hive will have problems using Sqoop-imported data if your database’s rows contain string fields that have Hive’s default row delimiters (\nand\rcharacters) or column delimiters (\01characters) present in them. You can use the--hive-drop-import-delimsoption to drop those characters on import to give Hive-compatible text data. Alternatively, you can use the--hive-delims-replacementoption to replace those characters with a user-defined string on import to give Hive-compatible text data. These options should only be used if you use Hive’s default delimiters and should not be used if different delimiters are specified.

bin/sqoop import --connect jdbc:oracle:thin:@172.21.62.200:1521:ORCL 
--username fetchuser 
--password fetch1q2w3e4R
--table TB_NEWS --fields-terminated-by '\t'
--hive-drop-import-delims
--map-column-java CONTENT=String
--hive-import --hive-overwrite 
--create-hive-table --hive-table news.TB_NEWS_TEST --delete-target-dir 

可以从中看出,“\n”、“\r”是hive默认的行分隔符,而“\01”则是hive默认的列分隔符,如果数据中含有这些分隔符,在不处理的情况下,hive就会对数据进行错误的分割,造成数据错位以及数据增多的问题,解决办法就是

第一种,使用--hive-drop-import-delims 来去除这些字符

第二种,使用--hive-delims-replacement来替换这些字符

问题二:oracle数据库中Date类型倒入到hive中出现时分秒截断

参考地址:http://www.cnblogs.com/wrencai/p/3935877.html

用sqoop将oracle数据表倒入到hive中,oracle中Date型数据会出现时分秒截断问题,只保留了‘yyyy-MM-dd',而不是’yyyy-MM-dd HH24:mi:ss'格式的,后面的‘HH24:mi:ss’被自动截断了,在对时间要求到秒级的分析处理中这种截断会产生问题。

在用sqoop倒入数据表是,添加--map-column-hive 和--map-column-java参数,来改变数据表列的默认映射类型(默认情况下sqoop倒入hive中Date类型会被映射成String),将Date列映射成Timestamp类型,在我的问题中我是通过sqoop创建job,进行数据表按时间增量倒入的,PASSTIME列的数据类型是Date,脚本如下:

sqoop job --create jobimport2hiveofv_vehicleinfo 
--import --hive-import 
--map-column-java PASSTIME=java.sql.Timestamp 
--map-column-hive PASSTIME=TIMESTAMP 
--incremental append 
--connect jdbc:oracle:thin:@118.228.196.29:1521/pmptgdbanalyze --username SAN --password PASS 
--verbose -m 1 
--bindir /opt/sqoop-1.4.4/lib 
--table V_VEHICLEINFO 
--check-column PASSTIME 
--last-value '2014-04-20 12:00:00'

注意:
(1)java.sql.Timestamp要带包名写全,否则可能会出错。
(2)--map-column-java和--map-column-hive连个参数都要显示给出,如果只给出--map-column-hive那么只会改变hive中表列的数据类型,
而codegen生成的Tablename.java源文件中还会是java.sql.Date类型,这样在转换成hive表中的TIMESTAMP类型时,就会出错导致hive中的PASSTIME字段全部为null。
原因可能是由于Date类型默认格式‘yyyy-M-dd',而转化到hive Timestamp类型时,严格要求按照’yyyy-mm-dd hh:mm:ss[.f...]'格式转换,参见hive官网timestamp格式说明。

(3)如果不设置--map-column-hive参数,只设置--map-column-java 为java.sq..Timestamp,也可以实现数据精确到时分秒,只不过以string类型保存到列hive中。
事实上,在我实验后,发现如果指定--mapcolumn-hive参数为timestamp,在java中使用对应的时间where比较条件时,无法查出数据,
反而,指定--map-column-hive参数为string,却能够在hive中和java代码中都能够使用时间列参与查询。

因此在设计Hive表的时候,一般都把字段设置成为String类型,这样方便处理。
 

原文链接:https://www.2cto.com/database/201803/733896.html

原文链接:https://blog.csdn.net/jiangsanfeng1111/article/details/53334819/

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值