You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@avro.apache.org by rs...@apache.org on 2022/09/14 18:32:59 UTC
[avro] 01/02: AVRO-2831: add ResolverTest (#1858)
This is an automated email from the ASF dual-hosted git repository.
rskraba pushed a commit to branch branch-1.11
in repository https://gitbox.apache.org/repos/asf/avro.git
commit 7464920d0577c8466f3cd6165538fc0bfb05d089
Author: clesaec <51...@users.noreply.github.com>
AuthorDate: Fri Sep 9 18:54:06 2022 +0200
AVRO-2831: add ResolverTest (#1858)
* AVRO-2831: add unit test on Avro
* AVRO-2831: add unit test on Avro
* AVRO-2831: Add license to TestResolver.java
---
.../src/main/java/org/apache/avro/Resolver.java | 10 +-
.../test/java/org/apache/avro/TestResolver.java | 122 +++++++++++++++++++++
2 files changed, 123 insertions(+), 9 deletions(-)
diff --git a/lang/java/avro/src/main/java/org/apache/avro/Resolver.java b/lang/java/avro/src/main/java/org/apache/avro/Resolver.java
index 9db847c2c..117c9e391 100644
--- a/lang/java/avro/src/main/java/org/apache/avro/Resolver.java
+++ b/lang/java/avro/src/main/java/org/apache/avro/Resolver.java
@@ -286,16 +286,10 @@ public class Resolver {
throw new IllegalArgumentException("Only use when reader and writer are different.");
Schema.Type wt = w.getType();
switch (r.getType()) {
- case INT:
- switch (wt) {
- case INT:
- return true;
- }
- break;
+
case LONG:
switch (wt) {
case INT:
- case LONG:
return true;
}
break;
@@ -303,7 +297,6 @@ public class Resolver {
switch (wt) {
case INT:
case LONG:
- case FLOAT:
return true;
}
break;
@@ -312,7 +305,6 @@ public class Resolver {
case INT:
case LONG:
case FLOAT:
- case DOUBLE:
return true;
}
break;
diff --git a/lang/java/avro/src/test/java/org/apache/avro/TestResolver.java b/lang/java/avro/src/test/java/org/apache/avro/TestResolver.java
new file mode 100644
index 000000000..1d3919319
--- /dev/null
+++ b/lang/java/avro/src/test/java/org/apache/avro/TestResolver.java
@@ -0,0 +1,122 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * https://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.avro;
+
+import java.io.IOException;
+import java.util.Arrays;
+
+import org.apache.avro.data.TimeConversions;
+import org.apache.avro.generic.IndexedRecord;
+import org.apache.avro.io.DatumReader;
+import org.apache.avro.io.DecoderFactory;
+import org.apache.avro.io.FastReaderBuilder;
+import org.apache.avro.io.JsonDecoder;
+import org.hamcrest.MatcherAssert;
+import org.hamcrest.Matchers;
+import org.junit.jupiter.api.Assertions;
+import org.junit.jupiter.api.Test;
+
+class TestResolver {
+
+ /**
+ * Test promote action INT -> LONG, with logical type for LONG.
+ */
+ @Test
+ void resolveTime() {
+ final Schema writeSchema = Schema.create(Schema.Type.INT);
+ final Schema readSchema = new TimeConversions.TimeMicrosConversion().getRecommendedSchema(); // LONG
+
+ Resolver.Action action = Resolver.resolve(writeSchema, readSchema);
+ Assertions.assertNotNull(action);
+ MatcherAssert.assertThat("Wrong class for action", action, Matchers.instanceOf(Resolver.Promote.class));
+ Assertions.assertEquals(action.type, Resolver.Action.Type.PROMOTE);
+ Assertions.assertNotNull(action.logicalType);
+ }
+
+ /**
+ * Test union type with promote action INT -> LONG, with logical type for LONG.
+ */
+ @Test
+ void resolveUnion() {
+ final Schema schema = new TimeConversions.TimeMicrosConversion().getRecommendedSchema();
+
+ final Schema writeSchema = Schema.createUnion(Schema.create(Schema.Type.INT));
+ final Schema readSchema = Schema.createUnion(schema);
+
+ Resolver.Action action = Resolver.resolve(writeSchema, readSchema);
+ Assertions.assertNotNull(action);
+ Assertions.assertEquals(action.type, Resolver.Action.Type.WRITER_UNION);
+ MatcherAssert.assertThat("Wrong class for action", action, Matchers.instanceOf(Resolver.WriterUnion.class));
+
+ Assertions.assertEquals(1, ((Resolver.WriterUnion) action).actions.length);
+ Resolver.Action innerAction = ((Resolver.WriterUnion) action).actions[0];
+
+ MatcherAssert.assertThat("Wrong class for action", innerAction, Matchers.instanceOf(Resolver.ReaderUnion.class));
+ Resolver.ReaderUnion innerUnionAction = (Resolver.ReaderUnion) innerAction;
+ Resolver.Action promoteAction = innerUnionAction.actualAction;
+ Assertions.assertEquals(promoteAction.type, Resolver.Action.Type.PROMOTE);
+ Assertions.assertNotNull(promoteAction.logicalType);
+ }
+
+ @Test
+ void resolveEnum() throws IOException {
+ final Schema writeSchema = Schema.createEnum("myEnum", "", "n1", Arrays.asList("e1", "e3", "e4"));
+ final Schema readSchema = Schema.createEnum("myEnum", "", "n1", Arrays.asList("e1", "e2", "e3"), "e2");
+
+ Resolver.Action action = Resolver.resolve(writeSchema, readSchema);
+ Assertions.assertNotNull(action);
+ Assertions.assertEquals(action.type, Resolver.Action.Type.ENUM);
+ MatcherAssert.assertThat("Wrong class for action", action, Matchers.instanceOf(Resolver.EnumAdjust.class));
+ Resolver.EnumAdjust adjust = (Resolver.EnumAdjust) action;
+
+ Assertions.assertArrayEquals(new int[] { 0, 2, 1 }, adjust.adjustments);
+ Assertions.assertEquals("e1", adjust.values[0].toString());
+ Assertions.assertEquals("e3", adjust.values[1].toString());
+ Assertions.assertEquals("e2", adjust.values[2].toString());
+
+ FastReaderBuilder reader = FastReaderBuilder.get();
+ Schema writeRecord = Schema.createRecord("rec1", "", "", false,
+ Arrays.asList(new Schema.Field("f1", writeSchema, "")));
+ Schema readRecord = Schema.createRecord("rec1", "", "", false,
+ Arrays.asList(new Schema.Field("f1", readSchema, "")));
+ DatumReader<Object> datumReader = reader.createDatumReader(writeRecord, readRecord);
+ JsonDecoder e2 = DecoderFactory.get().jsonDecoder(readRecord, "{ \"f1\" : \"e2\" }");
+ Object read = datumReader.read(null, e2);
+ Assertions.assertNotNull(read);
+ MatcherAssert.assertThat("", read, Matchers.instanceOf(IndexedRecord.class));
+ IndexedRecord result = (IndexedRecord) read;
+ Assertions.assertEquals("e3", result.get(0).toString());
+ }
+
+ @Test
+ void promoteIsValid() {
+ Assertions.assertThrows(IllegalArgumentException.class,
+ () -> Resolver.Promote.isValid(Schema.create(Schema.Type.INT), Schema.create(Schema.Type.INT)));
+
+ Assertions.assertTrue(Resolver.Promote.isValid(Schema.create(Schema.Type.INT), Schema.create(Schema.Type.LONG)));
+ Assertions.assertFalse(Resolver.Promote.isValid(Schema.create(Schema.Type.LONG), Schema.create(Schema.Type.INT)));
+
+ Assertions.assertTrue(Resolver.Promote.isValid(Schema.create(Schema.Type.INT), Schema.create(Schema.Type.FLOAT)));
+ Assertions.assertFalse(Resolver.Promote.isValid(Schema.create(Schema.Type.FLOAT), Schema.create(Schema.Type.INT)));
+
+ Assertions
+ .assertTrue(Resolver.Promote.isValid(Schema.create(Schema.Type.FLOAT), Schema.create(Schema.Type.DOUBLE)));
+ Assertions
+ .assertFalse(Resolver.Promote.isValid(Schema.create(Schema.Type.DOUBLE), Schema.create(Schema.Type.FLOAT)));
+ }
+}