You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@olingo.apache.org by il...@apache.org on 2014/04/23 18:28:05 UTC

[2/2] git commit: [OLINGO-234] All tests moved to fit

[OLINGO-234] All tests moved to fit


Project: http://git-wip-us.apache.org/repos/asf/olingo-odata4/repo
Commit: http://git-wip-us.apache.org/repos/asf/olingo-odata4/commit/713ed0ef
Tree: http://git-wip-us.apache.org/repos/asf/olingo-odata4/tree/713ed0ef
Diff: http://git-wip-us.apache.org/repos/asf/olingo-odata4/diff/713ed0ef

Branch: refs/heads/master
Commit: 713ed0efa5a9d03aa7570630609c59a152de529a
Parents: f87321f
Author: Francesco Chicchiriccò <il...@apache.org>
Authored: Wed Apr 23 18:27:55 2014 +0200
Committer: Francesco Chicchiriccò <il...@apache.org>
Committed: Wed Apr 23 18:27:55 2014 +0200

----------------------------------------------------------------------
 .../org/apache/olingo/fit/AbstractServices.java |  26 +-
 .../java/org/apache/olingo/fit/V4Services.java  | 365 ++++++++++++++-----
 .../fit/serializer/JSONEntryContainer.java      |  36 ++
 .../fit/serializer/JSONFeedContainer.java       |  36 ++
 .../fit/serializer/JSONPropertyContainer.java   |  36 ++
 .../fit/serializer/JsonEntryContainer.java      |  35 --
 .../fit/serializer/JsonFeedContainer.java       |  35 --
 .../fit/serializer/JsonPropertyContainer.java   |  35 --
 .../olingo/fit/utils/AbstractJSONUtilities.java |   2 +-
 .../olingo/fit/utils/AbstractUtilities.java     | 109 ++++--
 .../org/apache/olingo/fit/utils/Commons.java    |   2 +-
 .../org/apache/olingo/fit/utils/DataBinder.java |  45 +--
 .../org/apache/olingo/fit/utils/FSManager.java  |   9 +-
 .../main/resources/V40/Accounts/101/entity.xml  |   9 +
 .../V40/Accounts/101/links/MyGiftCard.full.json |  15 +
 .../V40/Accounts/101/links/MyGiftCard.xml       |  41 +++
 fit/src/main/resources/V40/Company/entity.xml   |   6 +
 .../resources/V40/Customers/2/entity.full.json  |  50 +++
 .../main/resources/V40/Customers/2/entity.xml   |  63 ++++
 .../resources/V40/ProductDetails/6 1/entity.xml |   3 +
 .../resources/V40/Products/5/entity.full.json   |  29 ++
 .../main/resources/V40/Products/5/entity.xml    |  55 +++
 .../resources/V40/Products/6/entity.full.json   |  29 ++
 .../main/resources/V40/Products/6/entity.xml    |  48 +++
 .../invoke/AbstractODataInvokeRequest.java      |  15 +-
 .../it/v4/BoundOperationInvokeTestITCase.java   | 102 ++----
 .../it/v4/OperationImportInvokeTestITCase.java  |   1 -
 .../commons/core/data/AtomSerializer.java       |  14 +-
 .../commons/core/data/JSONEntrySerializer.java  |  10 +
 29 files changed, 920 insertions(+), 341 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/AbstractServices.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/AbstractServices.java b/fit/src/main/java/org/apache/olingo/fit/AbstractServices.java
index 03c59e4..6ff2c11 100644
--- a/fit/src/main/java/org/apache/olingo/fit/AbstractServices.java
+++ b/fit/src/main/java/org/apache/olingo/fit/AbstractServices.java
@@ -80,7 +80,6 @@ import org.apache.olingo.commons.core.data.AtomEntryImpl;
 import org.apache.olingo.commons.core.data.AtomPropertyImpl;
 import org.apache.olingo.commons.core.data.AtomSerializer;
 import org.apache.olingo.commons.core.data.JSONEntryImpl;
-import org.apache.olingo.commons.core.data.JSONFeedImpl;
 import org.apache.olingo.commons.core.data.NullValueImpl;
 import org.apache.olingo.commons.core.data.PrimitiveValueImpl;
 import org.apache.olingo.fit.metadata.EntitySet;
@@ -97,8 +96,8 @@ import org.apache.olingo.fit.utils.AbstractUtilities;
 import org.apache.olingo.fit.utils.AbstractXMLUtilities;
 import org.apache.olingo.fit.utils.LinkInfo;
 import org.apache.olingo.fit.metadata.Metadata;
-import org.apache.olingo.fit.serializer.JsonFeedContainer;
-import org.apache.olingo.fit.serializer.JsonEntryContainer;
+import org.apache.olingo.fit.serializer.JSONFeedContainer;
+import org.apache.olingo.fit.serializer.JSONEntryContainer;
 import org.apache.olingo.fit.utils.ConstantKey;
 import org.apache.olingo.fit.utils.Constants;
 import org.apache.olingo.fit.utils.DataBinder;
@@ -138,7 +137,7 @@ public abstract class AbstractServices {
     this.version = version;
     this.atomDeserializer = Commons.getAtomDeserializer(version);
     this.atomSerializer = Commons.getAtomSerializer(version);
-    this.mapper = Commons.getJsonMapper(version);
+    this.mapper = Commons.getJSONMapper(version);
     this.dataBinder = new DataBinder(version);
 
     if (version.compareTo(ODataServiceVersion.V30) <= 0) {
@@ -421,7 +420,7 @@ public abstract class AbstractServices {
                 mapper.readValue(IOUtils.toInputStream(changes), new TypeReference<JSONEntryImpl>() {
                 });
 
-        entryChanges = dataBinder.getAtomEntry(jcont.getObject());
+        entryChanges = dataBinder.toAtomEntry(jcont.getObject());
       }
 
       final Container<AtomEntryImpl> container = atomDeserializer.read(entityInfo.getValue(), AtomEntryImpl.class);
@@ -511,7 +510,7 @@ public abstract class AbstractServices {
         final Container<JSONEntryImpl> jcont = mapper.readValue(res, new TypeReference<JSONEntryImpl>() {
         });
         cres = new Container<AtomEntryImpl>(jcont.getContextURL(), jcont.getMetadataETag(),
-                dataBinder.getAtomEntry(jcont.getObject()));
+                dataBinder.toAtomEntry(jcont.getObject()));
       }
 
       final String path = Commons.getEntityBasePath(entitySetName, entityId);
@@ -611,7 +610,7 @@ public abstract class AbstractServices {
                   mapper.readValue(IOUtils.toInputStream(entity), new TypeReference<JSONEntryImpl>() {
                   });
 
-          entry = dataBinder.getAtomEntry(jcontainer.getObject());
+          entry = dataBinder.toAtomEntry(jcontainer.getObject());
 
           container = new Container<AtomEntryImpl>(
                   jcontainer.getContextURL(),
@@ -887,8 +886,8 @@ public abstract class AbstractServices {
           writer.close();
         } else {
           mapper.writeValue(
-                  writer, new JsonFeedContainer<JSONFeedImpl>(container.getContextURL(), container.getMetadataETag(),
-                          dataBinder.getJsonFeed(container.getObject())));
+                  writer, new JSONFeedContainer(container.getContextURL(), container.getMetadataETag(),
+                          dataBinder.toJSONFeed(container.getObject())));
         }
 
         return xml.createResponse(
@@ -1076,7 +1075,6 @@ public abstract class AbstractServices {
               xml.writeEntry(utils.getKey(), container),
               Commons.getETag(entityInfo.getKey(), version),
               utils.getKey());
-
     } catch (Exception e) {
       LOG.error("Error retrieving entity", e);
       return xml.createFaultResponse(accept, e);
@@ -1502,9 +1500,9 @@ public abstract class AbstractServices {
             } else {
               mapper.writeValue(
                       writer,
-                      new JsonFeedContainer<JSONFeedImpl>(container.getContextURL(),
+                      new JSONFeedContainer(container.getContextURL(),
                               container.getMetadataETag(),
-                              dataBinder.getJsonFeed((AtomFeedImpl) container.getObject())));
+                              dataBinder.toJSONFeed((AtomFeedImpl) container.getObject())));
             }
           } else {
             final Container<Entry> container = atomDeserializer.<Entry, AtomEntryImpl>read(stream, AtomEntryImpl.class);
@@ -1515,9 +1513,9 @@ public abstract class AbstractServices {
             } else {
               mapper.writeValue(
                       writer,
-                      new JsonEntryContainer<JSONEntryImpl>(container.getContextURL(),
+                      new JSONEntryContainer(container.getContextURL(),
                               container.getMetadataETag(),
-                              dataBinder.getJsonEntry((AtomEntryImpl) container.getObject())));
+                              dataBinder.toJSONEntry((AtomEntryImpl) container.getObject())));
             }
           }
 

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/V4Services.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/V4Services.java b/fit/src/main/java/org/apache/olingo/fit/V4Services.java
index 9165af1..60c2e05 100644
--- a/fit/src/main/java/org/apache/olingo/fit/V4Services.java
+++ b/fit/src/main/java/org/apache/olingo/fit/V4Services.java
@@ -25,7 +25,6 @@ import java.io.File;
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.OutputStreamWriter;
-import java.io.StringWriter;
 import java.net.URI;
 import java.util.HashMap;
 import java.util.List;
@@ -62,13 +61,10 @@ import org.apache.olingo.commons.core.data.AtomPropertyImpl;
 import org.apache.olingo.commons.core.data.CollectionValueImpl;
 import org.apache.olingo.commons.core.data.EnumValueImpl;
 import org.apache.olingo.commons.core.data.JSONEntryImpl;
-import org.apache.olingo.commons.core.data.JSONFeedImpl;
 import org.apache.olingo.commons.core.data.JSONPropertyImpl;
 import org.apache.olingo.commons.core.data.PrimitiveValueImpl;
 import org.apache.olingo.commons.core.edm.EdmTypeInfo;
 import org.apache.olingo.fit.methods.PATCH;
-import org.apache.olingo.fit.serializer.JsonFeedContainer;
-import org.apache.olingo.fit.serializer.JsonPropertyContainer;
 import org.apache.olingo.fit.utils.AbstractUtilities;
 import org.apache.olingo.fit.utils.Accept;
 import org.apache.olingo.fit.utils.ConstantKey;
@@ -180,6 +176,266 @@ public class V4Services extends AbstractServices {
     return new ByteArrayInputStream(bos.toByteArray());
   }
 
+  @GET
+  @Path("/Company")
+  public Response getSingletonCompany(
+          @Context UriInfo uriInfo,
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format) {
+
+    return getEntityInternal(
+            uriInfo.getRequestUri().toASCIIString(), accept, "Company", StringUtils.EMPTY, format, null, null, false);
+  }
+
+  @GET
+  @Path("/Company/Microsoft.Test.OData.Services.ODataWCFService.GetEmployeesCount")
+  public Response functionGetEmployeesCount(
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format) {
+
+    try {
+      final Accept acceptType;
+      if (StringUtils.isNotBlank(format)) {
+        acceptType = Accept.valueOf(format.toUpperCase());
+      } else {
+        acceptType = Accept.parse(accept, version);
+      }
+
+      final AtomPropertyImpl property = new AtomPropertyImpl();
+      property.setType("Edm.Int32");
+      property.setValue(new PrimitiveValueImpl("2"));
+      final Container<AtomPropertyImpl> container = new Container<AtomPropertyImpl>(
+              URI.create(Constants.get(version, ConstantKey.ODATA_METADATA_PREFIX) + property.getType()), null,
+              property);
+
+      return xml.createResponse(
+              null,
+              xml.writeProperty(acceptType, container),
+              null,
+              acceptType);
+    } catch (Exception e) {
+      return xml.createFaultResponse(accept, e);
+    }
+  }
+
+  @POST
+  @Path("/Company/Microsoft.Test.OData.Services.ODataWCFService.IncreaseRevenue")
+  public Response actionIncreaseRevenue(
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @HeaderParam("Content-Type") @DefaultValue(StringUtils.EMPTY) String contentType,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format,
+          final String param) {
+
+    try {
+      final Accept acceptType;
+      if (StringUtils.isNotBlank(format)) {
+        acceptType = Accept.valueOf(format.toUpperCase());
+      } else {
+        acceptType = Accept.parse(accept, version);
+      }
+
+      final Accept contentTypeValue = Accept.parse(contentType, version);
+      final Entry entry = xml.readEntry(contentTypeValue, IOUtils.toInputStream(param, Constants.ENCODING));
+      
+      return xml.createResponse(
+              null,
+              xml.writeProperty(acceptType, entry.getProperty("IncreaseValue")),
+              null,
+              acceptType);
+    } catch (Exception e) {
+      return xml.createFaultResponse(accept, e);
+    }
+  }
+
+  @GET
+  @Path("/Products({entityId})/Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails({param:.*})")
+  public Response functionGetProductDetails(
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @PathParam("entityId") String entityId,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format) {
+
+    try {
+      final Accept acceptType;
+      if (StringUtils.isNotBlank(format)) {
+        acceptType = Accept.valueOf(format.toUpperCase());
+      } else {
+        acceptType = Accept.parse(accept, version);
+      }
+
+      final AtomEntryImpl entry = new AtomEntryImpl();
+      entry.setType("Microsoft.Test.OData.Services.ODataWCFService.ProductDetail");
+      final Property productId = new AtomPropertyImpl();
+      productId.setName("ProductID");
+      productId.setType("Edm.Int32");
+      productId.setValue(new PrimitiveValueImpl(entityId));
+      entry.getProperties().add(productId);
+      final Property productDetailId = new AtomPropertyImpl();
+      productDetailId.setName("ProductDetailID");
+      productDetailId.setType("Edm.Int32");
+      productDetailId.setValue(new PrimitiveValueImpl("2"));
+      entry.getProperties().add(productDetailId);
+
+      final AtomFeedImpl feed = new AtomFeedImpl();
+      feed.getEntries().add(entry);
+
+      final Container<AtomFeedImpl> container = new Container<AtomFeedImpl>(
+              URI.create(Constants.get(version, ConstantKey.ODATA_METADATA_PREFIX) + "ProductDetail"), null,
+              feed);
+
+      return xml.createResponse(
+              null,
+              xml.writeFeed(acceptType, container),
+              null,
+              acceptType);
+    } catch (Exception e) {
+      return xml.createFaultResponse(accept, e);
+    }
+  }
+
+  @POST
+  @Path("/Products({entityId})/Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight")
+  public Response actionAddAccessRight(
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @HeaderParam("Content-Type") @DefaultValue(StringUtils.EMPTY) String contentType,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format,
+          final String param) {
+
+    try {
+      final Accept acceptType;
+      if (StringUtils.isNotBlank(format)) {
+        acceptType = Accept.valueOf(format.toUpperCase());
+      } else {
+        acceptType = Accept.parse(accept, version);
+      }
+
+      final Accept contentTypeValue = Accept.parse(contentType, version);
+      final Entry entry = xml.readEntry(contentTypeValue, IOUtils.toInputStream(param, Constants.ENCODING));
+
+      assert 1 == entry.getProperties().size();
+      assert entry.getProperty("accessRight") != null;
+
+      entry.getProperty("accessRight").setType("Microsoft.Test.OData.Services.ODataWCFService.AccessLevel");
+
+      return xml.createResponse(
+              null,
+              xml.writeProperty(acceptType, entry.getProperty("accessRight")),
+              null,
+              acceptType);
+    } catch (Exception e) {
+      return xml.createFaultResponse(accept, e);
+    }
+  }
+
+  @POST
+  @Path("/Customers(PersonID={personId})/Microsoft.Test.OData.Services.ODataWCFService.ResetAddress")
+  public Response actionResetAddress(
+          @Context UriInfo uriInfo,
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @PathParam("personId") String personId,
+          @HeaderParam("Content-Type") @DefaultValue(StringUtils.EMPTY) String contentType,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format,
+          final String param) {
+
+    try {
+      final Accept contentTypeValue = Accept.parse(contentType, version);
+      final Entry entry = xml.readEntry(contentTypeValue, IOUtils.toInputStream(param, Constants.ENCODING));
+
+      assert 2 == entry.getProperties().size();
+      assert entry.getProperty("addresses") != null;
+      assert entry.getProperty("index") != null;
+
+      return getEntityInternal(
+              uriInfo.getRequestUri().toASCIIString(), accept, "Customers", personId, format, null, null, false);
+    } catch (Exception e) {
+      return xml.createFaultResponse(accept, e);
+    }
+  }
+
+  @GET
+  @Path("/ProductDetails(ProductID={productId},ProductDetailID={productDetailId})"
+          + "/Microsoft.Test.OData.Services.ODataWCFService.GetRelatedProduct")
+  public Response functionGetRelatedProduct(
+          @Context UriInfo uriInfo,
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @PathParam("productId") String productId,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format) {
+
+    return getEntityInternal(
+            uriInfo.getRequestUri().toASCIIString(), accept, "Products", productId, format, null, null, false);
+  }
+
+  @POST
+  @Path("/Accounts(101)/Microsoft.Test.OData.Services.ODataWCFService.RefreshDefaultPI")
+  public Response actionRefreshDefaultPI(
+          @Context UriInfo uriInfo,
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @HeaderParam("Content-Type") @DefaultValue(StringUtils.EMPTY) String contentType,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format,
+          final String param) {
+
+    try {
+      final Accept contentTypeValue = Accept.parse(contentType, version);
+      final Entry entry = xml.readEntry(contentTypeValue, IOUtils.toInputStream(param, Constants.ENCODING));
+      
+      assert 1 == entry.getProperties().size();
+      assert entry.getProperty("newDate") != null;
+
+      return functionGetDefaultPI(accept, format);
+    } catch (Exception e) {
+      return xml.createFaultResponse(accept, e);
+    }
+  }
+
+  @GET
+  @Path("/Accounts(101)/Microsoft.Test.OData.Services.ODataWCFService.GetDefaultPI")
+  public Response functionGetDefaultPI(
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format) {
+
+    return getContainedEntity(accept, "101", "MyPaymentInstruments", "101901", format);
+  }
+
+  @GET
+  @Path("/Accounts({entityId})/Microsoft.Test.OData.Services.ODataWCFService.GetAccountInfo")
+  public Response functionGetAccountInfo(
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @PathParam("entityId") String entityId,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format) {
+
+    return getPath(accept, "Accounts", entityId, "AccountInfo", format);
+  }
+
+  @GET
+  @Path("/Accounts({entityId})/MyGiftCard/Microsoft.Test.OData.Services.ODataWCFService.GetActualAmount({param:.*})")
+  public Response functionGetActualAmount(
+          @HeaderParam("Accept") @DefaultValue(StringUtils.EMPTY) String accept,
+          @PathParam("entityId") String entityId,
+          @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format) {
+
+    try {
+      final Accept acceptType;
+      if (StringUtils.isNotBlank(format)) {
+        acceptType = Accept.valueOf(format.toUpperCase());
+      } else {
+        acceptType = Accept.parse(accept, version);
+      }
+
+      final AtomPropertyImpl property = new AtomPropertyImpl();
+      property.setType("Edm.Double");
+      property.setValue(new PrimitiveValueImpl("41.79"));
+
+      final Container<AtomPropertyImpl> container = new Container<AtomPropertyImpl>(null, null, property);
+
+      return xml.createResponse(
+              null,
+              xml.writeProperty(acceptType, container),
+              null,
+              acceptType);
+    } catch (Exception e) {
+      return xml.createFaultResponse(accept, e);
+    }
+  }
+
   /**
    * Retrieve entity reference sample.
    *
@@ -280,9 +536,11 @@ public class V4Services extends AbstractServices {
         throw new UnsupportedMediaTypeException("Unsupported media type");
       }
 
-      final InputStream entry = FSManager.instance(version).
-              readFile(containedPath(entityId, containedEntitySetName).
-                      append('(').append(containedEntityId).append(')').toString(), Accept.ATOM);
+      final StringBuilder containedPath = containedPath(entityId, containedEntitySetName);
+      if (StringUtils.isNotBlank(containedEntityId)) {
+        containedPath.append('(').append(containedEntityId).append(')');
+      }
+      final InputStream entry = FSManager.instance(version).readFile(containedPath.toString(), Accept.ATOM);
 
       final Container<AtomEntryImpl> container = atomDeserializer.read(entry, AtomEntryImpl.class);
 
@@ -306,7 +564,6 @@ public class V4Services extends AbstractServices {
           @PathParam("containedEntitySetName") String containedEntitySetName,
           final String entity) {
 
-    // default
     try {
       final Accept acceptType = Accept.parse(accept, version);
       if (acceptType == Accept.XML || acceptType == Accept.TEXT) {
@@ -327,7 +584,7 @@ public class V4Services extends AbstractServices {
                 mapper.readValue(IOUtils.toInputStream(entity), new TypeReference<JSONEntryImpl>() {
                 });
 
-        entry = dataBinder.getAtomEntry(jcontainer.getObject());
+        entry = dataBinder.toAtomEntry(jcontainer.getObject());
 
         entryContainer = new Container<AtomEntryImpl>(
                 jcontainer.getContextURL(),
@@ -425,7 +682,7 @@ public class V4Services extends AbstractServices {
                 new TypeReference<JSONEntryImpl>() {
                 });
         jsonContainer.getObject().setType(typeInfo.getFullQualifiedName().toString());
-        entryChanges = dataBinder.getAtomEntry(jsonContainer.getObject());
+        entryChanges = dataBinder.toAtomEntry(jsonContainer.getObject());
       }
 
       for (Property property : entryChanges.getProperties()) {
@@ -494,6 +751,10 @@ public class V4Services extends AbstractServices {
           @PathParam("containedEntitySetName") String containedEntitySetName,
           @QueryParam("$format") @DefaultValue(StringUtils.EMPTY) String format) {
 
+    if ("MyGiftCard".equals(containedEntitySetName)) {
+      return getContainedEntity(accept, entityId, containedEntitySetName, null, format);
+    }
+
     try {
       final Accept acceptType;
       if (StringUtils.isNotBlank(format)) {
@@ -510,22 +771,9 @@ public class V4Services extends AbstractServices {
 
       final Container<AtomFeedImpl> container = atomDeserializer.read(feed, AtomFeedImpl.class);
 
-      final ByteArrayOutputStream content = new ByteArrayOutputStream();
-      final OutputStreamWriter writer = new OutputStreamWriter(content, Constants.ENCODING);
-
-      if (acceptType == Accept.ATOM) {
-        atomSerializer.write(writer, container);
-        writer.flush();
-        writer.close();
-      } else {
-        mapper.writeValue(
-                writer, new JsonFeedContainer<JSONFeedImpl>(container.getContextURL(), container.getMetadataETag(),
-                        dataBinder.getJsonFeed(container.getObject())));
-      }
-
       return xml.createResponse(
               null,
-              new ByteArrayInputStream(content.toByteArray()),
+              xml.writeFeed(acceptType, container),
               null,
               acceptType);
     } catch (Exception e) {
@@ -554,22 +802,9 @@ public class V4Services extends AbstractServices {
               URI.create(Constants.get(version, ConstantKey.ODATA_METADATA_PREFIX) + property.getType()), null,
               property);
 
-      final ByteArrayOutputStream content = new ByteArrayOutputStream();
-      final OutputStreamWriter writer = new OutputStreamWriter(content, Constants.ENCODING);
-
-      if (acceptType == Accept.XML) {
-        atomSerializer.write(writer, container);
-        writer.flush();
-        writer.close();
-      } else {
-        mapper.writeValue(
-                writer, new JsonPropertyContainer<JSONPropertyImpl>(container.getContextURL(),
-                        container.getMetadataETag(), dataBinder.getJsonProperty(container.getObject())));
-      }
-
       return xml.createResponse(
               null,
-              new ByteArrayInputStream(content.toByteArray()),
+              xml.writeProperty(acceptType, container),
               null,
               acceptType);
     } catch (Exception e) {
@@ -637,22 +872,9 @@ public class V4Services extends AbstractServices {
               URI.create(Constants.get(version, ConstantKey.ODATA_METADATA_PREFIX) + property.getType()), null,
               property);
 
-      final ByteArrayOutputStream content = new ByteArrayOutputStream();
-      final OutputStreamWriter writer = new OutputStreamWriter(content, Constants.ENCODING);
-
-      if (acceptType == Accept.XML) {
-        atomSerializer.write(writer, container);
-        writer.flush();
-        writer.close();
-      } else {
-        mapper.writeValue(
-                writer, new JsonPropertyContainer<JSONPropertyImpl>(container.getContextURL(),
-                        container.getMetadataETag(), dataBinder.getJsonProperty(container.getObject())));
-      }
-
       return xml.createResponse(
               null,
-              new ByteArrayInputStream(content.toByteArray()),
+              xml.writeProperty(acceptType, container),
               null,
               acceptType);
     } catch (Exception e) {
@@ -685,22 +907,9 @@ public class V4Services extends AbstractServices {
               URI.create(Constants.get(version, ConstantKey.ODATA_METADATA_PREFIX) + property.getType()), null,
               property);
 
-      final ByteArrayOutputStream content = new ByteArrayOutputStream();
-      final OutputStreamWriter writer = new OutputStreamWriter(content, Constants.ENCODING);
-
-      if (acceptType == Accept.XML) {
-        atomSerializer.write(writer, container);
-        writer.flush();
-        writer.close();
-      } else {
-        mapper.writeValue(
-                writer, new JsonPropertyContainer<JSONPropertyImpl>(container.getContextURL(),
-                        container.getMetadataETag(), dataBinder.getJsonProperty(container.getObject())));
-      }
-
       return xml.createResponse(
               null,
-              new ByteArrayInputStream(content.toByteArray()),
+              xml.writeProperty(acceptType, container),
               null,
               acceptType);
     } catch (Exception e) {
@@ -785,7 +994,7 @@ public class V4Services extends AbstractServices {
 
       return xml.createResponse(
               null,
-              new ByteArrayInputStream(param.getBytes(Constants.ENCODING)),
+              IOUtils.toInputStream(param, Constants.ENCODING),
               null,
               acceptType);
     } catch (Exception e) {
@@ -810,33 +1019,15 @@ public class V4Services extends AbstractServices {
       }
 
       final Accept contentTypeValue = Accept.parse(contentType, version);
-      Entry entry;
-      if (contentTypeValue == Accept.XML) {
-        final Container<AtomEntryImpl> paramContainer = atomDeserializer.read(
-                IOUtils.toInputStream(param, Constants.ENCODING), AtomEntryImpl.class);
-        entry = paramContainer.getObject();
-      } else {
-        final Container<JSONEntryImpl> paramContainer =
-                mapper.readValue(IOUtils.toInputStream(param, Constants.ENCODING),
-                        new TypeReference<JSONEntryImpl>() {
-                        });
-        entry = paramContainer.getObject();
-      }
+      final Entry entry = xml.readEntry(contentTypeValue, IOUtils.toInputStream(param, Constants.ENCODING));
 
       assert 1 == entry.getProperties().size();
       assert "Collection(Edm.String)".equals(entry.getProperty("emails").getType());
       assert entry.getProperty("emails").getValue().isCollection();
 
-      final StringWriter writer = new StringWriter();
-      if (acceptType == Accept.XML) {
-        atomSerializer.write(writer, entry.getProperty("emails"));
-      } else {
-        mapper.writeValue(writer, entry.getProperty("emails"));
-      }
-
       return xml.createResponse(
               null,
-              new ByteArrayInputStream(writer.toString().getBytes(Constants.ENCODING)),
+              xml.writeProperty(acceptType, entry.getProperty("emails")),
               null,
               acceptType);
     } catch (Exception e) {

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/serializer/JSONEntryContainer.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/serializer/JSONEntryContainer.java b/fit/src/main/java/org/apache/olingo/fit/serializer/JSONEntryContainer.java
new file mode 100644
index 0000000..f61f36a
--- /dev/null
+++ b/fit/src/main/java/org/apache/olingo/fit/serializer/JSONEntryContainer.java
@@ -0,0 +1,36 @@
+/*
+ * 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
+ *
+ *   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 org.apache.olingo.fit.serializer;
+
+import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
+import com.fasterxml.jackson.databind.annotation.JsonSerialize;
+import java.net.URI;
+import org.apache.olingo.commons.api.data.Container;
+import org.apache.olingo.commons.core.data.JSONEntryDeserializer;
+import org.apache.olingo.commons.core.data.JSONEntryImpl;
+import org.apache.olingo.commons.core.data.JSONEntrySerializer;
+
+@JsonDeserialize(using = JSONEntryDeserializer.class)
+@JsonSerialize(using = JSONEntrySerializer.class)
+public class JSONEntryContainer extends Container<JSONEntryImpl> {
+
+  public JSONEntryContainer(final URI contextURL, final String metadataETag, final JSONEntryImpl object) {
+    super(contextURL, metadataETag, object);
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/serializer/JSONFeedContainer.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/serializer/JSONFeedContainer.java b/fit/src/main/java/org/apache/olingo/fit/serializer/JSONFeedContainer.java
new file mode 100644
index 0000000..3c64f4f
--- /dev/null
+++ b/fit/src/main/java/org/apache/olingo/fit/serializer/JSONFeedContainer.java
@@ -0,0 +1,36 @@
+/*
+ * 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
+ *
+ *   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 org.apache.olingo.fit.serializer;
+
+import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
+import com.fasterxml.jackson.databind.annotation.JsonSerialize;
+import java.net.URI;
+import org.apache.olingo.commons.api.data.Container;
+import org.apache.olingo.commons.core.data.JSONFeedDeserializer;
+import org.apache.olingo.commons.core.data.JSONFeedImpl;
+import org.apache.olingo.commons.core.data.JSONFeedSerializer;
+
+@JsonDeserialize(using = JSONFeedDeserializer.class)
+@JsonSerialize(using = JSONFeedSerializer.class)
+public class JSONFeedContainer extends Container<JSONFeedImpl> {
+
+  public JSONFeedContainer(final URI contextURL, final String metadataETag, final JSONFeedImpl object) {
+    super(contextURL, metadataETag, object);
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/serializer/JSONPropertyContainer.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/serializer/JSONPropertyContainer.java b/fit/src/main/java/org/apache/olingo/fit/serializer/JSONPropertyContainer.java
new file mode 100644
index 0000000..2cf7a7c
--- /dev/null
+++ b/fit/src/main/java/org/apache/olingo/fit/serializer/JSONPropertyContainer.java
@@ -0,0 +1,36 @@
+/*
+ * 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
+ *
+ *   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 org.apache.olingo.fit.serializer;
+
+import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
+import com.fasterxml.jackson.databind.annotation.JsonSerialize;
+import java.net.URI;
+import org.apache.olingo.commons.api.data.Container;
+import org.apache.olingo.commons.core.data.JSONPropertyDeserializer;
+import org.apache.olingo.commons.core.data.JSONPropertyImpl;
+import org.apache.olingo.commons.core.data.JSONPropertySerializer;
+
+@JsonDeserialize(using = JSONPropertyDeserializer.class)
+@JsonSerialize(using = JSONPropertySerializer.class)
+public class JSONPropertyContainer extends Container<JSONPropertyImpl> {
+
+  public JSONPropertyContainer(final URI contextURL, final String metadataETag, final JSONPropertyImpl object) {
+    super(contextURL, metadataETag, object);
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/serializer/JsonEntryContainer.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/serializer/JsonEntryContainer.java b/fit/src/main/java/org/apache/olingo/fit/serializer/JsonEntryContainer.java
deleted file mode 100644
index 5ff4f6e..0000000
--- a/fit/src/main/java/org/apache/olingo/fit/serializer/JsonEntryContainer.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * 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
- *
- *   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 org.apache.olingo.fit.serializer;
-
-import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
-import com.fasterxml.jackson.databind.annotation.JsonSerialize;
-import java.net.URI;
-import org.apache.olingo.commons.api.data.Container;
-import org.apache.olingo.commons.core.data.JSONEntryDeserializer;
-import org.apache.olingo.commons.core.data.JSONEntrySerializer;
-
-@JsonDeserialize(using = JSONEntryDeserializer.class)
-@JsonSerialize(using = JSONEntrySerializer.class)
-public class JsonEntryContainer<T> extends Container<T> {
-
-  public JsonEntryContainer(final URI contextURL, final String metadataETag, final T object) {
-    super(contextURL, metadataETag, object);
-  }
-}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/serializer/JsonFeedContainer.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/serializer/JsonFeedContainer.java b/fit/src/main/java/org/apache/olingo/fit/serializer/JsonFeedContainer.java
deleted file mode 100644
index 6af08dd..0000000
--- a/fit/src/main/java/org/apache/olingo/fit/serializer/JsonFeedContainer.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * 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
- *
- *   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 org.apache.olingo.fit.serializer;
-
-import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
-import com.fasterxml.jackson.databind.annotation.JsonSerialize;
-import java.net.URI;
-import org.apache.olingo.commons.api.data.Container;
-import org.apache.olingo.commons.core.data.JSONFeedDeserializer;
-import org.apache.olingo.commons.core.data.JSONFeedSerializer;
-
-@JsonDeserialize(using = JSONFeedDeserializer.class)
-@JsonSerialize(using = JSONFeedSerializer.class)
-public class JsonFeedContainer<T> extends Container<T> {
-
-  public JsonFeedContainer(final URI contextURL, final String metadataETag, final T object) {
-    super(contextURL, metadataETag, object);
-  }
-}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/serializer/JsonPropertyContainer.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/serializer/JsonPropertyContainer.java b/fit/src/main/java/org/apache/olingo/fit/serializer/JsonPropertyContainer.java
deleted file mode 100644
index a79c397..0000000
--- a/fit/src/main/java/org/apache/olingo/fit/serializer/JsonPropertyContainer.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * 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
- *
- *   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 org.apache.olingo.fit.serializer;
-
-import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
-import com.fasterxml.jackson.databind.annotation.JsonSerialize;
-import java.net.URI;
-import org.apache.olingo.commons.api.data.Container;
-import org.apache.olingo.commons.core.data.JSONPropertyDeserializer;
-import org.apache.olingo.commons.core.data.JSONPropertySerializer;
-
-@JsonDeserialize(using = JSONPropertyDeserializer.class)
-@JsonSerialize(using = JSONPropertySerializer.class)
-public class JsonPropertyContainer<T> extends Container<T> {
-
-  public JsonPropertyContainer(final URI contextURL, final String metadataETag, final T object) {
-    super(contextURL, metadataETag, object);
-  }
-}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/utils/AbstractJSONUtilities.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/utils/AbstractJSONUtilities.java b/fit/src/main/java/org/apache/olingo/fit/utils/AbstractJSONUtilities.java
index 3a22c64..369d657 100644
--- a/fit/src/main/java/org/apache/olingo/fit/utils/AbstractJSONUtilities.java
+++ b/fit/src/main/java/org/apache/olingo/fit/utils/AbstractJSONUtilities.java
@@ -201,7 +201,7 @@ public abstract class AbstractJSONUtilities extends AbstractUtilities {
 
     final ObjectNode propertyNode = new ObjectNode(JsonNodeFactory.instance);
 
-    if (StringUtils.isNotBlank(edmType)) {
+    if (StringUtils.isNotBlank(edmType) && version.compareTo(ODataServiceVersion.V40) < 0) {
       propertyNode.put(Constants.get(
               version, ConstantKey.JSON_ODATAMETADATA_NAME),
               Constants.get(version, ConstantKey.ODATA_METADATA_PREFIX) + edmType);

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/utils/AbstractUtilities.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/utils/AbstractUtilities.java b/fit/src/main/java/org/apache/olingo/fit/utils/AbstractUtilities.java
index a84ef60..6a1dc10 100644
--- a/fit/src/main/java/org/apache/olingo/fit/utils/AbstractUtilities.java
+++ b/fit/src/main/java/org/apache/olingo/fit/utils/AbstractUtilities.java
@@ -25,7 +25,6 @@ import java.io.ByteArrayOutputStream;
 import java.io.File;
 import java.io.IOException;
 import java.io.InputStream;
-import java.io.OutputStreamWriter;
 import java.io.StringWriter;
 import java.util.AbstractMap.SimpleEntry;
 import java.util.ArrayList;
@@ -46,13 +45,21 @@ import org.apache.commons.vfs2.FileObject;
 import org.apache.olingo.commons.api.data.Container;
 import org.apache.olingo.commons.api.data.Entry;
 import org.apache.olingo.commons.api.data.Link;
+import org.apache.olingo.commons.api.data.Property;
 import org.apache.olingo.commons.api.edm.constants.ODataServiceVersion;
 import org.apache.olingo.commons.core.data.AtomEntryImpl;
+import org.apache.olingo.commons.core.data.AtomFeedImpl;
+import org.apache.olingo.commons.core.data.AtomPropertyImpl;
+import org.apache.olingo.commons.core.data.AtomSerializer;
 import org.apache.olingo.commons.core.data.JSONEntryImpl;
+import org.apache.olingo.commons.core.data.JSONPropertyImpl;
 import org.apache.olingo.fit.UnsupportedMediaTypeException;
 import org.apache.olingo.fit.metadata.Metadata;
 import org.apache.olingo.fit.metadata.NavigationProperty;
-import org.apache.olingo.fit.serializer.JsonEntryContainer;
+import org.apache.olingo.fit.serializer.FITAtomDeserializer;
+import org.apache.olingo.fit.serializer.JSONEntryContainer;
+import org.apache.olingo.fit.serializer.JSONFeedContainer;
+import org.apache.olingo.fit.serializer.JSONPropertyContainer;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -63,10 +70,6 @@ public abstract class AbstractUtilities {
    */
   protected static final Logger LOG = LoggerFactory.getLogger(AbstractUtilities.class);
 
-  protected final ODataServiceVersion version;
-
-  protected final FSManager fsManager;
-
   protected static final Pattern ENTITY_URI_PATTERN = Pattern.compile(".*\\/.*\\(.*\\)");
 
   /**
@@ -84,9 +87,25 @@ public abstract class AbstractUtilities {
    */
   public static final String BOUNDARY = "boundary";
 
+  protected final ODataServiceVersion version;
+
+  protected final FSManager fsManager;
+
+  protected final DataBinder dataBinder;
+
+  protected final FITAtomDeserializer atomDeserializer;
+
+  protected final AtomSerializer atomSerializer;
+
+  protected final ObjectMapper mapper;
+
   public AbstractUtilities(final ODataServiceVersion version) throws Exception {
     this.version = version;
     this.fsManager = FSManager.instance(version);
+    this.dataBinder = new DataBinder(version);
+    this.atomDeserializer = Commons.getAtomDeserializer(version);
+    this.atomSerializer = Commons.getAtomSerializer(version);
+    this.mapper = Commons.getJSONMapper(version);
   }
 
   public boolean isMediaContent(final String entityName) {
@@ -181,7 +200,7 @@ public abstract class AbstractUtilities {
 
   private InputStream toInputStream(final AtomEntryImpl entry) throws XMLStreamException {
     final StringWriter writer = new StringWriter();
-    Commons.getAtomSerializer(version).write(writer, entry);
+    atomSerializer.write(writer, entry);
 
     return IOUtils.toInputStream(writer.toString(), Constants.ENCODING);
   }
@@ -273,7 +292,8 @@ public abstract class AbstractUtilities {
     final List<String> hrefs = new ArrayList<String>();
 
     for (final Link link : entry.getNavigationLinks()) {
-      final NavigationProperty navProp = navigationProperties == null? null: navigationProperties.get(link.getTitle());
+      final NavigationProperty navProp = navigationProperties == null
+              ? null : navigationProperties.get(link.getTitle());
       if (navProp != null) {
         final String inlineEntitySetName = navProp.getTarget();
         if (link.getInlineEntry() != null) {
@@ -555,20 +575,36 @@ public abstract class AbstractUtilities {
     return builder.build();
   }
 
+  public InputStream writeFeed(final Accept accept, final Container<AtomFeedImpl> container)
+          throws XMLStreamException, IOException {
+
+    final StringWriter writer = new StringWriter();
+    if (accept == Accept.ATOM) {
+      atomSerializer.write(writer, container);
+      writer.flush();
+      writer.close();
+    } else {
+      mapper.writeValue(
+              writer, new JSONFeedContainer(container.getContextURL(),
+                      container.getMetadataETag(), dataBinder.toJSONFeed(container.getObject())));
+    }
+
+    return IOUtils.toInputStream(writer.toString(), Constants.ENCODING);
+  }
+
   public AtomEntryImpl readEntry(final Accept contentTypeValue, final InputStream entity)
           throws XMLStreamException, IOException {
 
     final AtomEntryImpl entry;
 
-    if (Accept.ATOM == contentTypeValue) {
-      final Container<AtomEntryImpl> container = Commons.getAtomDeserializer(version).
-              read(entity, AtomEntryImpl.class);
+    if (Accept.ATOM == contentTypeValue || Accept.XML == contentTypeValue) {
+      final Container<AtomEntryImpl> container = atomDeserializer.read(entity, AtomEntryImpl.class);
       entry = container.getObject();
     } else {
-      final Container<JSONEntryImpl> jcontainer =
-              Commons.getJsonMapper(version).readValue(entity, new TypeReference<JSONEntryImpl>() {
+      final Container<JSONEntryImpl> container =
+              mapper.readValue(entity, new TypeReference<JSONEntryImpl>() {
               });
-      entry = new DataBinder(version).getAtomEntry(jcontainer.getObject());
+      entry = dataBinder.toAtomEntry(container.getObject());
     }
 
     return entry;
@@ -577,21 +613,46 @@ public abstract class AbstractUtilities {
   public InputStream writeEntry(final Accept accept, final Container<AtomEntryImpl> container)
           throws XMLStreamException, IOException {
 
-    final ByteArrayOutputStream content = new ByteArrayOutputStream();
-    final OutputStreamWriter writer = new OutputStreamWriter(content, Constants.ENCODING);
-
+    final StringWriter writer = new StringWriter();
     if (accept == Accept.ATOM) {
-      Commons.getAtomSerializer(version).write(writer, container);
-      writer.flush();
-      writer.close();
+      atomSerializer.write(writer, container);
+    } else {
+      mapper.writeValue(
+              writer, new JSONEntryContainer(container.getContextURL(), container.getMetadataETag(),
+                      dataBinder.toJSONEntry(container.getObject())));
+    }
+
+    return IOUtils.toInputStream(writer.toString(), Constants.ENCODING);
+  }
+
+  public InputStream writeProperty(final Accept accept, final Property property)
+          throws XMLStreamException, IOException {
+
+    final StringWriter writer = new StringWriter();
+    if (accept == Accept.XML || accept == Accept.ATOM) {
+      atomSerializer.write(writer, property instanceof AtomPropertyImpl
+              ? property : dataBinder.toAtomProperty((JSONPropertyImpl) property, property.getType()));
+    } else {
+      mapper.writeValue(writer, property instanceof JSONPropertyImpl
+              ? property : dataBinder.toJSONProperty((AtomPropertyImpl) property));
+    }
+
+    return IOUtils.toInputStream(writer.toString(), Constants.ENCODING);
+  }
+
+  public InputStream writeProperty(final Accept accept, final Container<AtomPropertyImpl> container)
+          throws XMLStreamException, IOException {
+
+    final StringWriter writer = new StringWriter();
+    if (accept == Accept.XML) {
+      atomSerializer.write(writer, container);
     } else {
-      final ObjectMapper mapper = Commons.getJsonMapper(version);
       mapper.writeValue(
-              writer, new JsonEntryContainer<JSONEntryImpl>(container.getContextURL(), container.getMetadataETag(),
-                      new DataBinder(version).getJsonEntry((AtomEntryImpl) container.getObject())));
+              writer, new JSONPropertyContainer(container.getContextURL(), container.getMetadataETag(),
+                      dataBinder.toJSONProperty(container.getObject())));
     }
 
-    return new ByteArrayInputStream(content.toByteArray());
+    return IOUtils.toInputStream(writer.toString(), Constants.ENCODING);
   }
 
   private String getDefaultEntryKey(final String entitySetName, final AtomEntryImpl entry, final String propertyName)

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/utils/Commons.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/utils/Commons.java b/fit/src/main/java/org/apache/olingo/fit/utils/Commons.java
index c3c0cbb..5d35bdc 100644
--- a/fit/src/main/java/org/apache/olingo/fit/utils/Commons.java
+++ b/fit/src/main/java/org/apache/olingo/fit/utils/Commons.java
@@ -111,7 +111,7 @@ public abstract class Commons {
     return ATOM_SERIALIZER.get(version);
   }
 
-  public static ObjectMapper getJsonMapper(final ODataServiceVersion version) {
+  public static ObjectMapper getJSONMapper(final ODataServiceVersion version) {
     if (!JSON_MAPPER.containsKey(version)) {
       final ObjectMapper mapper = new ObjectMapper().setSerializationInclusion(JsonInclude.Include.NON_NULL);
 

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/utils/DataBinder.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/utils/DataBinder.java b/fit/src/main/java/org/apache/olingo/fit/utils/DataBinder.java
index 986c997..c9b3646 100644
--- a/fit/src/main/java/org/apache/olingo/fit/utils/DataBinder.java
+++ b/fit/src/main/java/org/apache/olingo/fit/utils/DataBinder.java
@@ -52,7 +52,7 @@ public class DataBinder {
     this.version = version;
   }
 
-  public JSONFeedImpl getJsonFeed(final AtomFeedImpl atomfeed) {
+  public JSONFeedImpl toJSONFeed(final AtomFeedImpl atomfeed) {
     final JSONFeedImpl jsonfeed = new JSONFeedImpl();
 
     BeanUtils.copyProperties(atomfeed, jsonfeed, "baseURI", "metadataContextURL");
@@ -62,13 +62,13 @@ public class DataBinder {
 
     final Collection<Entry> entries = jsonfeed.getEntries();
     for (Entry entry : atomfeed.getEntries()) {
-      entries.add(getJsonEntry((AtomEntryImpl) entry));
+      entries.add(toJSONEntry((AtomEntryImpl) entry));
     }
 
     return jsonfeed;
   }
 
-  public AtomFeedImpl getAtomFeed(final JSONFeedImpl jsonfeed) {
+  public AtomFeedImpl toAtomFeed(final JSONFeedImpl jsonfeed) {
     final AtomFeedImpl atomfeed = new AtomFeedImpl();
 
     BeanUtils.copyProperties(jsonfeed, atomfeed, "baseURI", "metadataContextURL");
@@ -78,17 +78,18 @@ public class DataBinder {
 
     final Collection<Entry> entries = atomfeed.getEntries();
     for (Entry entry : jsonfeed.getEntries()) {
-      entries.add(getAtomEntry((JSONEntryImpl) entry));
+      entries.add(toAtomEntry((JSONEntryImpl) entry));
     }
 
     return atomfeed;
   }
 
-  public JSONEntryImpl getJsonEntry(final AtomEntryImpl atomentry) {
+  public JSONEntryImpl toJSONEntry(final AtomEntryImpl atomentry) {
     final JSONEntryImpl jsonentry = new JSONEntryImpl();
 
     BeanUtils.copyProperties(atomentry, jsonentry, "baseURI", "properties", "links");
     jsonentry.setBaseURI(atomentry.getBaseURI() == null ? null : atomentry.getBaseURI().toASCIIString());
+    jsonentry.getOperations().addAll(atomentry.getOperations());
 
     for (Link link : atomentry.getNavigationLinks()) {
       final Link jlink = new LinkImpl();
@@ -100,12 +101,12 @@ public class DataBinder {
       if (link.getInlineEntry() instanceof AtomEntryImpl) {
         final Entry inlineEntry = link.getInlineEntry();
         if (inlineEntry instanceof AtomEntryImpl) {
-          jlink.setInlineEntry(getJsonEntry((AtomEntryImpl) link.getInlineEntry()));
+          jlink.setInlineEntry(toJSONEntry((AtomEntryImpl) link.getInlineEntry()));
         }
       } else if (link.getInlineFeed() instanceof AtomFeedImpl) {
         final Feed inlineFeed = link.getInlineFeed();
         if (inlineFeed instanceof AtomFeedImpl) {
-          jlink.setInlineFeed(getJsonFeed((AtomFeedImpl) link.getInlineFeed()));
+          jlink.setInlineFeed(toJSONFeed((AtomFeedImpl) link.getInlineFeed()));
         }
       }
 
@@ -114,13 +115,13 @@ public class DataBinder {
 
     final Collection<Property> properties = jsonentry.getProperties();
     for (Property property : atomentry.getProperties()) {
-      properties.add(getJsonProperty((AtomPropertyImpl) property));
+      properties.add(toJSONProperty((AtomPropertyImpl) property));
     }
 
     return jsonentry;
   }
 
-  public AtomEntryImpl getAtomEntry(final JSONEntryImpl jsonentry) {
+  public AtomEntryImpl toAtomEntry(final JSONEntryImpl jsonentry) {
     final AtomEntryImpl atomentry = new AtomEntryImpl();
 
     final Metadata metadata = Commons.getMetadata(version);
@@ -143,12 +144,12 @@ public class DataBinder {
       if (link.getInlineEntry() instanceof JSONEntryImpl) {
         final Entry inlineEntry = link.getInlineEntry();
         if (inlineEntry instanceof JSONEntryImpl) {
-          alink.setInlineEntry(getAtomEntry((JSONEntryImpl) link.getInlineEntry()));
+          alink.setInlineEntry(toAtomEntry((JSONEntryImpl) link.getInlineEntry()));
         }
       } else if (link.getInlineFeed() instanceof JSONFeedImpl) {
         final Feed inlineFeed = link.getInlineFeed();
         if (inlineFeed instanceof JSONFeedImpl) {
-          alink.setInlineFeed(getAtomFeed((JSONFeedImpl) link.getInlineFeed()));
+          alink.setInlineFeed(toAtomFeed((JSONFeedImpl) link.getInlineFeed()));
         }
       }
 
@@ -187,7 +188,7 @@ public class DataBinder {
             final Entry inlineEntry = new AtomEntryImpl();
             inlineEntry.setType(navProperties.get(property.getName()).getType());
             for (Property prop : entry.asComplex().get()) {
-              inlineEntry.getProperties().add(getAtomProperty((JSONPropertyImpl) prop, inlineEntry.getType()));
+              inlineEntry.getProperties().add(toAtomProperty((JSONPropertyImpl) prop, inlineEntry.getType()));
             }
             inline.getEntries().add(inlineEntry);
           }
@@ -197,14 +198,14 @@ public class DataBinder {
         }
         atomentry.getNavigationLinks().add(alink);
       } else {
-        properties.add(getAtomProperty((JSONPropertyImpl) property, atomentry.getType()));
+        properties.add(toAtomProperty((JSONPropertyImpl) property, atomentry.getType()));
       }
     }
 
     return atomentry;
   }
 
-  public JSONPropertyImpl getJsonProperty(final AtomPropertyImpl atomproperty) {
+  public JSONPropertyImpl toJSONProperty(final AtomPropertyImpl atomproperty) {
     final JSONPropertyImpl jsonproperty = new JSONPropertyImpl();
     BeanUtils.copyProperties(atomproperty, jsonproperty, "value");
 
@@ -213,7 +214,7 @@ public class DataBinder {
       jsonproperty.setValue(complex);
 
       for (Property field : atomproperty.getValue().asComplex().get()) {
-        complex.get().add(getJsonProperty((AtomPropertyImpl) field));
+        complex.get().add(toJSONProperty((AtomPropertyImpl) field));
       }
     } else if (atomproperty.getValue().isCollection()) {
       final CollectionValueImpl collection = new CollectionValueImpl();
@@ -225,7 +226,7 @@ public class DataBinder {
           collection.get().add(complex);
 
           for (Property field : element.asComplex().get()) {
-            complex.get().add(getJsonProperty((AtomPropertyImpl) field));
+            complex.get().add(toJSONProperty((AtomPropertyImpl) field));
           }
         } else {
           collection.get().add(element);
@@ -238,14 +239,14 @@ public class DataBinder {
     return jsonproperty;
   }
 
-  public AtomPropertyImpl getAtomProperty(final JSONPropertyImpl jsonproperty, final String entryType) {
+  public AtomPropertyImpl toAtomProperty(final JSONPropertyImpl jsonproperty, final String entryType) {
     final AtomPropertyImpl atomproperty = new AtomPropertyImpl();
     atomproperty.setName(jsonproperty.getName());
 
     if (StringUtils.isNotBlank(jsonproperty.getType())) {
       atomproperty.setType(jsonproperty.getType());
     } else {
-      final EntityType entityType = Commons.getMetadata(version).getEntityType(entryType);
+      final EntityType entityType = entryType == null ? null : Commons.getMetadata(version).getEntityType(entryType);
       if (entityType != null) {
         atomproperty.setType(entityType.getProperty(jsonproperty.getName()).getType());
       }
@@ -256,7 +257,7 @@ public class DataBinder {
       atomproperty.setValue(complex);
 
       for (Property field : jsonproperty.getValue().asComplex().get()) {
-        complex.get().add(getAtomProperty((JSONPropertyImpl) field, atomproperty.getType()));
+        complex.get().add(toAtomProperty((JSONPropertyImpl) field, atomproperty.getType()));
       }
     } else if (jsonproperty.getValue().isCollection()) {
       final CollectionValueImpl collection = new CollectionValueImpl();
@@ -268,8 +269,10 @@ public class DataBinder {
           collection.get().add(complex);
 
           for (Property field : element.asComplex().get()) {
-            complex.get().add(getAtomProperty((JSONPropertyImpl) field,
-                    atomproperty.getType().replaceAll("^Collection\\(", "").replaceAll("\\)$", "")));
+            complex.get().add(toAtomProperty((JSONPropertyImpl) field,
+                    atomproperty.getType() == null
+                    ? null
+                    : atomproperty.getType().replaceAll("^Collection\\(", "").replaceAll("\\)$", "")));
           }
         } else {
           collection.get().add(element);

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/java/org/apache/olingo/fit/utils/FSManager.java
----------------------------------------------------------------------
diff --git a/fit/src/main/java/org/apache/olingo/fit/utils/FSManager.java b/fit/src/main/java/org/apache/olingo/fit/utils/FSManager.java
index b7d21f4..014da7d 100644
--- a/fit/src/main/java/org/apache/olingo/fit/utils/FSManager.java
+++ b/fit/src/main/java/org/apache/olingo/fit/utils/FSManager.java
@@ -40,8 +40,7 @@ import org.apache.olingo.commons.api.data.Container;
 import org.apache.olingo.commons.api.edm.constants.ODataServiceVersion;
 import org.apache.olingo.commons.core.data.AtomEntryImpl;
 import org.apache.olingo.commons.core.data.AtomSerializer;
-import org.apache.olingo.commons.core.data.JSONEntryImpl;
-import org.apache.olingo.fit.serializer.JsonEntryContainer;
+import org.apache.olingo.fit.serializer.JSONEntryContainer;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -113,12 +112,12 @@ public class FSManager {
       putInMemory(new ByteArrayInputStream(content.toByteArray()), getAbsolutePath(relativePath, Accept.ATOM));
       content.reset();
 
-      final ObjectMapper mapper = Commons.getJsonMapper(version);
+      final ObjectMapper mapper = Commons.getJSONMapper(version);
       mapper.writeValue(
-              writer, new JsonEntryContainer<JSONEntryImpl>(
+              writer, new JSONEntryContainer(
                       container.getContextURL(),
                       container.getMetadataETag(),
-                      new DataBinder(version).getJsonEntry(container.getObject())));
+                      new DataBinder(version).toJSONEntry(container.getObject())));
 
       putInMemory(new ByteArrayInputStream(content.toByteArray()), getAbsolutePath(relativePath, Accept.JSON_FULLMETA));
     } catch (Exception e) {

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Accounts/101/entity.xml
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Accounts/101/entity.xml b/fit/src/main/resources/V40/Accounts/101/entity.xml
index 6ee3a87..82c8976 100644
--- a/fit/src/main/resources/V40/Accounts/101/entity.xml
+++ b/fit/src/main/resources/V40/Accounts/101/entity.xml
@@ -32,6 +32,15 @@
   <author>
     <name/>
   </author>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.RefreshDefaultPI" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.RefreshDefaultPI" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Accounts(101)/Microsoft.Test.OData.Services.ODataWCFService.RefreshDefaultPI"/>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.GetDefaultPI" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.GetDefaultPI" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Accounts(101)/Microsoft.Test.OData.Services.ODataWCFService.GetDefaultPI"/>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.GetAccountInfo" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.GetAccountInfo" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Accounts(101)/Microsoft.Test.OData.Services.ODataWCFService.GetAccountInfo"/>
   <content type="application/xml">
     <m:properties>
       <d:AccountID m:type="Int32">101</d:AccountID>

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Accounts/101/links/MyGiftCard.full.json
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Accounts/101/links/MyGiftCard.full.json b/fit/src/main/resources/V40/Accounts/101/links/MyGiftCard.full.json
new file mode 100644
index 0000000..4f8c0b9
--- /dev/null
+++ b/fit/src/main/resources/V40/Accounts/101/links/MyGiftCard.full.json
@@ -0,0 +1,15 @@
+{
+  "@odata.context": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Accounts(101)/MyGiftCard/$entity",
+  "@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.GiftCard",
+  "@odata.id": "Accounts(101)/MyGiftCard",
+  "@odata.editLink": "Accounts(101)/MyGiftCard",
+  "GiftCardID": 301,
+  "GiftCardNO": "AAA123A",
+  "Amount": 19.9,
+  "ExperationDate@odata.type": "#DateTimeOffset",
+  "ExperationDate": "2013-12-30T00:00:00Z",
+  "#Microsoft.Test.OData.Services.ODataWCFService.GetActualAmount": {
+    "title": "Microsoft.Test.OData.Services.ODataWCFService.GetActualAmount",
+    "target": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Accounts(101)/MyGiftCard/Microsoft.Test.OData.Services.ODataWCFService.GetActualAmount"
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Accounts/101/links/MyGiftCard.xml
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Accounts/101/links/MyGiftCard.xml b/fit/src/main/resources/V40/Accounts/101/links/MyGiftCard.xml
new file mode 100644
index 0000000..b332823
--- /dev/null
+++ b/fit/src/main/resources/V40/Accounts/101/links/MyGiftCard.xml
@@ -0,0 +1,41 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+
+    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
+
+      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.
+
+-->
+<entry xml:base="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/" xmlns="http://www.w3.org/2005/Atom" xmlns:d="http://docs.oasis-open.org/odata/ns/data" xmlns:m="http://docs.oasis-open.org/odata/ns/metadata" xmlns:georss="http://www.georss.org/georss" xmlns:gml="http://www.opengis.net/gml" m:context="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Accounts(101)/MyGiftCard/$entity">
+  <category term="#Microsoft.Test.OData.Services.ODataWCFService.GiftCard" scheme="http://docs.oasis-open.org/odata/ns/scheme" />
+  <id />
+  <title />
+  <updated>2014-04-23T13:48:48Z</updated>
+  <author>
+    <name />
+  </author>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.GetActualAmount" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.GetActualAmount" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Accounts(101)/MyGiftCard/Microsoft.Test.OData.Services.ODataWCFService.GetActualAmount"/>
+  <content type="application/xml">
+    <m:properties>
+      <d:GiftCardID m:type="Int32">301</d:GiftCardID>
+      <d:GiftCardNO>AAA123A</d:GiftCardNO>
+      <d:Amount m:type="Double">19.9</d:Amount>
+      <d:ExperationDate m:type="DateTimeOffset">2013-12-30T00:00:00Z</d:ExperationDate>
+    </m:properties>
+  </content>
+</entry>

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Company/entity.xml
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Company/entity.xml b/fit/src/main/resources/V40/Company/entity.xml
index 6beed3b..49a6167 100644
--- a/fit/src/main/resources/V40/Company/entity.xml
+++ b/fit/src/main/resources/V40/Company/entity.xml
@@ -32,6 +32,12 @@
   <author>
     <name />
   </author>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.IncreaseRevenue" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.IncreaseRevenue" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Company/Microsoft.Test.OData.Services.ODataWCFService.IncreaseRevenue"/>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.GetEmployeesCount" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.GetEmployeesCount" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Company/Microsoft.Test.OData.Services.ODataWCFService.GetEmployeesCount"/>
   <content type="application/xml">
     <m:properties>
       <d:CompanyID m:type="Int32">0</d:CompanyID>

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Customers/2/entity.full.json
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Customers/2/entity.full.json b/fit/src/main/resources/V40/Customers/2/entity.full.json
new file mode 100644
index 0000000..2756d88
--- /dev/null
+++ b/fit/src/main/resources/V40/Customers/2/entity.full.json
@@ -0,0 +1,50 @@
+{
+  "@odata.context": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Customers/$entity",
+  "@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.Customer",
+  "@odata.id": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)",
+  "@odata.editLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)",
+  "PersonID": 2,
+  "FirstName": "Jill",
+  "LastName": "Jones",
+  "MiddleName": null,
+  "HomeAddress": {
+    "@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.Address",
+    "Street": "Piazza La Bomba E Scappa",
+    "City": "Tollo",
+    "PostalCode": "66010"
+  },
+  "Home@odata.type": "#GeographyPoint",
+  "Home": {
+    "type": "Point",
+    "coordinates": [161.8, 15.0],
+    "crs": {
+      "type": "name",
+      "properties": {
+        "name": "EPSG:4326"
+      }
+    }
+  },
+  "Numbers@odata.type": "#Collection(String)",
+  "Numbers": [],
+  "Emails@odata.type": "#Collection(String)",
+  "Emails": [],
+  "City": "Sydney",
+  "Birthday@odata.type": "#DateTimeOffset",
+  "Birthday": "1983-01-15T00:00:00Z",
+  "TimeBetweenLastTwoOrders@odata.type": "#Duration",
+  "TimeBetweenLastTwoOrders": "PT0.0000002S",
+  "Parent@odata.associationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Parent/$ref",
+  "Parent@odata.navigationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Parent",
+  "Orders@odata.associationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Orders/$ref",
+  "Orders@odata.navigationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Orders",
+  "Company@odata.associationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Company/$ref",
+  "Company@odata.navigationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Company",
+  "#Microsoft.Test.OData.Services.ODataWCFService.ResetAddress": {
+    "title": "Microsoft.Test.OData.Services.ODataWCFService.ResetAddress",
+    "target": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Microsoft.Test.OData.Services.ODataWCFService.ResetAddress"
+  },
+  "#Microsoft.Test.OData.Services.ODataWCFService.GetHomeAddress": {
+    "title": "Microsoft.Test.OData.Services.ODataWCFService.GetHomeAddress",
+    "target": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Microsoft.Test.OData.Services.ODataWCFService.GetHomeAddress"
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Customers/2/entity.xml
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Customers/2/entity.xml b/fit/src/main/resources/V40/Customers/2/entity.xml
new file mode 100644
index 0000000..686fcac
--- /dev/null
+++ b/fit/src/main/resources/V40/Customers/2/entity.xml
@@ -0,0 +1,63 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+
+    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
+
+      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.
+
+-->
+<entry xml:base="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/" xmlns="http://www.w3.org/2005/Atom" xmlns:d="http://docs.oasis-open.org/odata/ns/data" xmlns:m="http://docs.oasis-open.org/odata/ns/metadata" xmlns:georss="http://www.georss.org/georss" xmlns:gml="http://www.opengis.net/gml" m:context="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Customers/$entity">
+  <id>http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)</id>
+  <category term="#Microsoft.Test.OData.Services.ODataWCFService.Customer" scheme="http://docs.oasis-open.org/odata/ns/scheme" />
+  <link rel="edit" href="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)" />
+  <link rel="http://docs.oasis-open.org/odata/ns/related/Parent" type="application/atom+xml;type=entry" title="Parent" href="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Parent" />
+  <link rel="http://docs.oasis-open.org/odata/ns/related/Orders" type="application/atom+xml;type=feed" title="Orders" href="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Orders" />
+  <link rel="http://docs.oasis-open.org/odata/ns/related/Company" type="application/atom+xml;type=entry" title="Company" href="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Company" />
+  <title />
+  <updated>2014-04-23T15:27:13Z</updated>
+  <author>
+    <name />
+  </author>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.ResetAddress" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.ResetAddress" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Microsoft.Test.OData.Services.ODataWCFService.ResetAddress"/>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.GetHomeAddress" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.GetHomeAddress" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Customers(PersonID=2)/Microsoft.Test.OData.Services.ODataWCFService.GetHomeAddress"/>
+  <content type="application/xml">
+    <m:properties>
+      <d:PersonID m:type="Int32">2</d:PersonID>
+      <d:FirstName>Jill</d:FirstName>
+      <d:LastName>Jones</d:LastName>
+      <d:MiddleName m:null="true" />
+      <d:HomeAddress m:type="#Microsoft.Test.OData.Services.ODataWCFService.Address">
+        <d:Street>Piazza La Bomba E Scappa</d:Street>
+        <d:City>Tollo</d:City>
+        <d:PostalCode>66010</d:PostalCode>
+      </d:HomeAddress>
+      <d:Home m:type="GeographyPoint">
+        <gml:Point gml:srsName="http://www.opengis.net/def/crs/EPSG/0/4326">
+          <gml:pos>15 161.8</gml:pos>
+        </gml:Point>
+      </d:Home>
+      <d:Numbers m:type="#Collection(String)" />
+      <d:Emails m:type="#Collection(String)" />
+      <d:City>Sydney</d:City>
+      <d:Birthday m:type="DateTimeOffset">1983-01-15T00:00:00Z</d:Birthday>
+      <d:TimeBetweenLastTwoOrders m:type="Duration">PT0.0000002S</d:TimeBetweenLastTwoOrders>
+    </m:properties>
+  </content>
+</entry>

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/ProductDetails/6 1/entity.xml
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/ProductDetails/6 1/entity.xml b/fit/src/main/resources/V40/ProductDetails/6 1/entity.xml
index ae66ac8..53d00b7 100644
--- a/fit/src/main/resources/V40/ProductDetails/6 1/entity.xml	
+++ b/fit/src/main/resources/V40/ProductDetails/6 1/entity.xml	
@@ -30,6 +30,9 @@
   <author>
     <name />
   </author>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.GetRelatedProduct" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.GetRelatedProduct" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/ProductDetails(ProductID=6,ProductDetailID=1)/Microsoft.Test.OData.Services.ODataWCFService.GetRelatedProduct"/>
   <content type="application/xml">
     <m:properties>
       <d:ProductID m:type="Int32">6</d:ProductID>

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Products/5/entity.full.json
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Products/5/entity.full.json b/fit/src/main/resources/V40/Products/5/entity.full.json
new file mode 100644
index 0000000..174daaf
--- /dev/null
+++ b/fit/src/main/resources/V40/Products/5/entity.full.json
@@ -0,0 +1,29 @@
+{
+  "@odata.context": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Products/$entity",
+  "@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.Product",
+  "@odata.id": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)",
+  "@odata.editLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)",
+  "ProductID": 5,
+  "Name": "Cheetos",
+  "QuantityPerUnit": "100g Bag",
+  "UnitPrice@odata.type": "#Single",
+  "UnitPrice": 3.24,
+  "QuantityInStock": 100,
+  "Discontinued": true,
+  "UserAccess@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.AccessLevel",
+  "UserAccess": "None",
+  "SkinColor@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.Color",
+  "SkinColor": "Red",
+  "CoverColors@odata.type": "#Collection(Microsoft.Test.OData.Services.ODataWCFService.Color)",
+  "CoverColors": ["Green", "Blue", "Blue"],
+  "Details@odata.associationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)/Details/$ref",
+  "Details@odata.navigationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)/Details",
+  "#Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight": {
+    "title": "Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight",
+    "target": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)/Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight"
+  },
+  "#Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails": {
+    "title": "Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails",
+    "target": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)/Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails"
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Products/5/entity.xml
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Products/5/entity.xml b/fit/src/main/resources/V40/Products/5/entity.xml
new file mode 100644
index 0000000..3f9f1bc
--- /dev/null
+++ b/fit/src/main/resources/V40/Products/5/entity.xml
@@ -0,0 +1,55 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+
+    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
+
+      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.
+
+-->
+<entry xml:base="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/" xmlns="http://www.w3.org/2005/Atom" xmlns:d="http://docs.oasis-open.org/odata/ns/data" xmlns:m="http://docs.oasis-open.org/odata/ns/metadata" xmlns:georss="http://www.georss.org/georss" xmlns:gml="http://www.opengis.net/gml" m:context="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Products/$entity">
+  <id>http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)</id>
+  <category term="#Microsoft.Test.OData.Services.ODataWCFService.Product" scheme="http://docs.oasis-open.org/odata/ns/scheme" />
+  <link rel="edit" href="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)" />
+  <link rel="http://docs.oasis-open.org/odata/ns/related/Details" type="application/atom+xml;type=feed" title="Details" href="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)/Details" />
+  <title />
+  <updated>2014-04-23T11:54:53Z</updated>
+  <author>
+    <name />
+  </author>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)/Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight"/>
+  <m:action metadata="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails" 
+            title="Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails" 
+            target="http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(5)/Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails"/>
+  <content type="application/xml">
+    <m:properties>
+      <d:ProductID m:type="Int32">5</d:ProductID>
+      <d:Name>Cheetos</d:Name>
+      <d:QuantityPerUnit>100g Bag</d:QuantityPerUnit>
+      <d:UnitPrice m:type="Single">3.24</d:UnitPrice>
+      <d:QuantityInStock m:type="Int32">100</d:QuantityInStock>
+      <d:Discontinued m:type="Boolean">true</d:Discontinued>
+      <d:UserAccess m:type="#Microsoft.Test.OData.Services.ODataWCFService.AccessLevel">None</d:UserAccess>
+      <d:SkinColor m:type="#Microsoft.Test.OData.Services.ODataWCFService.Color">Red</d:SkinColor>
+      <d:CoverColors m:type="#Collection(Microsoft.Test.OData.Services.ODataWCFService.Color)">
+        <m:element>Green</m:element>
+        <m:element>Blue</m:element>
+        <m:element>Blue</m:element>
+      </d:CoverColors>
+    </m:properties>
+  </content>
+</entry>

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/713ed0ef/fit/src/main/resources/V40/Products/6/entity.full.json
----------------------------------------------------------------------
diff --git a/fit/src/main/resources/V40/Products/6/entity.full.json b/fit/src/main/resources/V40/Products/6/entity.full.json
new file mode 100644
index 0000000..f3b2c54
--- /dev/null
+++ b/fit/src/main/resources/V40/Products/6/entity.full.json
@@ -0,0 +1,29 @@
+{
+  "@odata.context": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/$metadata#Products/$entity",
+  "@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.Product",
+  "@odata.id": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(6)",
+  "@odata.editLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(6)",
+  "ProductID": 6,
+  "Name": "Mushrooms",
+  "QuantityPerUnit": "Pound",
+  "UnitPrice@odata.type": "#Single",
+  "UnitPrice": 3.24,
+  "QuantityInStock": 100,
+  "Discontinued": false,
+  "UserAccess@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.AccessLevel",
+  "UserAccess": "ReadWrite",
+  "SkinColor@odata.type": "#Microsoft.Test.OData.Services.ODataWCFService.Color",
+  "SkinColor": "Blue",
+  "CoverColors@odata.type": "#Collection(Microsoft.Test.OData.Services.ODataWCFService.Color)",
+  "CoverColors": ["Red", "Blue"],
+  "Details@odata.associationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(6)/Details/$ref",
+  "Details@odata.navigationLink": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(6)/Details",
+  "#Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight": {
+    "title": "Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight",
+    "target": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(6)/Microsoft.Test.OData.Services.ODataWCFService.AddAccessRight"
+  },
+  "#Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails": {
+    "title": "Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails",
+    "target": "http://localhost:${cargo.servlet.port}/StaticService/V40/Static.svc/Products(6)/Microsoft.Test.OData.Services.ODataWCFService.GetProductDetails"
+  }
+}