使用Sqoop导入Parquet文件中的脏值

时间:2017-06-21 12:28:45

标签: hadoop sqoop parquet

我使用Sqoop1(版本1.4.6,CDH 5.7.4)从Oracle导入 Sqoop创建了一个临时的Parquet Hive Table,然后我使用Hive(beeline)到insert into目的地表。
这个双步摄取是由于目标表具有与Sqoop的不同的列类型映射,因此使用insert into我可以动态转换它们。我也在飞行中压缩Snappy。这工作正常。目前,我没有控制Sqoop的import命令的类型映射。在我的特定情况下,这太复杂了。

一开始我在flatfile中导入,但是我的字段包含一堆字符,这些字符会破坏我的行,如换行符,回车符,制表符等等。出于这个原因和其他原因,我决定搬到Parquet(不幸的是,avro不是一个选项,因为我们使用的工具不支持它。)
在我看来,像Parquet这样的二进制格式在处理这些字符时不会有问题。

原来我错了。
select * from table显示一些损坏的行,经过大量调试后,我发现有些字段分为两部分。我能够看到一个截断的记录(根据Oracle源代码),其中一部分是另一行(单独)。 由于我在Sqoop中使用自由形式查询,解决方案是使用替换函数REPLACE(REPLACE(REPLACE(note, chr(10), ' '), chr(13), ' '), chr(09), ' ') AS NOTE在提取时替换字符。

当然这显然是错误的方法,因为可能有其他字段有脏字符,并且还可能有其他脏字符。

所以问题是:

  1. 我错误地认为Parquet(或avro,或其他二进制格式) 不会关心字段内的字符吗?
  2. 我做错了吗?
  3. 如何防止出现此类问题?
  4. 由于

1 个答案:

答案 0 :(得分:1)

数目:

  1. 你错了。 Parquet不会受到内线分隔符(如换行符或制表符等)的影响。
  2. 否。实际上,您的数据存储在镶木地板文件中,与oracle中的数据相同。然而;当您将数据打印到屏幕时,根据您的客户端(假设您使用配置单元客户端),您会看到结果已损坏,因为服务器很可能以明文形式将数据发送到客户端。
  3. 为了防止这种情况,在打印数据时,您可以使用配置单元功能:regexp_replace(your_text_column, "\t|\n|\r\n", " ")。这会阻止您的客户<&em>混淆&#34;。
  4. 此外,您不必对包含此类特定字符的数据使用镶木地板。我认为hive的默认分隔符(\ 001)就足够了。非打印字符不太可能出现在文本字段中。