diff --git a/lang/java/avro/src/main/java/org/apache/avro/SchemaCompatibility.java b/lang/java/avro/src/main/java/org/apache/avro/SchemaCompatibility.java index 3e5628d9b3b..8b6a2839ad6 100644 --- a/lang/java/avro/src/main/java/org/apache/avro/SchemaCompatibility.java +++ b/lang/java/avro/src/main/java/org/apache/avro/SchemaCompatibility.java @@ -324,8 +324,10 @@ private SchemaCompatibilityResult calculateCompatibility(final Schema reader, fi // Reader compatible with all branches of a writer union is compatible if (writer.getType() == Schema.Type.UNION) { + int index = 0; for (Schema s : writer.getTypes()) { - result = result.mergedWith(getCompatibility(reader, s)); + result = result.mergedWith(getCompatibility(Integer.toString(index), reader, s, location)); + index++; } return result; } diff --git a/lang/java/avro/src/test/java/org/apache/avro/TestSchemaCompatibility.java b/lang/java/avro/src/test/java/org/apache/avro/TestSchemaCompatibility.java index f5e24597232..275bcfafede 100644 --- a/lang/java/avro/src/test/java/org/apache/avro/TestSchemaCompatibility.java +++ b/lang/java/avro/src/test/java/org/apache/avro/TestSchemaCompatibility.java @@ -233,6 +233,22 @@ void unionReaderWriterSubsetIncompatibility() { final Schema unionReader = Schema.createUnion(list(INT_SCHEMA, STRING_SCHEMA)); final SchemaPairCompatibility result = checkReaderWriterCompatibility(unionReader, unionWriter); assertEquals(SchemaCompatibilityType.INCOMPATIBLE, result.getType()); + assertEquals("/2", result.getResult().getIncompatibilities().get(0).getLocation()); + } + + @Test + void unionWriterSimpleReaderIncompatibility() { + Schema mandatorySchema = SchemaBuilder.record("Account").fields().name("age").type().intType().noDefault() + .endRecord(); + Schema optionalSchema = SchemaBuilder.record("Account").fields().optionalInt("age").endRecord(); + + SchemaPairCompatibility compatibility = checkReaderWriterCompatibility(mandatorySchema, optionalSchema); + + assertEquals(SchemaCompatibilityType.INCOMPATIBLE, compatibility.getType()); + + Incompatibility incompatibility = compatibility.getResult().getIncompatibilities().get(0); + assertEquals("reader type: INT not compatible with writer type: NULL", incompatibility.getMessage()); + assertEquals("/fields/0/type/0", incompatibility.getLocation()); } // ----------------------------------------------------------------------------------------------- diff --git a/lang/java/avro/src/test/java/org/apache/avro/TestSchemaCompatibilityTypeMismatch.java b/lang/java/avro/src/test/java/org/apache/avro/TestSchemaCompatibilityTypeMismatch.java index ba625448da3..247e40404ba 100644 --- a/lang/java/avro/src/test/java/org/apache/avro/TestSchemaCompatibilityTypeMismatch.java +++ b/lang/java/avro/src/test/java/org/apache/avro/TestSchemaCompatibilityTypeMismatch.java @@ -90,11 +90,11 @@ public static Stream data() { Arguments.of(ENUM2_AB_SCHEMA, INT_SCHEMA, "reader type: ENUM not compatible with writer type: INT", "/"), Arguments.of(FLOAT_SCHEMA, INT_LONG_FLOAT_DOUBLE_UNION_SCHEMA, - "reader type: FLOAT not compatible with writer type: DOUBLE", "/"), + "reader type: FLOAT not compatible with writer type: DOUBLE", "/3"), Arguments.of(LONG_SCHEMA, INT_FLOAT_UNION_SCHEMA, "reader type: LONG not compatible with writer type: FLOAT", - "/"), + "/1"), Arguments.of(INT_SCHEMA, INT_FLOAT_UNION_SCHEMA, "reader type: INT not compatible with writer type: FLOAT", - "/"), + "/1"), Arguments.of(INT_LIST_RECORD, LONG_LIST_RECORD, "reader type: INT not compatible with writer type: LONG", "/fields/0/type"),