操作hadoop中的行数据以添加缺失的列

操作hadoop中的行数据以添加缺失的列

问题描述:

我有来自存储在hdfs中的IIS的日志文件,但由于Web服务器配置,某些日志没有所有列或它们以不同的顺序出现。我想生成具有共同模式的文件,因此我可以在它们上面定义一个Hive表。操作hadoop中的行数据以添加缺失的列

实施例良好日志:

#Fields: date time s-ip cs-method cs-uri-stem useragent 
2013-07-16 00:00:00 10.1.15.8 GET /common/viewFile/1232 Mozilla/5.0+Chrome/27.0.1453.116 

实施例记录与缺少的列(CS-方法和用户代理缺失):

#Fields: date time s-ip cs-uri-stem 
2013-07-16 00:00:00 10.1.15.8 /common/viewFile/1232 

与缺少的列日志需要被映射到完全模式等这个:

#Fields: date time s-ip cs-method cs-uri-stem useragent 
2013-07-16 00:00:00 10.1.15.8 null /common/viewFile/1232 null 

不好的日志可以有任何的组合列已启用且顺序不同。

如何根据日志文件中的Fields行将可用列映射到完整模式?

编辑: 通常我会通过定义我的列架构作为字典映射列名索引来解决这个问题。即:col ['date'] = 0 col ['time'] = 1等等然后我会从文件中读取#Fields行并解析出启用的列并生成头文件字典映射头文件名到文件中的列索引。然后,对于剩余的数据行,我通过索引知道它的标题,通过header =列名将其映射到我的列模式,然后按正确的顺序生成新行,并插入空数据的缺失列。我的问题是我不明白如何在hadoop中执行此操作,因为每个地图都是单独执行的,因此如何与每个地图共享#Fields信息?

+0

这是不是一个真正的猪的问题。告诉我们你将如何以任何语言解决这个问题,包括伪代码。如果你被赋予了一个专门的领域,你将如何确定它的含义以及它应该进入哪一列? –

+0

我加了解释说明如果我可以在处理它们的时候从每个文件中提取和分享字段信息。否则,我认为RegexSerDe应该能够映射这些字段,但是当文件中有可用的数据时不会浪费? – smashbourne

您可以使用this将标题应用于创建地图的列。从那里,你可以使用UDF,如:

myudf.py

#!/usr/bin/python 

@outputSchema('newM:map[]') 
def completemap(M): 
    if M is None: 
     return None 
    to_add = ['A', 'D', 'F'] 
    for item in to_add: 
     if item not in M: 
      M[item] = None 
    return M 

@outputSchema('A:chararray, B:chararray, C:chararray, D:chararray, E:chararray, F:chararray') 
def completemap_v2(M): 
    if M is None: 
     return (None, 
       None, 
       None, 
       None, 
       None, 
       None) 
    return (M.get('A', None), 
      M.get('B', None), 
      M.get('C', None), 
      M.get('D', None), 
      M.get('E', None), 
      M.get('F', None)) 

要在丢失的元组添加到地图。

样品输入:

csv1.in    csv2.in 
-------   --------- 
A|B|C    D|E|F 
Hello|This|is  PLEASE|WORK|FOO 
FOO|BAR|BING  OR|EVERYTHING|WILL 
BANG|BOSH   BE|FOR|NAUGHT 

示例脚本:

A = LOAD 'tests/csv' USING myudfs.ExampleCSVLoader('\\|') AS (M:map[]); 
B = FOREACH A GENERATE FLATTEN(myudf.completemap_v2(M)); 

输出:

B: {null::A: chararray,null::B: chararray,null::C: chararray,null::D: chararray,null::E: chararray,null::F: chararray} 
(,,,,,) 
(,,,PLEASE,WORK,FOO) 
(,,,OR,EVERYTHING,WILL) 
(,,,BE,FOR,NAUGHT) 
(,,,,,) 
(Hello,This,is,,,) 
(FOO,BAR,BING,,,) 
(BANG,BOSH,,,,)