Avro Decoder with support optional fields in JSON. Based on Celos fork.
Gradle
dependencies { implementation 'com.github.goodforgod:avro-json-optional-decoder:1.1.6' }Maven
<dependency> <groupId>com.github.goodforgod</groupId> <artifactId>avro-json-optional-decoder</artifactId> <version>1.1.6</version> </dependency>Library is Java 1.8 compatible.
Library is compatible with different Apache Avro versions. Please use compatible library version for your Apache Avro version.
| Apache Avro Version | Library Version |
|---|---|
| 1.9.2 | 1.1.6 |
| 1.8.2 | 1.0.1 |
For given AVRO Schema.
{ "type" : "record", "name" : "Person", "fields" : [ { "name" : "username", "type" : "string" }, { "name" : "name", "type" : [ "null", "string" ] } ] }Such JSON will be treated correctly.
{"username":"user1","name":null}However, such JSON (name field is missing).
{"username":"user1"}Will fail with:
org.apache.avro.AvroTypeException: Expected field name not found: name JsonOptionalDecoder provided by library allow correct JSON validation in both cases, decoding JSON that doesn't specify optional values, provided they have defaults.
Check guides on how-to-use Avro Decoders.
Be aware JsonOptionalDecoder is not thread-safe.
For given AVRO Schema.
{ "name": "Test", "type": "record", "fields": [ { "name": "required", "type": "string" }, { "name": "inner", "type": [ "null", { "name": "inner", "type": "record", "fields": [ { "name": "req", "type": "string" } ] } ] } ] }This input will be correct:
{"required":"u", "inner": {"req": "q"}}As this input will be correct:
{"required":"u"}If property default is not specified, then missing field will be treated as avro null value.
{ "name" : "name", "type" : [ "null", "string" ] }You can specify default value as per AVRO specification.
Keep in mind you mind putting type corresponding to default value first, due to AVRO incorrect union type validation.
{ "name" : "name", "type" : [ "string", "null" ], "default": "bob" }Change
Decoder decoder = DecoderFactory.get().jsonDecoder(SCHEMA, INPUT_STREAM_OR_STRING);With
Decoder decoder = new JsonOptionalDecoder(SCHEMA, INPUT_STREAM_OR_STRING);This project licensed under the MIT - see the LICENSE file for details.