2017-08-13 50 views
3

我有一個看起來像這樣一些JSON數據存儲空值:在Avro的文件

{ 
    "id": 1998983092, 
    "name": "Test Name 1", 
    "type": "search string", 
    "creationDate": "2017-06-06T13:49:15.091+0000", 
    "lastModificationDate": "2017-06-28T14:53:19.698+0000", 
    "lastModifiedUsername": "[email protected]", 
    "lockedQuery": false, 
    "lockedByUsername": null 
    } 

我能夠在lockedQuery空值添加到GenericRecord對象沒有問題。

GenericRecord record = new GenericData.Record(schema); 
if(json.isNull("lockedQuery")){ 
    record.put("lockedQuery", null); 
} 

但是,後來當我嘗試將該GenericRecord對象寫入avro文件時,我得到一個空指針異常。

File file = new File("~/test.arvo"); 
DatumWriter<GenericRecord> datumWriter = new GenericDatumWriter<>(schema); 
DataFileWriter<GenericRecord> dataFileWriter = new DataFileWriter<>(datumWriter); 
dataFileWriter.create(schema, file); 
for(GenericRecord record: masterList) { 
    dataFileWriter.append(record); // NULL POINTER HERE 
} 

當我運行該代碼時,出現以下異常。有關如何處理空值到Avro文件的任何提示非常感謝。提前致謝。

java.lang.NullPointerException: null of boolean in field lockedQuery of 
com.mydomain.test1.domain.MyAvroRecord 
Exception in thread "main" java.lang.RuntimeException: 
org.apache.avro.file.DataFileWriter$AppendWriteException: 
java.lang.NullPointerException: null of boolean in field lockedQuery of 
com.mydomain.test1.domain.MyAvroRecord 
at com.mydomain.avro.App.main(App.java:198) 
Caused by: org.apache.avro.file.DataFileWriter$AppendWriteException: 
java.lang.NullPointerException: null of boolean in field lockedQuery of 
com.mydomain.test1.domain.MyAvroRecord 
at org.apache.avro.file.DataFileWriter.append(DataFileWriter.java:308) 

編輯:這裏是MyAvroRecord

public class MyAvroRecord { 
    long id; 
    String name; 
    String type; 
    Date timestamp; 
    Date lastModifcationDate; 
    String lastModifiedUsername; 
    Boolean lockedQuery; 
+1

這可能會有助於「MyAvroRecord」的定義。我並不特別是Avro專家,但通常在Java中,您不能將'null'存儲在'boolean'(小寫)字段中,因爲它是一個原語。如果你想在一個布爾值中存儲一個空值,你必須使用'Boolean'(大寫),它是一個Object,可以爲空。 –

+0

感謝您的建議。我從MyAvroRecord添加了成員​​定義。模式文件與類型匹配。我正在使用布爾值並切換到布爾對象,但仍然具有相同的空指針。當我將「false」作爲默認值存儲時,錯誤消失,但我仍然不能在基於對象的布爾值中使用null。 – mba12

回答

4

爲了能夠設置的Avro場null你應該允許這架Avro架構,通過增加null作爲可能的類型領域之一。就以實例來看看從文件的Avro:

{ 
    "type": "record", 
    "name": "MyRecord", 
    "fields" : [ 
    {"name": "userId", "type": "long"},    // mandatory field 
    {"name": "userName", "type": ["null", "string"]} // optional field 
    ] 
} 

這裏userName被聲明爲複合型這可能是要麼nullstring。這種定義允許將userName字段設置爲空。由於對比userId只能包含長整型值,因此嘗試將userId設置爲空將導致NullPointerException