public class StringToStringsMapImpl extends MinimalEObjectImpl.Container implements BasicEMap.Entry<String,EList<String>> {
// ...
@Override
public EList<String> setValue(EList<String> value) {
EList<String> oldValue = getValue();
getTypedValue().clear();
getTypedValue().addAll(value);
return oldValue;
}
I have a valid json that I created with this library. I then try to deserialize it back into this EMap.
Expected: The values in the map entries would be EList instances.
Actual: ClassCast exceptions.
The org.emfjson.jackson.databind.deser.EMapDeserializer sees a token that is not START_OBJECT (but rather START_ARRAY) and performs a readValue with Object.class. Jackson does its lookups and concludes a com.fasterxml.jackson.databind.deser.std.UntypedObjectDeserializer should be used, and this creates an ArrayList at line 840.
The org.eclipse.emf.ecore.util.EcoreEMap runs a setValue on line 270 with the ArrayList value, and this triggers a ClassCastException because this list should have been an EList.
Stacktrace:
Exception in thread "main" java.lang.ClassCastException: class java.util.ArrayList cannot be cast to class org.eclipse.emf.common.util.EList (java.util.ArrayList is in module java.base of loader 'bootstrap'; org.eclipse.emf.common.util.EList is in unnamed module of loader 'app')
at no.ntnu.stud.treedocumentmodel.impl.NodeTypeToNodeTypesMapImpl.setValue(NodeTypeToNodeTypesMapImpl.java:1)
at org.eclipse.emf.ecore.util.EcoreEMap.newEntry(EcoreEMap.java:270)
at org.eclipse.emf.common.util.BasicEMap.put(BasicEMap.java:584)
at org.emfjson.jackson.databind.deser.EMapDeserializer.deserialize(EMapDeserializer.java:66)
at org.emfjson.jackson.databind.deser.EMapDeserializer.deserialize(EMapDeserializer.java:30)
at org.emfjson.jackson.databind.property.EObjectFeatureProperty.deserializeAndSet(EObjectFeatureProperty.java:64)
at org.emfjson.jackson.databind.deser.EObjectDeserializer.deserialize(EObjectDeserializer.java:78)
at org.emfjson.jackson.databind.deser.EObjectDeserializer.deserialize(EObjectDeserializer.java:38)
at com.fasterxml.jackson.databind.ObjectReader._bindAndClose(ObjectReader.java:1608)
at com.fasterxml.jackson.databind.ObjectReader.readValue(ObjectReader.java:1292)
Assumed fixes:
Perhaps do a check for START_ARRAY in EMapDeserializer#57 and treat this differently?
Register EList as a deserialization class for json array
Check in EMapDeserializer if the value is ArrayList and convert it to EList. I think this is a bad solution; more of a band-aid fix for this particular case
Description: I am trying to deserialize an
EMap
withBasicEMap.Entry<String,EList<String>>
as its contents. Example of this structure:It uses this construct from Ecore:
I have a valid json that I created with this library. I then try to deserialize it back into this
EMap
.Expected: The values in the map entries would be
EList
instances.Actual: ClassCast exceptions. The
org.emfjson.jackson.databind.deser.EMapDeserializer
sees a token that is notSTART_OBJECT
(but ratherSTART_ARRAY
) and performs areadValue
withObject.class
. Jackson does its lookups and concludes acom.fasterxml.jackson.databind.deser.std.UntypedObjectDeserializer
should be used, and this creates anArrayList
at line840
. Theorg.eclipse.emf.ecore.util.EcoreEMap
runs asetValue
on line 270 with theArrayList
value, and this triggers aClassCastException
because this list should have been anEList
.Stacktrace:
Assumed fixes:
START_ARRAY
inEMapDeserializer#57
and treat this differently?EList
as a deserialization class for json arrayEMapDeserializer
if the value isArrayList
and convert it toEList
. I think this is a bad solution; more of a band-aid fix for this particular caseThanks!