From 934bab363ca2e05e0b5416823153f175644e6dd8 Mon Sep 17 00:00:00 2001 From: pkupczyk <pkupczyk> Date: Sun, 10 Jun 2012 17:04:08 +0000 Subject: [PATCH] SP-116 / BIS-14 Query Plugins in JSON-RPC - fix for nested arrays SVN: 25622 --- .../JsonContainerDeserializer.java | 372 ------------------ .../deserializer/JsonDeserializerFactory.java | 200 ++++++++++ .../JsonDeserializerProvider.java | 36 +- .../JsonTypeAndClassDeserializer.java | 17 +- .../IJsonTypeValueToClassObjectMapping.java | 27 -- ...nReflectionsBaseTypeToSubTypesMapping.java | 26 +- ...lectionsTypeValueToClassObjectMapping.java | 82 ---- .../serializer/JsonSerializerFactory.java | 142 +++++++ .../server/json/JsonDeserializationTest.java | 57 ++- .../api/server/json/JsonTestObjectMapper.java | 10 +- .../json/object/ObjectWithContainerTypes.java | 24 +- .../shared/api/json/GenericObjectMapper.java | 10 +- .../api/json/ScreeningObjectMapper.java | 10 +- 13 files changed, 458 insertions(+), 555 deletions(-) delete mode 100644 openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonContainerDeserializer.java create mode 100644 openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonDeserializerFactory.java delete mode 100644 openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/IJsonTypeValueToClassObjectMapping.java delete mode 100644 openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/JsonReflectionsTypeValueToClassObjectMapping.java create mode 100644 openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/serializer/JsonSerializerFactory.java diff --git a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonContainerDeserializer.java b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonContainerDeserializer.java deleted file mode 100644 index 4f524d118e0..00000000000 --- a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonContainerDeserializer.java +++ /dev/null @@ -1,372 +0,0 @@ -/* - * Copyright 2012 ETH Zuerich, CISD - * - * Licensed 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 - * - * http://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 ch.systemsx.cisd.common.api.server.json.deserializer; - -import java.io.IOException; -import java.lang.reflect.Constructor; -import java.lang.reflect.InvocationTargetException; -import java.util.ArrayList; -import java.util.Collection; -import java.util.EnumMap; -import java.util.EnumSet; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Iterator; -import java.util.List; -import java.util.ListIterator; -import java.util.Map; -import java.util.Set; - -import org.codehaus.jackson.JsonParser; -import org.codehaus.jackson.map.DeserializationContext; -import org.codehaus.jackson.map.JsonDeserializer; -import org.codehaus.jackson.map.JsonMappingException; -import org.codehaus.jackson.map.ObjectMapper; -import org.codehaus.jackson.map.deser.BeanDeserializer; -import org.codehaus.jackson.map.deser.BeanDeserializerFactory; -import org.codehaus.jackson.map.deser.SettableBeanProperty; -import org.codehaus.jackson.map.introspect.BasicBeanDescription; -import org.codehaus.jackson.map.util.ClassUtil; -import org.codehaus.jackson.type.JavaType; - -import ch.systemsx.cisd.common.api.server.json.common.JsonConstants; -import ch.systemsx.cisd.common.api.server.json.mapping.IJsonClassValueToClassObjectsMapping; -import ch.systemsx.cisd.common.api.server.json.mapping.IJsonTypeValueToClassObjectMapping; - -/** - * @author pkupczyk - */ - -@SuppressWarnings( - { "rawtypes", "unchecked" }) -public class JsonContainerDeserializer extends JsonDeserializer<Object> -{ - - private JsonDeserializer<Object> originalDeserializer; - - private IJsonTypeValueToClassObjectMapping typeValueToClassObjectMapping; - - private IJsonClassValueToClassObjectsMapping classValueToClassObjectsMapping; - - public JsonContainerDeserializer(JsonDeserializer<Object> originalDeserializer, - IJsonTypeValueToClassObjectMapping typeValueToClassObjectMapping, - IJsonClassValueToClassObjectsMapping classValueToClassObjectsMapping) - { - this.originalDeserializer = originalDeserializer; - this.typeValueToClassObjectMapping = typeValueToClassObjectMapping; - this.classValueToClassObjectsMapping = classValueToClassObjectsMapping; - } - - public static boolean canDeserialize(JavaType type) - { - Class<?> clazz = type.getRawClass(); - return Map.class.isAssignableFrom(clazz) || Collection.class.isAssignableFrom(clazz); - } - - @Override - public Object deserialize(JsonParser jp, DeserializationContext ctxt) throws IOException - { - Object object = getOriginalDeserializer().deserialize(jp, ctxt); - return tryConvertNestedMaps(object, ctxt); - } - - private Object tryConvertNestedMaps(Object object, DeserializationContext ctxt) - { - if (object instanceof EnumMap || object instanceof EnumSet) - { - return object; - } - if (object instanceof Map) - { - return tryConvertNestedMapsInMap((Map) object, ctxt); - } else if (object instanceof List) - { - return tryConvertNestedMapsInList((List) object, ctxt); - } else if (object instanceof Set) - { - return tryConvertNestedMapsInCollection((Set) object, new HashSet(), ctxt); - } else if (object instanceof Collection) - { - return tryConvertNestedMapsInCollection((Collection) object, new ArrayList(), ctxt); - } else - { - return object; - } - } - - private Object tryConvertNestedMapsInMap(Map map, DeserializationContext ctxt) - { - if (map == null || map.isEmpty()) - { - return map; - } - - Iterator<Map.Entry> iterator = map.entrySet().iterator(); - - String typeValue = null; - String classValue = null; - Map changedValues = null; - - while (iterator.hasNext()) - { - Map.Entry entry = iterator.next(); - Object key = entry.getKey(); - Object value = entry.getValue(); - - if (value instanceof String) - { - if (JsonConstants.getTypeField().equals(key)) - { - typeValue = (String) entry.getValue(); - } else if (JsonConstants.getLegacyClassField().equals(key)) - { - classValue = (String) entry.getValue(); - } - } else - { - Object newValue = tryConvertNestedMaps(value, ctxt); - - if (newValue != value) - { - if (changedValues == null) - { - changedValues = new HashMap(); - } - changedValues.put(key, newValue); - } - } - } - - if (changedValues != null) - { - map.putAll(changedValues); - } - - if (typeValue == null && classValue == null) - { - return map; - } else - { - return tryConvertMap(map, typeValue, classValue, ctxt); - } - } - - private Object tryConvertNestedMapsInList(List list, DeserializationContext ctxt) - { - if (list == null || list.isEmpty()) - { - return list; - } - - ListIterator iterator = list.listIterator(); - - while (iterator.hasNext()) - { - Object item = iterator.next(); - Object newItem = tryConvertNestedMaps(item, ctxt); - - if (newItem != item) - { - iterator.set(newItem); - } - } - return list; - } - - private Object tryConvertNestedMapsInCollection(Collection collection, - Collection newCollection, DeserializationContext ctxt) - { - if (collection == null || collection.isEmpty()) - { - return collection; - } - - Iterator iterator = collection.iterator(); - boolean changed = false; - - while (iterator.hasNext()) - { - Object item = iterator.next(); - Object newItem = tryConvertNestedMaps(item, ctxt); - - if (newItem != item) - { - changed = true; - } - newCollection.add(newItem); - } - - if (changed) - { - return newCollection; - } else - { - return collection; - } - } - - private Object tryConvertMap(Map map, String typeValue, String classValue, - DeserializationContext ctxt) - { - Class<?> clazz = tryGetClass(typeValue, classValue); - - if (clazz != null) - { - boolean hadTypeValue = map.containsKey(JsonConstants.getTypeField()); - boolean hadClassValue = map.containsKey(JsonConstants.getLegacyClassField()); - - map.remove(JsonConstants.getTypeField()); - map.remove(JsonConstants.getLegacyClassField()); - - try - { - Object instance = tryCreateInstance(clazz, ctxt); - - Iterator<SettableBeanProperty> properties = tryGetProperties(clazz, ctxt); - if (properties != null) - { - trySetProperties(instance, properties, map, ctxt); - } - - return instance; - - } catch (IOException e) - { - if (hadTypeValue) - { - map.put(JsonConstants.getTypeField(), typeValue); - } - if (hadClassValue) - { - map.put(JsonConstants.getLegacyClassField(), classValue); - } - return map; - } - } else - { - return map; - } - } - - private Class tryGetClass(String typeValue, String classValue) - { - Class<?> clazz = null; - - if (typeValue != null) - { - clazz = getTypeValueToClassObjectMapping().getClass(typeValue); - } else if (classValue != null) - { - List<Class<?>> clazzList = getClassValueToClassObjectsMapping().getClasses(classValue); - if (clazzList != null && clazzList.size() == 1) - { - clazz = clazzList.get(0); - } - } - - return clazz; - } - - private Object tryCreateInstance(Class<?> clazz, DeserializationContext ctxt) - throws IOException - { - try - { - JavaType type = ctxt.getConfig().getTypeFactory().constructType(clazz); - BasicBeanDescription beanDesc = ctxt.getConfig().introspect(type); - Constructor<?> defaultConstructor = beanDesc.findDefaultConstructor(); - ClassUtil.checkAndFixAccess(defaultConstructor); - return defaultConstructor.newInstance(); - - } catch (InstantiationException e) - { - throw new JsonMappingException("Couldn't create an instance of class: " + clazz, e); - } catch (IllegalAccessException e) - { - throw new JsonMappingException("Couldn't create an instance of class: " + clazz, e); - } catch (IllegalArgumentException e) - { - throw new JsonMappingException("Couldn't create an instance of class: " + clazz, e); - } catch (InvocationTargetException e) - { - throw new JsonMappingException("Couldn't create an instance of class: " + clazz, e); - } - } - - private Iterator<SettableBeanProperty> tryGetProperties(Class<?> clazz, - DeserializationContext ctxt) throws IOException - { - JavaType type = ctxt.getConfig().getTypeFactory().constructType(clazz); - JsonDeserializer deserializer = - getBeanDeserializerFactory().createBeanDeserializer(ctxt.getConfig(), - ctxt.getDeserializerProvider(), type, null); - - if (deserializer instanceof BeanDeserializer) - { - return ((BeanDeserializer) deserializer).properties(); - } else - { - return null; - } - } - - private void trySetProperties(Object instance, Iterator<SettableBeanProperty> properties, - Map values, DeserializationContext ctxt) throws IOException - { - while (properties.hasNext()) - { - SettableBeanProperty property = properties.next(); - Object value = values.get(property.getName()); - - if (value != null) - { - if (property.getType().getRawClass().isAssignableFrom(value.getClass())) - { - property.set(instance, value); - } else - { - ObjectMapper mapper = new ObjectMapper(); - String json = mapper.writeValueAsString(value); - Object newValue = mapper.readValue(json, property.getType()); - property.set(instance, newValue); - } - } - - } - } - - private BeanDeserializerFactory getBeanDeserializerFactory() - { - return BeanDeserializerFactory.instance; - } - - private JsonDeserializer<Object> getOriginalDeserializer() - { - return originalDeserializer; - } - - private IJsonTypeValueToClassObjectMapping getTypeValueToClassObjectMapping() - { - return typeValueToClassObjectMapping; - } - - private IJsonClassValueToClassObjectsMapping getClassValueToClassObjectsMapping() - { - return classValueToClassObjectsMapping; - } - -} diff --git a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonDeserializerFactory.java b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonDeserializerFactory.java new file mode 100644 index 00000000000..683565ab836 --- /dev/null +++ b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonDeserializerFactory.java @@ -0,0 +1,200 @@ +/* + * Copyright 2012 ETH Zuerich, CISD + * + * Licensed 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 + * + * http://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 ch.systemsx.cisd.common.api.server.json.deserializer; + +import java.io.IOException; +import java.io.StringWriter; +import java.util.Collection; + +import org.codehaus.jackson.JsonFactory; +import org.codehaus.jackson.JsonGenerator; +import org.codehaus.jackson.JsonNode; +import org.codehaus.jackson.JsonParser; +import org.codehaus.jackson.map.AnnotationIntrospector; +import org.codehaus.jackson.map.BeanProperty; +import org.codehaus.jackson.map.DeserializationConfig; +import org.codehaus.jackson.map.DeserializationContext; +import org.codehaus.jackson.map.DeserializerProvider; +import org.codehaus.jackson.map.JsonDeserializer; +import org.codehaus.jackson.map.JsonMappingException; +import org.codehaus.jackson.map.TypeDeserializer; +import org.codehaus.jackson.map.deser.BeanDeserializerFactory; +import org.codehaus.jackson.map.introspect.AnnotatedClass; +import org.codehaus.jackson.map.introspect.BasicBeanDescription; +import org.codehaus.jackson.map.jsontype.NamedType; +import org.codehaus.jackson.map.jsontype.TypeIdResolver; +import org.codehaus.jackson.map.jsontype.impl.TypeNameIdResolver; +import org.codehaus.jackson.map.type.ArrayType; +import org.codehaus.jackson.map.type.CollectionLikeType; +import org.codehaus.jackson.map.type.CollectionType; +import org.codehaus.jackson.map.type.MapLikeType; +import org.codehaus.jackson.map.type.MapType; +import org.codehaus.jackson.type.JavaType; + +import ch.systemsx.cisd.base.annotation.JsonObject; +import ch.systemsx.cisd.common.api.server.json.common.JsonConstants; +import ch.systemsx.cisd.common.api.server.json.mapping.IJsonClassValueToClassObjectsMapping; +import ch.systemsx.cisd.common.api.server.json.mapping.JsonStaticClassValueToClassObjectsMapping; + +/** + * @author pkupczyk + */ +public class JsonDeserializerFactory extends BeanDeserializerFactory +{ + + private IJsonClassValueToClassObjectsMapping classValueToClassObjectsMapping = + new JsonStaticClassValueToClassObjectsMapping(); + + public JsonDeserializerFactory( + IJsonClassValueToClassObjectsMapping classValueToClassObjectsMapping) + { + super(null); + this.classValueToClassObjectsMapping = classValueToClassObjectsMapping; + } + + @Override + public JsonDeserializer<?> createArrayDeserializer(DeserializationConfig config, + DeserializerProvider p, ArrayType type, BeanProperty property) + throws JsonMappingException + { + ArrayType newType = + type.withContentTypeHandler(createContentTypeDeserializer(config, type, property)); + return super.createArrayDeserializer(config, p, newType, property); + } + + @Override + public JsonDeserializer<?> createCollectionDeserializer(DeserializationConfig config, + DeserializerProvider p, CollectionType type, BeanProperty property) + throws JsonMappingException + { + CollectionType newType = + type.withContentTypeHandler(createContentTypeDeserializer(config, type, property)); + return super.createCollectionDeserializer(config, p, newType, property); + } + + @Override + public JsonDeserializer<?> createCollectionLikeDeserializer(DeserializationConfig config, + DeserializerProvider p, CollectionLikeType type, BeanProperty property) + throws JsonMappingException + { + CollectionLikeType newType = + type.withContentTypeHandler(createContentTypeDeserializer(config, type, property)); + return super.createCollectionLikeDeserializer(config, p, newType, property); + } + + @Override + public JsonDeserializer<?> createMapDeserializer(DeserializationConfig config, + DeserializerProvider p, MapType type, BeanProperty property) + throws JsonMappingException + { + MapType newType = + type.withContentTypeHandler(createContentTypeDeserializer(config, type, property)); + return super.createMapDeserializer(config, p, newType, property); + } + + @Override + public JsonDeserializer<?> createMapLikeDeserializer(DeserializationConfig config, + DeserializerProvider p, MapLikeType type, BeanProperty property) + throws JsonMappingException + { + MapLikeType newType = + type.withContentTypeHandler(createContentTypeDeserializer(config, type, property)); + return super.createMapLikeDeserializer(config, p, newType, property); + } + + private TypeDeserializer createContentTypeDeserializer(DeserializationConfig config, + JavaType containerType, BeanProperty property) + { + JavaType contentType = containerType.getContentType(); + + if (contentType == null || contentType.getRawClass() == null) + { + return null; + } + + Class<?> contentClass = contentType.getRawClass(); + + if (contentClass.equals(Object.class) || contentClass.isAnnotationPresent(JsonObject.class)) + { + BasicBeanDescription bean = + config.introspectClassAnnotations(contentType.getRawClass()); + AnnotatedClass ac = bean.getClassInfo(); + AnnotationIntrospector ai = config.getAnnotationIntrospector(); + Collection<NamedType> subtypes = + config.getSubtypeResolver().collectAndResolveSubtypes(ac, config, ai); + TypeIdResolver resolver = + TypeNameIdResolver.construct(config, contentType, subtypes, false, true); + JsonTypeAndClassWithFallbackDeserializer deserializer = + new JsonTypeAndClassWithFallbackDeserializer(contentType, subtypes, resolver, + property, JsonConstants.getTypeField()); + deserializer.setClassValueToClassObjectsMapping(this.classValueToClassObjectsMapping); + return deserializer; + } else + { + return null; + } + } + + private class JsonTypeAndClassWithFallbackDeserializer extends JsonTypeAndClassDeserializer + { + + public JsonTypeAndClassWithFallbackDeserializer(JavaType type, + Collection<NamedType> subtypes, TypeIdResolver idRes, BeanProperty property, + String typePropName) + { + super(type, subtypes, idRes, property, typePropName); + } + + @Override + public Object deserializeTypedFromObject(JsonParser parser, DeserializationContext ctxt) + throws IOException + { + String json = parserToString(parser); + JsonFactory factory = new JsonFactory(parser.getCodec()); + + try + { + JsonParser jp1 = factory.createJsonParser(json); + jp1.nextToken(); + return super.deserializeTypedFromObject(jp1, ctxt); + } catch (IOException e) + { + JsonParser jp2 = factory.createJsonParser(json); + jp2.nextToken(); + return super.deserializeWithoutType(jp2, ctxt, null); + } + } + + private String parserToString(JsonParser parser) + { + try + { + JsonFactory factory = new JsonFactory(parser.getCodec()); + StringWriter writer = new StringWriter(); + JsonGenerator generator = factory.createJsonGenerator(writer); + generator.setCodec(parser.getCodec()); + JsonNode node = parser.readValueAs(JsonNode.class); + generator.writeTree(node); + return writer.toString(); + } catch (IOException e) + { + throw new IllegalArgumentException(e); + } + } + } + +} diff --git a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonDeserializerProvider.java b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonDeserializerProvider.java index a8f00125e29..a649d11e4d1 100644 --- a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonDeserializerProvider.java +++ b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonDeserializerProvider.java @@ -16,15 +16,8 @@ package ch.systemsx.cisd.common.api.server.json.deserializer; -import org.codehaus.jackson.map.BeanProperty; -import org.codehaus.jackson.map.DeserializationConfig; -import org.codehaus.jackson.map.JsonDeserializer; -import org.codehaus.jackson.map.JsonMappingException; +import org.codehaus.jackson.map.DeserializerFactory; import org.codehaus.jackson.map.deser.StdDeserializerProvider; -import org.codehaus.jackson.type.JavaType; - -import ch.systemsx.cisd.common.api.server.json.mapping.IJsonClassValueToClassObjectsMapping; -import ch.systemsx.cisd.common.api.server.json.mapping.IJsonTypeValueToClassObjectMapping; /** * @author pkupczyk @@ -32,32 +25,9 @@ import ch.systemsx.cisd.common.api.server.json.mapping.IJsonTypeValueToClassObje public class JsonDeserializerProvider extends StdDeserializerProvider { - private IJsonTypeValueToClassObjectMapping typeValueToClassObjectMapping; - - private IJsonClassValueToClassObjectsMapping classValueToClassObjectsMapping; - - public JsonDeserializerProvider( - IJsonTypeValueToClassObjectMapping typeValueToClassObjectMapping, - IJsonClassValueToClassObjectsMapping classValueToClassObjectsMapping) + public JsonDeserializerProvider(DeserializerFactory f) { - this.typeValueToClassObjectMapping = typeValueToClassObjectMapping; - this.classValueToClassObjectsMapping = classValueToClassObjectsMapping; - } - - @Override - protected JsonDeserializer<Object> _createDeserializer(DeserializationConfig config, - JavaType type, BeanProperty property) throws JsonMappingException - { - JsonDeserializer<Object> deserializer = super._createDeserializer(config, type, property); - - if (JsonContainerDeserializer.canDeserialize(type)) - { - return new JsonContainerDeserializer(deserializer, typeValueToClassObjectMapping, - classValueToClassObjectsMapping); - } else - { - return deserializer; - } + super(f); } } diff --git a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonTypeAndClassDeserializer.java b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonTypeAndClassDeserializer.java index de2c0841a8e..4f704616c03 100644 --- a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonTypeAndClassDeserializer.java +++ b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/deserializer/JsonTypeAndClassDeserializer.java @@ -108,7 +108,14 @@ public class JsonTypeAndClassDeserializer extends AsPropertyTypeDeserializer tb.copyCurrentStructure(jp); } - return deserializeWithoutType(jp, ctxt, tb); + if (hasSubtypes) + { + throw new JsonMappingException( + "Cannot deserialize a polymorphic type without type information"); + } else + { + return deserializeWithoutType(jp, ctxt, tb); + } } private Object deserializeWithType(JsonParser jp, DeserializationContext ctxt, TokenBuffer tb, @@ -177,15 +184,9 @@ public class JsonTypeAndClassDeserializer extends AsPropertyTypeDeserializer throw new NoMatchingLegacyClassesException(classValue); } - private Object deserializeWithoutType(JsonParser jp, DeserializationContext ctxt, TokenBuffer tb) + public Object deserializeWithoutType(JsonParser jp, DeserializationContext ctxt, TokenBuffer tb) throws IOException, JsonProcessingException { - if (hasSubtypes) - { - throw new JsonMappingException( - "Cannot deserialize a polymorphic type without type information"); - } - final JsonParser actualJp; final JsonDeserializer<Object> deserializer = ctxt.getDeserializerProvider().findValueDeserializer(ctxt.getConfig(), _baseType, diff --git a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/IJsonTypeValueToClassObjectMapping.java b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/IJsonTypeValueToClassObjectMapping.java deleted file mode 100644 index c763377cd51..00000000000 --- a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/IJsonTypeValueToClassObjectMapping.java +++ /dev/null @@ -1,27 +0,0 @@ -/* - * Copyright 2012 ETH Zuerich, CISD - * - * Licensed 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 - * - * http://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 ch.systemsx.cisd.common.api.server.json.mapping; - -/** - * @author pkupczyk - */ -public interface IJsonTypeValueToClassObjectMapping -{ - - public Class<?> getClass(String typeValue); - -} diff --git a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/JsonReflectionsBaseTypeToSubTypesMapping.java b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/JsonReflectionsBaseTypeToSubTypesMapping.java index 6eb2a4c0f90..f31feba089c 100644 --- a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/JsonReflectionsBaseTypeToSubTypesMapping.java +++ b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/JsonReflectionsBaseTypeToSubTypesMapping.java @@ -37,15 +37,24 @@ public class JsonReflectionsBaseTypeToSubTypesMapping implements IJsonBaseTypeTo private Map<Class<?>, Set<NamedType>> baseTypeToSubTypesMap; + private Set<NamedType> allSubTypesSet; + public JsonReflectionsBaseTypeToSubTypesMapping(String prefix) { baseTypeToSubTypesMap = createBaseTypeToSubTypesMap(prefix); + allSubTypesSet = createAllSubTypesSet(baseTypeToSubTypesMap); } @Override public Set<NamedType> getSubTypes(Class<?> baseType) { - return baseTypeToSubTypesMap.get(baseType); + if (Object.class.equals(baseType)) + { + return allSubTypesSet; + } else + { + return baseTypeToSubTypesMap.get(baseType); + } } private static Map<Class<?>, Set<NamedType>> createBaseTypeToSubTypesMap(String prefix) @@ -80,13 +89,26 @@ public class JsonReflectionsBaseTypeToSubTypesMapping implements IJsonBaseTypeTo return subTypesMap; } + private static Set<NamedType> createAllSubTypesSet( + Map<Class<?>, Set<NamedType>> baseTypeToSubTypesMap) + { + Set<NamedType> allSubTypes = new HashSet<NamedType>(); + for (Set<NamedType> subTypes : baseTypeToSubTypesMap.values()) + { + allSubTypes.addAll(subTypes); + } + return allSubTypes; + } + public static final JsonReflectionsBaseTypeToSubTypesMapping getInstance() { synchronized (JsonReflectionsBaseTypeToSubTypesMapping.class) { if (instance == null) { - instance = new JsonReflectionsBaseTypeToSubTypesMapping(JsonConstants.getClassesPrefix()); + instance = + new JsonReflectionsBaseTypeToSubTypesMapping( + JsonConstants.getClassesPrefix()); } return instance; } diff --git a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/JsonReflectionsTypeValueToClassObjectMapping.java b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/JsonReflectionsTypeValueToClassObjectMapping.java deleted file mode 100644 index 67a1b3d601f..00000000000 --- a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/mapping/JsonReflectionsTypeValueToClassObjectMapping.java +++ /dev/null @@ -1,82 +0,0 @@ -/* - * Copyright 2012 ETH Zuerich, CISD - * - * Licensed 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 - * - * http://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 ch.systemsx.cisd.common.api.server.json.mapping; - -import java.util.HashMap; -import java.util.Map; -import java.util.Set; - -import org.reflections.Reflections; - -import ch.systemsx.cisd.base.annotation.JsonObject; -import ch.systemsx.cisd.common.api.server.json.common.JsonConstants; - -/** - * @author pkupczyk - */ -public class JsonReflectionsTypeValueToClassObjectMapping implements - IJsonTypeValueToClassObjectMapping -{ - - private static JsonReflectionsTypeValueToClassObjectMapping instance; - - private Map<String, Class<?>> typeToClassMap; - - public JsonReflectionsTypeValueToClassObjectMapping(String prefix) - { - typeToClassMap = createTypeToClassMap(prefix); - } - - @Override - public Class<?> getClass(String type) - { - return typeToClassMap.get(type); - } - - private static Map<String, Class<?>> createTypeToClassMap(String prefix) - { - Reflections reflections = new Reflections(prefix); - - Set<Class<?>> types = reflections.getTypesAnnotatedWith(JsonObject.class); - Map<String, Class<?>> typesMap = new HashMap<String, Class<?>>(); - - if (types != null) - { - for (Class<?> type : types) - { - JsonObject typeAnnotation = type.getAnnotation(JsonObject.class); - typesMap.put(typeAnnotation.value(), type); - } - } - - return typesMap; - } - - public static final JsonReflectionsTypeValueToClassObjectMapping getInstance() - { - synchronized (JsonReflectionsTypeValueToClassObjectMapping.class) - { - if (instance == null) - { - instance = - new JsonReflectionsTypeValueToClassObjectMapping( - JsonConstants.getClassesPrefix()); - } - return instance; - } - } -} diff --git a/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/serializer/JsonSerializerFactory.java b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/serializer/JsonSerializerFactory.java new file mode 100644 index 00000000000..667ee4e99c6 --- /dev/null +++ b/openbis-common/source/java/ch/systemsx/cisd/common/api/server/json/serializer/JsonSerializerFactory.java @@ -0,0 +1,142 @@ +/* + * Copyright 2012 ETH Zuerich, CISD + * + * Licensed 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 + * + * http://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 ch.systemsx.cisd.common.api.server.json.serializer; + +import java.util.Collection; + +import org.codehaus.jackson.map.AnnotationIntrospector; +import org.codehaus.jackson.map.BeanProperty; +import org.codehaus.jackson.map.JsonSerializer; +import org.codehaus.jackson.map.SerializationConfig; +import org.codehaus.jackson.map.TypeSerializer; +import org.codehaus.jackson.map.introspect.AnnotatedClass; +import org.codehaus.jackson.map.introspect.BasicBeanDescription; +import org.codehaus.jackson.map.jsontype.NamedType; +import org.codehaus.jackson.map.jsontype.TypeIdResolver; +import org.codehaus.jackson.map.jsontype.impl.AsPropertyTypeSerializer; +import org.codehaus.jackson.map.jsontype.impl.TypeNameIdResolver; +import org.codehaus.jackson.map.ser.BeanSerializerFactory; +import org.codehaus.jackson.map.type.ArrayType; +import org.codehaus.jackson.map.type.CollectionLikeType; +import org.codehaus.jackson.map.type.CollectionType; +import org.codehaus.jackson.map.type.MapLikeType; +import org.codehaus.jackson.map.type.MapType; +import org.codehaus.jackson.type.JavaType; + +import ch.systemsx.cisd.base.annotation.JsonObject; +import ch.systemsx.cisd.common.api.server.json.common.JsonConstants; + +/** + * @author pkupczyk + */ +public class JsonSerializerFactory extends BeanSerializerFactory +{ + + public JsonSerializerFactory() + { + super(null); + } + + @Override + protected JsonSerializer<?> buildArraySerializer(SerializationConfig config, ArrayType type, + BasicBeanDescription beanDesc, BeanProperty property, boolean staticTyping, + TypeSerializer elementTypeSerializer, JsonSerializer<Object> elementValueSerializer) + { + ArrayType newType = + type.withContentTypeHandler(createContentTypeSerializer(config, type, property)); + return super.buildArraySerializer(config, newType, beanDesc, property, staticTyping, + elementTypeSerializer, elementValueSerializer); + } + + @Override + protected JsonSerializer<?> buildCollectionSerializer(SerializationConfig config, + CollectionType type, BasicBeanDescription beanDesc, BeanProperty property, + boolean staticTyping, TypeSerializer elementTypeSerializer, + JsonSerializer<Object> elementValueSerializer) + { + CollectionType newType = + type.withContentTypeHandler(createContentTypeSerializer(config, type, property)); + return super.buildCollectionSerializer(config, newType, beanDesc, property, staticTyping, + elementTypeSerializer, elementValueSerializer); + } + + @Override + protected JsonSerializer<?> buildCollectionLikeSerializer(SerializationConfig config, + CollectionLikeType type, BasicBeanDescription beanDesc, BeanProperty property, + boolean staticTyping, TypeSerializer elementTypeSerializer, + JsonSerializer<Object> elementValueSerializer) + { + CollectionLikeType newType = + type.withContentTypeHandler(createContentTypeSerializer(config, type, property)); + return super.buildCollectionLikeSerializer(config, newType, beanDesc, property, + staticTyping, elementTypeSerializer, elementValueSerializer); + } + + @Override + protected JsonSerializer<?> buildMapSerializer(SerializationConfig config, MapType type, + BasicBeanDescription beanDesc, BeanProperty property, boolean staticTyping, + JsonSerializer<Object> keySerializer, TypeSerializer elementTypeSerializer, + JsonSerializer<Object> elementValueSerializer) + { + MapType newType = + type.withContentTypeHandler(createContentTypeSerializer(config, type, property)); + return super.buildMapSerializer(config, newType, beanDesc, property, staticTyping, + keySerializer, elementTypeSerializer, elementValueSerializer); + } + + @Override + protected JsonSerializer<?> buildMapLikeSerializer(SerializationConfig config, + MapLikeType type, BasicBeanDescription beanDesc, BeanProperty property, + boolean staticTyping, JsonSerializer<Object> keySerializer, + TypeSerializer elementTypeSerializer, JsonSerializer<Object> elementValueSerializer) + { + MapLikeType newType = + type.withContentTypeHandler(createContentTypeSerializer(config, type, property)); + return super.buildMapLikeSerializer(config, newType, beanDesc, property, staticTyping, + keySerializer, elementTypeSerializer, elementValueSerializer); + } + + private TypeSerializer createContentTypeSerializer(SerializationConfig config, + JavaType containerType, BeanProperty property) + { + JavaType contentType = containerType.getContentType(); + + if (contentType == null || contentType.getRawClass() == null) + { + return null; + } + + Class<?> contentClass = contentType.getRawClass(); + + if (contentClass.equals(Object.class) || contentClass.isAnnotationPresent(JsonObject.class)) + { + BasicBeanDescription bean = + config.introspectClassAnnotations(contentType.getRawClass()); + AnnotatedClass ac = bean.getClassInfo(); + AnnotationIntrospector ai = config.getAnnotationIntrospector(); + Collection<NamedType> subtypes = + config.getSubtypeResolver().collectAndResolveSubtypes(ac, config, ai); + TypeIdResolver resolver = + TypeNameIdResolver.construct(config, contentType, subtypes, true, false); + return new AsPropertyTypeSerializer(resolver, property, JsonConstants.getTypeField()); + } else + { + return null; + } + } + +} diff --git a/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/JsonDeserializationTest.java b/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/JsonDeserializationTest.java index 134eec9c6b2..b9327ad5294 100644 --- a/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/JsonDeserializationTest.java +++ b/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/JsonDeserializationTest.java @@ -17,6 +17,7 @@ package ch.systemsx.cisd.common.api.server.json; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.EnumMap; @@ -1063,7 +1064,7 @@ public class JsonDeserializationTest Collection collection = new ArrayList(map.values()); List list = new ArrayList(map.values()); - // Object[] array = map.values().toArray(new Object[map.size()]); + Object[] array = map.values().toArray(new Object[map.size()]); Map specificMap = new LinkedHashMap(); specificMap.put("itemWithKnownType", createObjectWithKnownType()); @@ -1071,7 +1072,7 @@ public class JsonDeserializationTest Collection specificCollection = new ArrayList(specificMap.values()); List specificList = new ArrayList(specificMap.values()); - // Object[] specificArray = specificMap.values().toArray(new Object[specificMap.size()]); + Object[] specificArray = specificMap.values().toArray(new Object[specificMap.size()]); Map<String, Object> object = new HashMap<String, Object>(); @@ -1080,16 +1081,28 @@ public class JsonDeserializationTest object.put("collectionWithObjectType", collection); object.put("collectionWithSpecificType", specificCollection); + object.put("linkedHashSetWithoutType", collection); + object.put("linkedHashSetWithObjectType", collection); + object.put("linkedHashSetWithSpecificType", specificCollection); + object.put("mapWithoutType", map); object.put("mapWithObjectType", map); object.put("mapWithSpecificType", specificMap); + object.put("linkedHashMapWithoutType", map); + object.put("linkedHashMapWithObjectType", map); + object.put("linkedHashMapWithSpecificType", specificMap); + object.put("listWithoutType", list); object.put("listWithObjectType", list); object.put("listWithSpecificType", specificList); - // object.put("arrayWithObjectType", array); - // object.put("arrayWithSpecificType", specificArray); + object.put("linkedListWithoutType", list); + object.put("linkedListWithObjectType", list); + object.put("linkedListWithSpecificType", specificList); + + object.put("arrayWithObjectType", array); + object.put("arrayWithSpecificType", specificArray); return object; } @@ -1098,17 +1111,33 @@ public class JsonDeserializationTest { Assert.assertEquals(object.getClass(), ObjectWithContainerTypes.class); ObjectWithContainerTypes objectWithContainers = (ObjectWithContainerTypes) object; + assertObjectsCollection(objectWithContainers.collectionWithObjectType); assertObjectsCollection(objectWithContainers.collectionWithoutType); assertObjectsSpecificCollection(objectWithContainers.collectionWithSpecificType); + + assertObjectsCollection(objectWithContainers.linkedHashSetWithObjectType); + assertObjectsCollection(objectWithContainers.linkedHashSetWithoutType); + assertObjectsSpecificCollection(objectWithContainers.linkedHashSetWithSpecificType); + assertObjectsMap(objectWithContainers.mapWithObjectType); assertObjectsMap(objectWithContainers.mapWithoutType); assertObjectsSpecificMap(objectWithContainers.mapWithSpecificType); + + assertObjectsMap(objectWithContainers.linkedHashMapWithObjectType); + assertObjectsMap(objectWithContainers.linkedHashMapWithoutType); + assertObjectsSpecificMap(objectWithContainers.linkedHashMapWithSpecificType); + assertObjectsCollection(objectWithContainers.listWithObjectType); assertObjectsCollection(objectWithContainers.listWithoutType); assertObjectsSpecificCollection(objectWithContainers.listWithSpecificType); - // assertObjectsArray(objectWithContainers.arrayWithObjectType); - // assertObjectsSpecificArray(objectWithContainers.arrayWithSpecificType); + + assertObjectsCollection(objectWithContainers.linkedListWithObjectType); + assertObjectsCollection(objectWithContainers.linkedListWithoutType); + assertObjectsSpecificCollection(objectWithContainers.linkedListWithSpecificType); + + assertObjectsArray(objectWithContainers.arrayWithObjectType); + assertObjectsSpecificArray(objectWithContainers.arrayWithSpecificType); } @SuppressWarnings( @@ -1169,15 +1198,15 @@ public class JsonDeserializationTest assertObjectWithKnownUniqueClass(map.get("itemWithKnownUniqueClass")); } - // private void assertObjectsArray(Object[] array) - // { - // assertObjectsCollection(Arrays.asList(array)); - // } + private void assertObjectsArray(Object[] array) + { + assertObjectsCollection(Arrays.asList(array)); + } - // private void assertObjectsSpecificArray(Object[] array) - // { - // assertObjectsSpecificCollection(Arrays.asList(array)); - // } + private void assertObjectsSpecificArray(Object[] array) + { + assertObjectsSpecificCollection(Arrays.asList(array)); + } @SuppressWarnings("unchecked") private <T> T deserialize(Object object, Class<?> rootClass) throws Exception diff --git a/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/JsonTestObjectMapper.java b/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/JsonTestObjectMapper.java index 4aaec7ed0fb..80beb5f5873 100644 --- a/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/JsonTestObjectMapper.java +++ b/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/JsonTestObjectMapper.java @@ -18,10 +18,10 @@ package ch.systemsx.cisd.common.api.server.json; import org.codehaus.jackson.map.ObjectMapper; +import ch.systemsx.cisd.common.api.server.json.deserializer.JsonDeserializerFactory; import ch.systemsx.cisd.common.api.server.json.deserializer.JsonDeserializerProvider; import ch.systemsx.cisd.common.api.server.json.introspector.JsonTypeAndClassAnnotationIntrospector; import ch.systemsx.cisd.common.api.server.json.mapping.JsonReflectionsBaseTypeToSubTypesMapping; -import ch.systemsx.cisd.common.api.server.json.mapping.JsonReflectionsTypeValueToClassObjectMapping; import ch.systemsx.cisd.common.api.server.json.mapping.JsonStaticClassValueToClassObjectsMapping; import ch.systemsx.cisd.common.api.server.json.object.ObjectWithContainerTypes; import ch.systemsx.cisd.common.api.server.json.object.ObjectWithDateTypes; @@ -41,6 +41,7 @@ import ch.systemsx.cisd.common.api.server.json.object.ObjectWithTypeB; import ch.systemsx.cisd.common.api.server.json.object.ObjectWithTypeBIllegalDuplicate; import ch.systemsx.cisd.common.api.server.json.object.ObjectWithTypeButNoSubtypes; import ch.systemsx.cisd.common.api.server.json.resolver.JsonReflectionsSubTypeResolver; +import ch.systemsx.cisd.common.api.server.json.serializer.JsonSerializerFactory; /** * @author pkupczyk @@ -50,9 +51,6 @@ public class JsonTestObjectMapper extends ObjectMapper public JsonTestObjectMapper() { - JsonReflectionsTypeValueToClassObjectMapping typeMapping = - new JsonReflectionsTypeValueToClassObjectMapping(getClass().getPackage().getName()); - JsonReflectionsBaseTypeToSubTypesMapping subTypesMapping = new JsonReflectionsBaseTypeToSubTypesMapping(getClass().getPackage().getName()); @@ -82,7 +80,9 @@ public class JsonTestObjectMapper extends ObjectMapper setAnnotationIntrospector(new JsonTypeAndClassAnnotationIntrospector(classMapping)); setSubtypeResolver(new JsonReflectionsSubTypeResolver(subTypesMapping)); - setDeserializerProvider(new JsonDeserializerProvider(typeMapping, classMapping)); + setDeserializerProvider(new JsonDeserializerProvider(new JsonDeserializerFactory( + classMapping))); + setSerializerFactory(new JsonSerializerFactory()); } } diff --git a/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/object/ObjectWithContainerTypes.java b/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/object/ObjectWithContainerTypes.java index 75272f60e3b..76dcd06977c 100644 --- a/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/object/ObjectWithContainerTypes.java +++ b/openbis-common/sourceTest/java/ch/systemsx/cisd/common/api/server/json/object/ObjectWithContainerTypes.java @@ -17,6 +17,8 @@ package ch.systemsx.cisd.common.api.server.json.object; import java.util.Collection; +import java.util.LinkedHashSet; +import java.util.LinkedList; import java.util.List; import java.util.Map; @@ -37,22 +39,38 @@ public class ObjectWithContainerTypes public Collection<ObjectWithType> collectionWithSpecificType; + public LinkedHashSet linkedHashSetWithoutType; + + public Collection<Object> linkedHashSetWithObjectType; + + public Collection<ObjectWithType> linkedHashSetWithSpecificType; + public List listWithoutType; public List<Object> listWithObjectType; public List<ObjectWithType> listWithSpecificType; + public LinkedList linkedListWithoutType; + + public LinkedList<Object> linkedListWithObjectType; + + public LinkedList<ObjectWithType> linkedListWithSpecificType; + public Map mapWithoutType; public Map<String, Object> mapWithObjectType; public Map<String, ObjectWithType> mapWithSpecificType; - // TODO: check why it doesn't work properly during both serialization and deserialization + public Map linkedHashMapWithoutType; + + public Map<String, Object> linkedHashMapWithObjectType; + + public Map<String, ObjectWithType> linkedHashMapWithSpecificType; - // public Object[] arrayWithObjectType; + public Object[] arrayWithObjectType; - // public ObjectWithType[] arrayWithSpecificType; + public ObjectWithType[] arrayWithSpecificType; } diff --git a/openbis/source/java/ch/systemsx/cisd/openbis/generic/shared/api/json/GenericObjectMapper.java b/openbis/source/java/ch/systemsx/cisd/openbis/generic/shared/api/json/GenericObjectMapper.java index 323927d12c5..b419b9beee4 100644 --- a/openbis/source/java/ch/systemsx/cisd/openbis/generic/shared/api/json/GenericObjectMapper.java +++ b/openbis/source/java/ch/systemsx/cisd/openbis/generic/shared/api/json/GenericObjectMapper.java @@ -18,11 +18,12 @@ package ch.systemsx.cisd.openbis.generic.shared.api.json; import org.codehaus.jackson.map.ObjectMapper; +import ch.systemsx.cisd.common.api.server.json.deserializer.JsonDeserializerFactory; import ch.systemsx.cisd.common.api.server.json.deserializer.JsonDeserializerProvider; import ch.systemsx.cisd.common.api.server.json.introspector.JsonTypeAndClassAnnotationIntrospector; import ch.systemsx.cisd.common.api.server.json.mapping.JsonReflectionsBaseTypeToSubTypesMapping; -import ch.systemsx.cisd.common.api.server.json.mapping.JsonReflectionsTypeValueToClassObjectMapping; import ch.systemsx.cisd.common.api.server.json.resolver.JsonReflectionsSubTypeResolver; +import ch.systemsx.cisd.common.api.server.json.serializer.JsonSerializerFactory; /** * Jackson library object mapper used in generic OpenBIS. @@ -38,9 +39,8 @@ public class GenericObjectMapper extends ObjectMapper GenericJsonClassValueToClassObjectsMapping.getInstance())); setSubtypeResolver(new JsonReflectionsSubTypeResolver( JsonReflectionsBaseTypeToSubTypesMapping.getInstance())); - setDeserializerProvider(new JsonDeserializerProvider( - JsonReflectionsTypeValueToClassObjectMapping.getInstance(), - GenericJsonClassValueToClassObjectsMapping.getInstance())); + setDeserializerProvider(new JsonDeserializerProvider(new JsonDeserializerFactory( + GenericJsonClassValueToClassObjectsMapping.getInstance()))); + setSerializerFactory(new JsonSerializerFactory()); } - } diff --git a/screening/source/java/ch/systemsx/cisd/openbis/plugin/screening/shared/api/json/ScreeningObjectMapper.java b/screening/source/java/ch/systemsx/cisd/openbis/plugin/screening/shared/api/json/ScreeningObjectMapper.java index 8be41e89ed2..13c9b638c3d 100644 --- a/screening/source/java/ch/systemsx/cisd/openbis/plugin/screening/shared/api/json/ScreeningObjectMapper.java +++ b/screening/source/java/ch/systemsx/cisd/openbis/plugin/screening/shared/api/json/ScreeningObjectMapper.java @@ -18,11 +18,13 @@ package ch.systemsx.cisd.openbis.plugin.screening.shared.api.json; import org.codehaus.jackson.map.ObjectMapper; +import ch.systemsx.cisd.common.api.server.json.deserializer.JsonDeserializerFactory; import ch.systemsx.cisd.common.api.server.json.deserializer.JsonDeserializerProvider; import ch.systemsx.cisd.common.api.server.json.introspector.JsonTypeAndClassAnnotationIntrospector; import ch.systemsx.cisd.common.api.server.json.mapping.JsonReflectionsBaseTypeToSubTypesMapping; -import ch.systemsx.cisd.common.api.server.json.mapping.JsonReflectionsTypeValueToClassObjectMapping; import ch.systemsx.cisd.common.api.server.json.resolver.JsonReflectionsSubTypeResolver; +import ch.systemsx.cisd.common.api.server.json.serializer.JsonSerializerFactory; +import ch.systemsx.cisd.openbis.generic.shared.api.json.GenericJsonClassValueToClassObjectsMapping; /** * Jackson library object mapper used in screening OpenBIS. @@ -38,9 +40,9 @@ public class ScreeningObjectMapper extends ObjectMapper ScreeningJsonClassValueToClassObjectsMapping.getInstance())); setSubtypeResolver(new JsonReflectionsSubTypeResolver( JsonReflectionsBaseTypeToSubTypesMapping.getInstance())); - setDeserializerProvider(new JsonDeserializerProvider( - JsonReflectionsTypeValueToClassObjectMapping.getInstance(), - ScreeningJsonClassValueToClassObjectsMapping.getInstance())); + setDeserializerProvider(new JsonDeserializerProvider(new JsonDeserializerFactory( + GenericJsonClassValueToClassObjectsMapping.getInstance()))); + setSerializerFactory(new JsonSerializerFactory()); } } -- GitLab