avro 模式中的可选数组

Posted

技术标签:

【中文标题】avro 模式中的可选数组【英文标题】:optional array in avro schema 【发布时间】:2012-03-14 03:14:01 【问题描述】:

我想知道是否可以有一个可选数组。 让我们假设这样的架构:

 
    "type": "record",
    "name": "test_avro",
    "fields" : [
        "name": "test_field_1", "type": "long",
        "name": "subrecord", "type": [
         "type": "record",
         "name": "subrecord_type",
           "fields":["name":"field_1", "type":"long"]
          ,"null"]
    ,
    "name": "simple_array",
    "type":
        "type": "array",
        "items": "string"
      
    
  ]

尝试在没有“simple_array”的情况下写入 avro 记录会导致数据文件写入器中出现 NPE。 对于子记录,这很好,但是当我尝试将数组定义为可选时:

"name": "simple_array",
 "type":[
   "type": "array",
   "items": "string"
   , "null"]

它不会导致 NPE 而是运行时异常:

AvroRuntimeException: Not an array schema: ["type":"array","items":"string","null"]

谢谢。

【问题讨论】:

【参考方案1】:

我认为你想要的是 null 和数组的联合:


    "type":"record",
    "name":"test_avro",
    "fields":[
            "name":"test_field_1",
            "type":"long"
        ,
        
            "name":"subrecord",
            "type":[
                    "type":"record",
                    "name":"subrecord_type",
                    "fields":[
                            "name":"field_1",
                            "type":"long"
                        
                    ]
                ,
                "null"
            ]
        ,
        
            "name":"simple_array",
            "type":["null",
                
                    "type":"array",
                    "items":"string"
                
            ],
            "default":null
        
    ]

当我在 Python 中将上述模式与示例数据一起使用时,结果如下(schema_string 是上述 json 字符串):

>>> from avro import io, datafile, schema
>>> from json import dumps
>>> 
>>> sample_data = 'test_field_1':12L
>>> rec_schema = schema.parse(schema_string)
>>> rec_writer = io.DatumWriter(rec_schema)
>>> rec_reader = io.DatumReader()
>>> 
>>> # write avro file
... df_writer = datafile.DataFileWriter(open("/tmp/foo", 'wb'), rec_writer, writers_schema=rec_schema)
>>> df_writer.append(sample_data)
>>> df_writer.close()
>>> 
>>> # read avro file
... df_reader = datafile.DataFileReader(open('/tmp/foo', 'rb'), rec_reader)
>>> print dumps(df_reader.next())
"simple_array": null, "test_field_1": 12, "subrecord": null

【讨论】:

对 java 列表有同样的问题,你的回答解决了我的问题。谢谢! 我得到了同样的错误。在我的设置中,我尝试使用 MapReduce Java 程序处理 Avro 文件。作业很成功。数据管道的下一个阶段是在转换后的数据上创建一个配置单元表(avroSerde),该表也成功创建但是当我尝试使用 hql 查询表时(它又执行了一个 mapreduce 作业),作业失败带有“错误:java.lang.RuntimeException: org.apache.hadoop.hive.ql.metadata.HiveException: Hive Runtime Error while processing writable”

以上是关于avro 模式中的可选数组的主要内容,如果未能解决你的问题,请参考以下文章

表单输入文本模式中的可选字符

Java 中的可选 orElse 可选

如何在 Avro 中将记录与地图混合?

是否可以在 Avro 模式中有一个可选字段(即该字段根本不会出现在 .json 文件中)?

AngularJS 表单。 JSON中的可选属性[重复]

Python regex - 字符串中的可选字段