Skip to content

Commit 020c67e

Browse files
committed
AVRO-4135: [Java] JSON decoding unqualified union types
Support unqualified type references for unions when decoding them from json. AVRO-2287 makes it unclear if type reference for a JSON encoded union needs to be qualified or not. Today all encoders use the fully qualified types except the C JSON encoder which uses the unqualified type. In this patch we make the java JSON Decoder more lenient and let it fallback to unqualified types names when no qualified type name matches. Which matches the behavior currently implemented in the Javascript Json decoder. This patch is an alternative for apache#3373 where it is proposed to update the C library instead.
1 parent 60796e5 commit 020c67e

2 files changed

Lines changed: 22 additions & 0 deletions

File tree

lang/java/avro/src/main/java/org/apache/avro/io/parsing/Symbol.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -475,6 +475,16 @@ public int findLabel(String label) {
475475
return i;
476476
}
477477
}
478+
// AVRO-4135 We are a bit more flexible here since we have to deal with the C
479+
// serializer being less strict, so
480+
// we fall back to looking up unqualified names.
481+
for (int i = 0; i < labels.length; i++) {
482+
String candidate = labels[i];
483+
if (candidate != null && candidate.length() > label.length()
484+
&& candidate.charAt(candidate.length() - label.length() - 1) == '.' && candidate.endsWith(label)) {
485+
return i;
486+
}
487+
}
478488
}
479489
return -1;
480490
}

lang/java/avro/src/test/java/org/apache/avro/io/TestJsonDecoder.java

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -92,4 +92,16 @@ void testIntWithError() throws IOException {
9292
JsonDecoder decoder = DecoderFactory.get().jsonDecoder(schema, record);
9393
Assertions.assertThrows(AvroTypeException.class, () -> reader.read(null, decoder));
9494
}
95+
96+
@Test
97+
void testUnionTypeQualification() throws Exception {
98+
final Schema schema = SchemaBuilder.unionOf().nullType().and()
99+
.type(SchemaBuilder.record("r").namespace("space").fields().endRecord()).endUnion();
100+
GenericDatumReader<GenericRecord> reader = new GenericDatumReader<>(schema, schema);
101+
JsonDecoder decoder = DecoderFactory.get().jsonDecoder(schema, "{\"space.r\": {}}");
102+
assertEquals("space.r", reader.read(null, decoder).getSchema().getFullName());
103+
// AVRO-4135: C json encoder uses unqualified types.
104+
decoder = DecoderFactory.get().jsonDecoder(schema, "{\"r\": {}}");
105+
assertEquals("space.r", reader.read(null, decoder).getSchema().getFullName());
106+
}
95107
}

0 commit comments

Comments
 (0)