[OLINGO-1505]Support instance annotation for Stream property
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/deserializer/json/ODataJsonDeserializer.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/deserializer/json/ODataJsonDeserializer.java
index babc5a0..4e09c7a 100644
--- a/lib/server-core/src/main/java/org/apache/olingo/server/core/deserializer/json/ODataJsonDeserializer.java
+++ b/lib/server-core/src/main/java/org/apache/olingo/server/core/deserializer/json/ODataJsonDeserializer.java
@@ -115,6 +115,9 @@
private static final String ODATA_ANNOTATION_MARKER = "@";
private static final String ODATA_CONTROL_INFORMATION_PREFIX = "@odata.";
private static final String REASON = "reason";
+ private static final String ODATA_STREAM_PROPERTY_MEDIA_READ_LINK = "mediaReadLink";
+ private static final String ODATA_STREAM_PROPERTY_MEDIA_EDIT_LINK = "mediaEditLink";
+ private static final String ODATA_STREAM_PROPERTY_MEDIA_MIME_TYPE = "mediaMimeType";
private final boolean isIEEE754Compatible;
private ServiceMetadata serviceMetadata;
@@ -479,6 +482,9 @@
entity.getAnnotations().add(annotation);
}
toRemove.add(field.getKey());
+ } else if (isStreamPropertyNode(field.getKey())) {
+ consumeStreamPropertyNode(entity, edmEntityType, field);
+ toRemove.add(field.getKey());
}
}
// remove here to avoid iterator issues.
@@ -487,6 +493,53 @@
removeAnnotations(node);
}
+ /**
+ * Process stream property instance annotation,
+ * include
+ * <ul>
+ * <li>odata.mediaReadLink for 4.0 or mediaReadLink for 4.01</li>
+ * <li>odata.mediaEditLink for 4.0 or mediaEditLink for 4.01</li>
+ * <li>odata.mediaMimeType for 4.0 or mediaMimeType for 4.01</li>
+ * </ul>
+ *
+ * @return true if jsonNodeKey present stream property annotation, false for otherwise
+ */
+ private boolean isStreamPropertyNode(String jsonNodeKey) {
+ return jsonNodeKey.endsWith(ODATA_STREAM_PROPERTY_MEDIA_READ_LINK)
+ || jsonNodeKey.endsWith(ODATA_STREAM_PROPERTY_MEDIA_EDIT_LINK)
+ || jsonNodeKey.endsWith(ODATA_STREAM_PROPERTY_MEDIA_MIME_TYPE);
+ }
+
+ /**
+ * Construct a empty {@code Property} and fill stream property annotation data into it
+ *
+ * @param entity entity instance which is filled
+ * @param edmEntityType edm entity type which for which the json node is consumed
+ * @param field Json field entry which current consuming
+ *
+ * @throws DeserializerException thrown by {@code instanceAnnotDeserializer} if consume
+ * instance annotation failed
+ */
+ private void consumeStreamPropertyNode(final Entity entity,
+ final EdmEntityType edmEntityType,
+ final Entry<String, JsonNode> field) throws DeserializerException {
+ String[] keySplit = field.getKey().split(ODATA_ANNOTATION_MARKER);
+ String termName = keySplit[1];
+ Annotation annotation = instanceAnnotDeserializer.consumeInstanceAnnotation(termName, field.getValue());
+ String propertyName = keySplit[0];
+ if(edmEntityType.getProperty(propertyName) == null) {
+ return;
+ }
+
+ Property property = entity.getProperty(propertyName);
+ if(property == null) {
+ property = new Property();
+ property.setName(propertyName);
+ entity.addProperty(property);
+ }
+ property.getAnnotations().add(annotation);
+ }
+
private void consumeEntityProperties(final EdmEntityType edmEntityType, final ObjectNode node,
final Entity entity) throws DeserializerException {
List<String> propertyNames = edmEntityType.getPropertyNames();
@@ -929,7 +982,7 @@
/**
* Returns the primitive type's default class or the manually mapped class if present.
* @param mapping
- * @param edmPrimitiveType
+ * @param type
* @return the java class to be used during deserialization
*/
private Class<?> getJavaClassForPrimitiveType(final EdmMapping mapping, final EdmPrimitiveType type) {
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/deserializer/json/ODataJsonInstanceAnnotationDeserializer.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/deserializer/json/ODataJsonInstanceAnnotationDeserializer.java
index 0ac5251..d00f641 100644
--- a/lib/server-core/src/main/java/org/apache/olingo/server/core/deserializer/json/ODataJsonInstanceAnnotationDeserializer.java
+++ b/lib/server-core/src/main/java/org/apache/olingo/server/core/deserializer/json/ODataJsonInstanceAnnotationDeserializer.java
@@ -108,7 +108,7 @@
case PRIMITIVE:
if (valuable.getType() == null && typeInfo != null) {
- valuable.setType(typeInfo.getFullQualifiedName().toString());
+ valuable.setType(typeInfo.getPrimitiveTypeKind().name());
}
final Object primitiveValue = fromPrimitive(node, typeInfo);
valuable.setValue(primitiveValue instanceof Geospatial ?
diff --git a/lib/server-test/src/test/java/org/apache/olingo/server/core/deserializer/json/ODataJsonDeserializerWithInstanceAnnotationsTest.java b/lib/server-test/src/test/java/org/apache/olingo/server/core/deserializer/json/ODataJsonDeserializerWithInstanceAnnotationsTest.java
index ab4b2eb..283be48 100644
--- a/lib/server-test/src/test/java/org/apache/olingo/server/core/deserializer/json/ODataJsonDeserializerWithInstanceAnnotationsTest.java
+++ b/lib/server-test/src/test/java/org/apache/olingo/server/core/deserializer/json/ODataJsonDeserializerWithInstanceAnnotationsTest.java
@@ -231,7 +231,43 @@
assertEquals(ValueType.COLLECTION_COMPLEX, complxProperties.get(1).getValueType());
assertEquals(2, complxProperties.get(1).asCollection().size());
}
-
+
+ @Test
+ public void instanceAnnotationForStreamProperty() throws DeserializerException {
+ final String entityString = "{"
+ + "\"@odata.context\":\"$metadata#ETWithStream/$entity\","
+ + "\"PropertyInt16@odata.type\":\"#Int16\","
+ + "\"PropertyInt16\":32767,"
+ + "\"PropertyStream@odata.mediaReadLink\":\"http://mockReadLink1\","
+ + "\"PropertyStream@odata.mediaEditLink\":\"http://mockEditLink1\","
+ + "\"PropertyStream@odata.mediaMimeType\":\"image/png\","
+ + "\"PropertyStream@mediaReadLink\":\"http://mockReadLink2\","
+ + "\"PropertyStream@mediaEditLink\":\"http://mockEditLink2\","
+ + "\"PropertyStream@mediaMimeType\":\"image/jpeg\""
+ +"}";
+ final Entity entity = deserialize(entityString, "ETWithStream");
+ assertNotNull(entity);
+ Property propertyStream = entity.getProperty("PropertyStream");
+ assertNotNull(propertyStream);
+ List<Annotation> annotations = propertyStream.getAnnotations();
+ assertEquals(6, annotations.size());
+ for(Annotation annotation : annotations) {
+ if("odata.mediaReadLink".equals(annotation.getTerm())) {
+ assertEquals("http://mockReadLink1", annotation.getValue().toString());
+ } else if("odata.mediaEditLink".equals(annotation.getTerm())) {
+ assertEquals("http://mockEditLink1", annotation.getValue().toString());
+ } else if("odata.mediaMimeType".equals(annotation.getTerm())) {
+ assertEquals("image/png", annotation.getValue().toString());
+ } else if("mediaReadLink".equals(annotation.getTerm())) {
+ assertEquals("http://mockReadLink2", annotation.getValue().toString());
+ } else if("mediaEditLink".equals(annotation.getTerm())) {
+ assertEquals("http://mockEditLink2", annotation.getValue().toString());
+ } else if("mediaMimeType".equals(annotation.getTerm())) {
+ assertEquals("image/jpeg", annotation.getValue().toString());
+ }
+ }
+ }
+
protected static DeserializerResult deserializeWithResultWithConstantV401(final InputStream stream,
final String entityTypeName, final ContentType contentType)
throws DeserializerException {