You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@olingo.apache.org by ch...@apache.org on 2014/11/13 17:17:31 UTC

[2/9] olingo-odata4 git commit: Changeset Sorter

Changeset Sorter

Signed-off-by: Christian Amend <ch...@apache.org>


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

Branch: refs/heads/olingo472
Commit: ee2451cbd064e3a5b4585f37192c983f32fe5c55
Parents: 15bd152
Author: Christian Holzer <c....@sap.com>
Authored: Tue Oct 28 18:18:21 2014 +0100
Committer: Christian Amend <ch...@apache.org>
Committed: Thu Nov 13 17:10:55 2014 +0100

----------------------------------------------------------------------
 .../olingo/server/api/batch/BatchOperation.java |   4 +-
 .../server/api/processor/BatchProcessor.java    |  10 +-
 .../olingo/server/core/batch/StringUtil.java    |  54 ------
 .../core/batch/handler/BatchOperationImpl.java  |  16 +-
 .../core/batch/handler/BatchPartHandler.java    |  65 ++++++--
 .../server/core/batch/handler/UriMapping.java   |  34 ++++
 .../core/batch/parser/BatchRequestPartImpl.java |   4 +
 .../olingo/server/core/batch/StringUtil.java    |  54 ++++++
 .../batch/handler/BatchChangeSetSorterTest.java | 164 +++++++++++++++++++
 .../tecsvc/processor/TechnicalProcessor.java    |  44 +----
 10 files changed, 333 insertions(+), 116 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-api/src/main/java/org/apache/olingo/server/api/batch/BatchOperation.java
----------------------------------------------------------------------
diff --git a/lib/server-api/src/main/java/org/apache/olingo/server/api/batch/BatchOperation.java b/lib/server-api/src/main/java/org/apache/olingo/server/api/batch/BatchOperation.java
index 8e438cf..af7d9c1 100644
--- a/lib/server-api/src/main/java/org/apache/olingo/server/api/batch/BatchOperation.java
+++ b/lib/server-api/src/main/java/org/apache/olingo/server/api/batch/BatchOperation.java
@@ -27,9 +27,9 @@ import org.apache.olingo.server.api.ODataResponse;
 public interface BatchOperation {
   public List<BatchRequestPart> parseBatchRequest(InputStream in) throws BatchException;
 
-  public ODataResponse handleODataRequest(ODataRequest request);
+  public ODataResponse handleODataRequest(ODataRequest request, BatchRequestPart requestPart);
 
-  public ODataResponsePart handleBatchRequest(BatchRequestPart request);
+  public ODataResponsePart handleBatchRequest(BatchRequestPart request) throws BatchException;
 
   public void writeResponseParts(List<ODataResponsePart> batchResponses, ODataResponse response) throws BatchException,
       IOException;

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-api/src/main/java/org/apache/olingo/server/api/processor/BatchProcessor.java
----------------------------------------------------------------------
diff --git a/lib/server-api/src/main/java/org/apache/olingo/server/api/processor/BatchProcessor.java b/lib/server-api/src/main/java/org/apache/olingo/server/api/processor/BatchProcessor.java
index 5a9518d..221b38a 100644
--- a/lib/server-api/src/main/java/org/apache/olingo/server/api/processor/BatchProcessor.java
+++ b/lib/server-api/src/main/java/org/apache/olingo/server/api/processor/BatchProcessor.java
@@ -6,9 +6,9 @@
  * 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
@@ -23,9 +23,11 @@ import java.util.List;
 import org.apache.olingo.server.api.ODataRequest;
 import org.apache.olingo.server.api.ODataResponse;
 import org.apache.olingo.server.api.batch.BatchOperation;
+import org.apache.olingo.server.api.batch.BatchRequestPart;
 
 public interface BatchProcessor extends Processor {
-  void executeBatch(BatchOperation operation, ODataRequest requst, ODataResponse response);
+  void executeBatch(BatchOperation operation, ODataRequest requests, ODataResponse response);
 
-  List<ODataResponse> executeChangeSet(BatchOperation operation, List<ODataRequest> requests);
+  List<ODataResponse> executeChangeSet(BatchOperation operation, List<ODataRequest> requests,
+      BatchRequestPart requestPart);
 }

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/StringUtil.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/StringUtil.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/StringUtil.java
deleted file mode 100644
index 2602852..0000000
--- a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/StringUtil.java
+++ /dev/null
@@ -1,54 +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.server.core.batch;
-
-import java.io.ByteArrayInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.InputStreamReader;
-import java.io.UnsupportedEncodingException;
-
-import org.apache.olingo.commons.api.ODataRuntimeException;
-import org.apache.olingo.server.core.batch.parser.BufferedReaderIncludingLineEndings;
-
-public class StringUtil {
-  
-  
-  public static String toString(final InputStream in) throws IOException {
-    final StringBuilder builder = new StringBuilder();
-    final BufferedReaderIncludingLineEndings reader = new BufferedReaderIncludingLineEndings(new InputStreamReader(in));
-    String currentLine;
-    
-    while((currentLine = reader.readLine()) != null) {
-      builder.append(currentLine);
-    }
-    
-    reader.close();
-    
-    return builder.toString();
-  }
-
-  public static InputStream toInputStream(final String string) {
-    try {
-      return new ByteArrayInputStream(string.getBytes("UTF-8"));
-    } catch (UnsupportedEncodingException e) {
-      throw new ODataRuntimeException("Charset UTF-8 not found");
-    }
-  }
-}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchOperationImpl.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchOperationImpl.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchOperationImpl.java
index bc148f0..1f5e243 100644
--- a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchOperationImpl.java
+++ b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchOperationImpl.java
@@ -6,9 +6,9 @@
  * 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
@@ -44,21 +44,21 @@ public class BatchOperationImpl implements BatchOperation {
     partHandler = new BatchPartHandler(oDataHandler, batchProcessor, this);
     writer = new BatchResponseWriter();
     parser = new BatchParser(getContentType(request), request.getRawBaseUri(),
-                              request.getRawServiceResolutionUri(), isStrict);
+        request.getRawServiceResolutionUri(), isStrict);
   }
 
   @Override
   public List<BatchRequestPart> parseBatchRequest(InputStream in) throws BatchException {
     return parser.parseBatchRequest(in);
   }
-
+  
   @Override
-  public ODataResponse handleODataRequest(ODataRequest request) {
-    return partHandler.handleODataRequest(request);
+  public ODataResponse handleODataRequest(ODataRequest request, BatchRequestPart requestPart) {
+    return partHandler.handleODataRequest(request, requestPart);
   }
-
+  
   @Override
-  public ODataResponsePart handleBatchRequest(BatchRequestPart request) {
+  public ODataResponsePart handleBatchRequest(BatchRequestPart request) throws BatchException {
     return partHandler.handleBatchRequest(request);
   }
 

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchPartHandler.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchPartHandler.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchPartHandler.java
index a78d585..df23c55 100644
--- a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchPartHandler.java
+++ b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/BatchPartHandler.java
@@ -19,11 +19,14 @@
 package org.apache.olingo.server.core.batch.handler;
 
 import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.List;
+import java.util.Map;
 
 import org.apache.olingo.commons.api.http.HttpHeader;
 import org.apache.olingo.server.api.ODataRequest;
 import org.apache.olingo.server.api.ODataResponse;
+import org.apache.olingo.server.api.batch.BatchException;
 import org.apache.olingo.server.api.batch.BatchOperation;
 import org.apache.olingo.server.api.batch.BatchRequestPart;
 import org.apache.olingo.server.api.batch.ODataResponsePart;
@@ -36,7 +39,8 @@ public class BatchPartHandler {
   private ODataHandler oDataHandler;
   private BatchProcessor batchProcessor;
   private BatchOperation batchOperation;
-
+  private Map<BatchRequestPart, UriMapping> uriMapping = new HashMap<BatchRequestPart, UriMapping>();
+  
   public BatchPartHandler(final ODataHandler oDataHandler, final BatchProcessor processor,
       final BatchOperation batchOperation) {
     this.oDataHandler = oDataHandler;
@@ -44,23 +48,62 @@ public class BatchPartHandler {
     this.batchOperation = batchOperation;
   }
 
-  public ODataResponse handleODataRequest(ODataRequest request) {
-    final ODataResponse response = oDataHandler.process(request);
-    response.setHeader(BatchParserCommon.HTTP_CONTENT_ID, request.getHeader(BatchParserCommon.HTTP_CONTENT_ID));
+  public ODataResponse handleODataRequest(ODataRequest request, BatchRequestPart requestPart) {
+    final ODataResponse response;
+    
+    if(requestPart.isChangeSet()) {
+      final UriMapping mapping = getUriMappingOrDefault(requestPart);
+      final String reference = BatchChangeSetSorter.getReferenceInURI(request);
+      if(reference != null) {
+        BatchChangeSetSorter.replaceContentIdReference(request, reference, mapping.getUri(reference));
+      }
+      
+       response = oDataHandler.process(request);
+       
+      final String contentId = request.getHeader(BatchParserCommon.HTTP_CONTENT_ID);
+      final String locationHeader = request.getHeader(HttpHeader.LOCATION);
+      mapping.addMapping(contentId, locationHeader);
+    } else {
+      response = oDataHandler.process(request);
+    }
+    
+    final String contentId = request.getHeader(BatchParserCommon.HTTP_CONTENT_ID);
+    if(contentId != null) {
+      response.setHeader(BatchParserCommon.HTTP_CONTENT_ID, contentId);
+    }
     
     return  response;
   }
-
-  public ODataResponsePart handleBatchRequest(BatchRequestPart request) {
-    final List<ODataResponse> responses = new ArrayList<ODataResponse>();
-
+  
+  private UriMapping getUriMappingOrDefault(final BatchRequestPart requestPart) {
+    UriMapping mapping = uriMapping.get(requestPart);
+    
+    if(uriMapping == null) {
+      mapping = new UriMapping();
+    }
+    uriMapping.put(requestPart, mapping);
+    
+    return mapping;
+  }
+  
+  public ODataResponsePart handleBatchRequest(BatchRequestPart request) throws BatchException {
     if (request.isChangeSet()) {
-      responses.addAll(batchProcessor.executeChangeSet(batchOperation, request.getRequests()));
-      return new ODataResponsePartImpl(responses, true);
+      return handleChangeSet(request);
     } else {
-      responses.add(handleODataRequest(request.getRequests().get(0)));
+      final List<ODataResponse> responses = new ArrayList<ODataResponse>();
+      responses.add(handleODataRequest(request.getRequests().get(0), request));
+      
       return new ODataResponsePartImpl(responses, false);
     }
   }
 
+  private ODataResponsePart handleChangeSet(BatchRequestPart request) throws BatchException {
+    final List<ODataResponse> responses = new ArrayList<ODataResponse>();
+    final BatchChangeSetSorter sorter = new BatchChangeSetSorter(request.getRequests());
+
+    responses.addAll(batchProcessor.executeChangeSet(batchOperation, sorter.getOrderdRequests(), request));
+    
+    return new ODataResponsePartImpl(responses, true);
+  }
+
 }

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/UriMapping.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/UriMapping.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/UriMapping.java
new file mode 100644
index 0000000..0123320
--- /dev/null
+++ b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/handler/UriMapping.java
@@ -0,0 +1,34 @@
+/*
+ * 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.server.core.batch.handler;
+
+import java.util.HashMap;
+import java.util.Map;
+
+public class UriMapping {
+  private Map<String, String> uriMapping = new HashMap<String, String>();
+  
+  public void addMapping(final String contentId, final String uri) {
+    uriMapping.put(contentId, uri);
+  }
+  
+  public String getUri(final String contentId) {
+    return uriMapping.get(contentId);
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/parser/BatchRequestPartImpl.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/parser/BatchRequestPartImpl.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/parser/BatchRequestPartImpl.java
index 6c80216..9765b37 100644
--- a/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/parser/BatchRequestPartImpl.java
+++ b/lib/server-core/src/main/java/org/apache/olingo/server/core/batch/parser/BatchRequestPartImpl.java
@@ -25,6 +25,10 @@ import java.util.List;
 import org.apache.olingo.server.api.ODataRequest;
 import org.apache.olingo.server.api.batch.BatchRequestPart;
 
+/**
+ * Has to be immutable!
+ *
+ */
 public class BatchRequestPartImpl implements BatchRequestPart {
 
   private List<ODataRequest> requests = new ArrayList<ODataRequest>();

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-core/src/test/java/org/apache/olingo/server/core/batch/StringUtil.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/test/java/org/apache/olingo/server/core/batch/StringUtil.java b/lib/server-core/src/test/java/org/apache/olingo/server/core/batch/StringUtil.java
new file mode 100644
index 0000000..2602852
--- /dev/null
+++ b/lib/server-core/src/test/java/org/apache/olingo/server/core/batch/StringUtil.java
@@ -0,0 +1,54 @@
+/*
+ * 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.server.core.batch;
+
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.UnsupportedEncodingException;
+
+import org.apache.olingo.commons.api.ODataRuntimeException;
+import org.apache.olingo.server.core.batch.parser.BufferedReaderIncludingLineEndings;
+
+public class StringUtil {
+  
+  
+  public static String toString(final InputStream in) throws IOException {
+    final StringBuilder builder = new StringBuilder();
+    final BufferedReaderIncludingLineEndings reader = new BufferedReaderIncludingLineEndings(new InputStreamReader(in));
+    String currentLine;
+    
+    while((currentLine = reader.readLine()) != null) {
+      builder.append(currentLine);
+    }
+    
+    reader.close();
+    
+    return builder.toString();
+  }
+
+  public static InputStream toInputStream(final String string) {
+    try {
+      return new ByteArrayInputStream(string.getBytes("UTF-8"));
+    } catch (UnsupportedEncodingException e) {
+      throw new ODataRuntimeException("Charset UTF-8 not found");
+    }
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-core/src/test/java/org/apache/olingo/server/core/batch/handler/BatchChangeSetSorterTest.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/test/java/org/apache/olingo/server/core/batch/handler/BatchChangeSetSorterTest.java b/lib/server-core/src/test/java/org/apache/olingo/server/core/batch/handler/BatchChangeSetSorterTest.java
new file mode 100644
index 0000000..9196514
--- /dev/null
+++ b/lib/server-core/src/test/java/org/apache/olingo/server/core/batch/handler/BatchChangeSetSorterTest.java
@@ -0,0 +1,164 @@
+/*
+ * 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.server.core.batch.handler;
+
+import static org.junit.Assert.*;
+
+import java.io.ByteArrayInputStream;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import org.apache.olingo.commons.api.http.HttpMethod;
+import org.apache.olingo.server.api.ODataRequest;
+import org.apache.olingo.server.api.batch.BatchException;
+import org.apache.olingo.server.core.batch.parser.BatchParserCommon;
+import org.junit.Test;
+
+public class BatchChangeSetSorterTest {
+
+  private static final String BASE_URI = "http://localhost/odata.src";
+  
+  @Test
+  public void test() throws BatchException {
+    final List<ODataRequest> changeSet = new ArrayList<ODataRequest>();
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "$1/Adress", "2"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employees", "1"));
+    
+   BatchChangeSetSorter sorter = new BatchChangeSetSorter(changeSet);
+   final List<ODataRequest> sortedChangeSet = sorter.getOrderdRequests();
+   
+   assertEquals(2, sortedChangeSet.size());
+   assertEquals("1", getContentId(sortedChangeSet.get(0)));
+   assertEquals("2", getContentId(sortedChangeSet.get(1)));
+  }
+  
+  private String getContentId(ODataRequest request) {
+    return request.getHeader(BatchParserCommon.HTTP_CONTENT_ID);
+  }
+  
+  @Test
+  public void testNoContentId() throws BatchException {
+    final List<ODataRequest> changeSet = new ArrayList<ODataRequest>();
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "$1/Department", "2"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employees", "1"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employee('2')/Address"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employee('3')/Address"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "$2/Manager", "3"));
+    
+    BatchChangeSetSorter sorter = new BatchChangeSetSorter(changeSet);
+   final List<ODataRequest> sortedChangeSet = sorter.getOrderdRequests();
+   
+   assertEquals(5, sortedChangeSet.size());
+   assertEquals("1", getContentId(sortedChangeSet.get(0)));
+   assertEquals(null, getContentId(sortedChangeSet.get(1)));
+   assertEquals(null, getContentId(sortedChangeSet.get(2)));
+   assertEquals("2", getContentId(sortedChangeSet.get(3)));
+   assertEquals("3", getContentId(sortedChangeSet.get(4)));
+  }
+  
+  @SuppressWarnings("unused")
+  @Test(expected=BatchException.class)
+  public void testContentIdNotAvailable() throws BatchException {
+    final List<ODataRequest> changeSet = new ArrayList<ODataRequest>();
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "$1/Department", "2"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employees", "1"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employee('2')/Address"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employee('3')/Address"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "$4/Manager", "3")); //4 is not available
+    
+   BatchChangeSetSorter sorter = new BatchChangeSetSorter(changeSet);
+   final List<ODataRequest> sortedChangeSet = sorter.getOrderdRequests();
+  }
+  
+  @Test
+  public void testStringAsContentId() throws BatchException {
+    final List<ODataRequest> changeSet = new ArrayList<ODataRequest>();
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "$One/Department", "Two"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employees", "One"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employee('2')/Address"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "Employee('3')/Address"));
+    changeSet.add(createRequest(HttpMethod.POST, BASE_URI, "$Two/Manager", "Three"));
+    
+   BatchChangeSetSorter sorter = new BatchChangeSetSorter(changeSet);
+   final List<ODataRequest> sortedChangeSet = sorter.getOrderdRequests();
+   
+   assertEquals(5, sortedChangeSet.size());
+   assertEquals("One", getContentId(sortedChangeSet.get(0)));
+   assertEquals(null, getContentId(sortedChangeSet.get(1)));
+   assertEquals(null, getContentId(sortedChangeSet.get(2)));
+   assertEquals("Two", getContentId(sortedChangeSet.get(3)));
+   assertEquals("Three", getContentId(sortedChangeSet.get(4)));
+  }
+  
+  @Test
+  public void testRewriting() {
+    final String CONTENT_ID = "1";
+    final String ODATA_PATH ="$" + CONTENT_ID + "/Address";
+    final String RESOURCE_URI = "Employee('1')";
+    final ODataRequest request = createRequest(HttpMethod.POST, BASE_URI, ODATA_PATH);
+    
+    BatchChangeSetSorter.replaceContentIdReference(request, CONTENT_ID, RESOURCE_URI);
+    assertEquals(BASE_URI + "/" + "Employee('1')/Address", request.getRawRequestUri());
+    assertEquals("Employee('1')/Address", request.getRawODataPath());
+  }
+  
+  @Test
+  public void testRewritingNoContentId() {
+    final String CONTENT_ID = "1";
+    final String ODATA_PATH = /* "$" + CONTENT_ID + */ "Address";
+    final String RESOURCE_URI = "Employee('1')";
+    final ODataRequest request = createRequest(HttpMethod.POST, BASE_URI, ODATA_PATH);
+    
+    BatchChangeSetSorter.replaceContentIdReference(request, CONTENT_ID, RESOURCE_URI);
+    assertEquals(BASE_URI + "/" + "Address", request.getRawRequestUri());
+    assertEquals("Address", request.getRawODataPath());
+  }
+  
+  @Test
+  public void testWrongRewriting() {
+    final String CONTENT_ID = "1";
+    final String ODATA_PATH = /*"$1" */ "$2" + "/Address";
+    final String RESOURCE_URI = "Employee('1')";
+    final ODataRequest request = createRequest(HttpMethod.POST, BASE_URI, ODATA_PATH);
+    
+    BatchChangeSetSorter.replaceContentIdReference(request, CONTENT_ID, RESOURCE_URI);
+    assertEquals(BASE_URI + "/" + "$2/Address", request.getRawRequestUri());
+    assertEquals("$2/Address", request.getRawODataPath());
+  }
+  
+  private ODataRequest createRequest(HttpMethod method, String baseUrl, String oDataPath) {
+    return createRequest(method, baseUrl, oDataPath, null);
+  }
+  
+  private ODataRequest createRequest(HttpMethod method, String baseUrl, String oDataPath, String contentId) {
+    final ODataRequest request = new ODataRequest();
+    request.setBody(new ByteArrayInputStream(new byte[0]));
+    request.setMethod(HttpMethod.GET);
+    request.setRawBaseUri(baseUrl);
+    request.setRawODataPath(oDataPath);
+    request.setRawRequestUri(baseUrl + "/" + oDataPath);
+    request.setRawQueryPath("");
+    
+    if(contentId != null) {
+      request.addHeader(BatchParserCommon.HTTP_CONTENT_ID, Arrays.asList(new String[] { contentId }));
+    }
+    return request;
+  }
+}

http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/ee2451cb/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/processor/TechnicalProcessor.java
----------------------------------------------------------------------
diff --git a/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/processor/TechnicalProcessor.java b/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/processor/TechnicalProcessor.java
index b59c92e..e5a0d44 100644
--- a/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/processor/TechnicalProcessor.java
+++ b/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/processor/TechnicalProcessor.java
@@ -21,7 +21,6 @@ package org.apache.olingo.server.tecsvc.processor;
 import java.io.ByteArrayInputStream;
 import java.io.IOException;
 import java.io.UnsupportedEncodingException;
-import java.util.ArrayList;
 import java.util.LinkedList;
 import java.util.List;
 import java.util.Locale;
@@ -74,7 +73,7 @@ import org.apache.olingo.server.tecsvc.data.DataProvider;
 /**
  * Technical Processor which provides currently implemented processor functionality.
  */
-public class TechnicalProcessor implements EntitySetProcessor, EntityProcessor, PropertyProcessor, BatchProcessor {
+public class TechnicalProcessor implements EntitySetProcessor, EntityProcessor, PropertyProcessor {
 
   private OData odata;
   private DataProvider dataProvider;
@@ -198,12 +197,12 @@ public class TechnicalProcessor implements EntitySetProcessor, EntityProcessor,
     List<UriResource> subResPaths = resourcePaths.subList(1, resourcePaths.size());
     for (UriResource subResPath : subResPaths) {
       UriResourceKind kind = subResPath.getKind();
-      if(kind != UriResourceKind.primitiveProperty
-              && kind != UriResourceKind.complexProperty
-              && kind != UriResourceKind.count
-              && kind != UriResourceKind.value) {
+      if (kind != UriResourceKind.primitiveProperty
+          && kind != UriResourceKind.complexProperty
+          && kind != UriResourceKind.count
+          && kind != UriResourceKind.value) {
         throw new ODataApplicationException("Invalid resource type.",
-                HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ROOT);
+            HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ROOT);
       }
     }
 
@@ -219,6 +218,7 @@ public class TechnicalProcessor implements EntitySetProcessor, EntityProcessor,
       final EdmEntitySet entitySet, final boolean isSingleEntity,
       final ExpandOption expand, final SelectOption select,
       final List<UriParameter> keys, final String propertyPath) throws SerializerException {
+
     return ContextURL.with().entitySet(entitySet)
         .selectList(serializer.buildContextURLSelectList(entitySet, expand, select))
         .suffix(isSingleEntity && propertyPath == null ? Suffix.ENTITY : null)
@@ -226,7 +226,6 @@ public class TechnicalProcessor implements EntitySetProcessor, EntityProcessor,
         .navOrPropertyPath(propertyPath)
         .build();
   }
-
   @Override
   public void readProperty(final ODataRequest request, ODataResponse response, final UriInfo uriInfo,
       final ContentType contentType) throws ODataApplicationException, SerializerException {
@@ -334,33 +333,4 @@ public class TechnicalProcessor implements EntitySetProcessor, EntityProcessor,
       }
     }
   }
-
-  @Override
-  public void executeBatch(BatchOperation operation, ODataRequest requst, ODataResponse response) {
-    try {
-      final List<BatchRequestPart> parts = operation.parseBatchRequest(requst.getBody());
-      final List<ODataResponsePart> responseParts = new ArrayList<ODataResponsePart>();
-      
-      for(BatchRequestPart part : parts) {
-        responseParts.add(operation.handleBatchRequest(part));
-      }
-      
-      operation.writeResponseParts(responseParts, response);
-    } catch (BatchException e) {
-      throw new ODataRuntimeException(e);
-    } catch (IOException e) {
-      throw new ODataRuntimeException(e);
-    }
-  }
-
-  @Override
-  public List<ODataResponse> executeChangeSet(BatchOperation operation, List<ODataRequest> requests) {
-    List<ODataResponse> responses = new ArrayList<ODataResponse>();
-    
-    for(ODataRequest request : requests) {
-      responses.add(operation.handleODataRequest(request));
-    }
-    
-    return responses;
-  }
 }