owlike/genson

Unable to deserialize string or literal into Object type field.

Closed this issue · 7 comments

Consider the following:

public static class BaseSimple<T> {
    public T value;

    public BaseSimple() {
    }

    public BaseSimple(final T value) {
      this.value = value;
    }

    @Override
    public boolean equals(final Object o) {
      if (this == o) return true;
      if (o == null || getClass() != o.getClass()) return false;
      final BaseSimple<?> that = (BaseSimple<?>) o;
      return Objects.equals(value, that.value);
    }

    @Override
    public int hashCode() {
      return Objects.hash(value);
    }
  }

  public static class Simple<T> extends BaseSimple<T> {
    @SuppressWarnings("unused")
    public Simple() {}
    public Simple(final T value) {
      super(value);
    }
  }

Along with the following test:

@Test
  public void testDeserializeStringIntoObjectField() {
     BaseSimple result = genson.deserialize("{\"value\":\"test\"}", BaseSimple.class);
     assertEquals(new BaseSimple("test"), result);
  }

@Test
  public void testDeserializeStringIntoObjectFieldHierachy() {
      Simple result = genson.deserialize("{\"value\":\"test\"}", Simple.class);
      assertEquals(new Simple("test"), result);
  }

The first test case, testDeserializeStringIntoObjectField works fine. The second test, testDeserializeStringIntoObjectFieldHierachy, fails with:

Caused by: com.owlike.genson.stream.JsonStreamException: Illegal character at row 0 and column 15 expected { but read '}' !
at com.owlike.genson.stream.JsonReader.newWrongTokenException(JsonReader.java:948)
at com.owlike.genson.stream.JsonReader.begin(JsonReader.java:420)
at com.owlike.genson.stream.JsonReader.beginObject(JsonReader.java:158)
at com.owlike.genson.reflect.BeanDescriptor.deserialize(BeanDescriptor.java:117)
at com.owlike.genson.reflect.BeanDescriptor.deserialize(BeanDescriptor.java:103)
at com.owlike.genson.convert.RuntimeTypeConverter.deserialize(RuntimeTypeConverter.java:53)
at com.owlike.genson.convert.NullConverterFactory$NullConverterWrapper.deserialize(NullConverterFactory.java:77)
at com.owlike.genson.reflect.PropertyMutator.deserialize(PropertyMutator.java:31)

If I wrap the type in the deserialization call in the failing test with GenericType then the test will pass. Seems in the case where the target field is Object, we shouldn't need the extra info provided by GenericType, the value should just be set of it's a JSON string/number/bool.

Sorry, transcription error on my part. I've fixed example in the issue report.

One of those days. It's correct now.

Ok, I see the problem, thanks for reporting it. I'll make a fix for it.

Basically TypeUtil.match is not handling properly the case when the type is an unbound generic (which means its Object).

Yep, I was just about to share that from my debugging. Thank you!

Fixed in here #136. Thank you!

PS: if you want to review the code you are welcome :)