当我尝试使用以下架构解码Avro记录时,我收到以下错误:
{
"type":"record",
"name":"Example",
"namespace":"com.example.test",
"fields":[
{
"name":"nestedExample",
"type":{
"type":"record",
"name":"NestedExample",
"namespace":"com.example.test.Example$",
"fields":[]
}
}
]
}
java.lang.ClassCastException: org.apache.avro.generic.GenericData $ Record无法转换为 com.example.test.Example $ .NestedExample at com.example.test.Example.put(Example.java:40)at org.apache.avro.generic.GenericData.setField(GenericData.java:573)at at org.apache.avro.generic.GenericData.setField(GenericData.java:590)at at org.apache.avro.generic.GenericDatumReader.readField(GenericDatumReader.java:193) 在 org.apache.avro.generic.GenericDatumReader.readRecord(GenericDatumReader.java:183) 在 org.apache.avro.generic.GenericDatumReader.read(GenericDatumReader.java:151) 在 org.apache.avro.generic.GenericDatumReader.read(GenericDatumReader.java:142)
这似乎与嵌套类型的命名空间有关。注意:如果在具有嵌套类的Java类上使用反射,则这就是Avro反射指定命名空间的方式。如果我将命名空间更改为与Example相同,那么我可以正确解码记录。 当嵌套记录类型位于自己的命名空间中时,如何解码具有嵌套记录类型的记录?
我正在使用Avro maven插件生成Java类。我的Avro版本是1.7.7。这是我用来解码Example记录的代码:
public class Avro_NestedRecord {
List<Example> examples;
@Before
public void setUp() throws Exception {
examples = Arrays.asList(new Example[] {
Example.newBuilder()
.setNestedExample(new com.example.test.Example$.NestedExample())
.build()
});
}
@Test
public void thisIsHowWeCodeSpecificRecordsDirectly() throws IOException {
Schema schema = Example.getClassSchema();
// write
ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
BinaryEncoder encoderInstance = EncoderFactory.get().directBinaryEncoder(outputStream, null);
SpecificDatumWriter<Example> specificDatumWriter = new SpecificDatumWriter<Example>(schema);
specificDatumWriter.write(examples.get(0), encoderInstance);
// read
ByteArrayInputStream inStream = new ByteArrayInputStream(outputStream.toByteArray());
BinaryDecoder decoderInstance = DecoderFactory.get().directBinaryDecoder(inStream, null);
SpecificDatumReader<Example> specificDatumReader = new SpecificDatumReader<Example>(schema);
specificDatumReader.read(null, decoderInstance);
}
}