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 2015/09/30 15:12:05 UTC
[3/3] olingo-odata4 git commit: [OLINGO-780] The URI Parser validates
if a function is composable or not
[OLINGO-780] The URI Parser validates if a function is composable or not
Project: http://git-wip-us.apache.org/repos/asf/olingo-odata4/repo
Commit: http://git-wip-us.apache.org/repos/asf/olingo-odata4/commit/b9403cd3
Tree: http://git-wip-us.apache.org/repos/asf/olingo-odata4/tree/b9403cd3
Diff: http://git-wip-us.apache.org/repos/asf/olingo-odata4/diff/b9403cd3
Branch: refs/heads/master
Commit: b9403cd39433ba6d66054c92d02974e3187f401f
Parents: b7dcae8
Author: Christia Holzer <c....@sap.com>
Authored: Wed Sep 30 11:22:29 2015 +0200
Committer: Christia Holzer <c....@sap.com>
Committed: Wed Sep 30 15:04:24 2015 +0200
----------------------------------------------------------------------
.../uri/validator/UriValidationException.java | 4 +-
.../server/core/uri/validator/UriValidator.java | 36 ++++++++++-
.../server-core-exceptions-i18n.properties | 1 +
.../tecsvc/provider/FunctionProvider.java | 2 +-
.../olingo/server/core/ODataHandlerTest.java | 24 ++++---
.../core/uri/antlr/TestFullResourcePath.java | 66 ++++++++++++++++++++
6 files changed, 120 insertions(+), 13 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/b9403cd3/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidationException.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidationException.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidationException.java
index 5760e88..d883b0c 100644
--- a/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidationException.java
+++ b/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidationException.java
@@ -52,7 +52,9 @@ public class UriValidationException extends ODataLibraryException {
/** parameter: unallowed kind before $value */
UNALLOWED_KIND_BEFORE_VALUE,
/** parameter: unallowed kind before $count */
- UNALLOWED_KIND_BEFORE_COUNT;
+ UNALLOWED_KIND_BEFORE_COUNT,
+ /** parameter: unallowed resource path */
+ UNALLOWED_RESOURCE_PATH;
@Override
public String getKey() {
http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/b9403cd3/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidator.java
----------------------------------------------------------------------
diff --git a/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidator.java b/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidator.java
index 8693f1e..feb52ec 100644
--- a/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidator.java
+++ b/lib/server-core/src/main/java/org/apache/olingo/server/core/uri/validator/UriValidator.java
@@ -222,7 +222,14 @@ public class UriValidator {
private RowIndexForUriType rowIndexForResourceKind(final UriInfo uriInfo) throws UriValidationException {
RowIndexForUriType idx;
-
+
+ final int nonComposableFunctionIndex = getIndexOfLastNonComposableFunction(uriInfo);
+ if(nonComposableFunctionIndex != -1 && (uriInfo.getUriResourceParts().size() - 1) > nonComposableFunctionIndex) {
+ throw new UriValidationException("Non composable functions followed by further resource parts are not allowed",
+ UriValidationException.MessageKeys.UNALLOWED_RESOURCE_PATH,
+ uriInfo.getUriResourceParts().get(nonComposableFunctionIndex + 1).getSegmentValue());
+ }
+
int lastPathSegmentIndex = uriInfo.getUriResourceParts().size() - 1;
UriResource lastPathSegment = uriInfo.getUriResourceParts().get(lastPathSegmentIndex);
@@ -241,7 +248,11 @@ public class UriValidator {
idx = rowIndexForEntitySet(lastPathSegment);
break;
case function:
- idx = rowIndexForFunction(lastPathSegment);
+ if(nonComposableFunctionIndex == -1) {
+ idx = rowIndexForFunction(lastPathSegment);
+ } else {
+ idx = RowIndexForUriType.none;
+ }
break;
case primitiveProperty:
idx = rowIndexForPrimitiveProperty(lastPathSegment);
@@ -266,6 +277,21 @@ public class UriValidator {
return idx;
}
+ private int getIndexOfLastNonComposableFunction(final UriInfo uriInfo) {
+ for(int i = 0; i < uriInfo.getUriResourceParts().size(); i++) {
+ final UriResource resourcePath = uriInfo.getUriResourceParts().get(i);
+
+ if(resourcePath instanceof UriResourceFunction) {
+ final UriResourceFunction resourceFuntion = (UriResourceFunction) resourcePath;
+ if(!resourceFuntion.getFunction().isComposable()) {
+ return i;
+ }
+ }
+ }
+
+ return -1;
+ }
+
private RowIndexForUriType rowIndexForValue(final UriInfo uriInfo) throws UriValidationException {
RowIndexForUriType idx;
int secondLastPathSegmentIndex = uriInfo.getUriResourceParts().size() - 2;
@@ -327,6 +353,12 @@ public class UriValidator {
RowIndexForUriType idx;
UriResourceFunction urf = (UriResourceFunction) lastPathSegment;
EdmReturnType rt = urf.getFunction().getReturnType();
+
+ if(!urf.getFunction().isComposable()) {
+ return RowIndexForUriType.none;
+ }
+
+
switch (rt.getType().getKind()) {
case ENTITY:
idx = rt.isCollection() && urf.getKeyPredicates().isEmpty() ?
http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/b9403cd3/lib/server-core/src/main/resources/server-core-exceptions-i18n.properties
----------------------------------------------------------------------
diff --git a/lib/server-core/src/main/resources/server-core-exceptions-i18n.properties b/lib/server-core/src/main/resources/server-core-exceptions-i18n.properties
index f7c2894..de14eb0 100644
--- a/lib/server-core/src/main/resources/server-core-exceptions-i18n.properties
+++ b/lib/server-core/src/main/resources/server-core-exceptions-i18n.properties
@@ -81,6 +81,7 @@ UriValidationException.LAST_SEGMENT_NOT_TYPED=The last segment '%1$s' is not typ
UriValidationException.SECOND_LAST_SEGMENT_NOT_TYPED=The second last segment '%1$s' is not typed.
UriValidationException.UNALLOWED_KIND_BEFORE_VALUE=The kind '%1$s' is not allowed before '$value'.
UriValidationException.UNALLOWED_KIND_BEFORE_COUNT=The kind '%1$s' is not allowed before '$count'.
+UriValidationException.UNALLOWED_RESOURCE_PATH=The resource part '%1$s' is not allowed.
ContentNegotiatorException.UNSUPPORTED_ACCEPT_TYPES=The content-type range '%1$s' is not supported as value of the Accept header.
ContentNegotiatorException.UNSUPPORTED_CONTENT_TYPE=The content type '%1$s' is not supported.
http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/b9403cd3/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/provider/FunctionProvider.java
----------------------------------------------------------------------
diff --git a/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/provider/FunctionProvider.java b/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/provider/FunctionProvider.java
index df4cfbd..a83abab 100644
--- a/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/provider/FunctionProvider.java
+++ b/lib/server-tecsvc/src/main/java/org/apache/olingo/server/tecsvc/provider/FunctionProvider.java
@@ -574,7 +574,7 @@ public class FunctionProvider {
.setParameters(Arrays.asList(
new CsdlParameter().setName("BindingParam").setType(EntityTypeProvider.nameETBaseTwoKeyNav)
.setCollection(true).setNullable(false)))
- .setComposable(true)
+ .setComposable(false)
.setReturnType(
new CsdlReturnType().setType(EntityTypeProvider.nameETBaseTwoKeyNav).setCollection(true)
.setNullable(false))
http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/b9403cd3/lib/server-test/src/test/java/org/apache/olingo/server/core/ODataHandlerTest.java
----------------------------------------------------------------------
diff --git a/lib/server-test/src/test/java/org/apache/olingo/server/core/ODataHandlerTest.java b/lib/server-test/src/test/java/org/apache/olingo/server/core/ODataHandlerTest.java
index 76b7b50..d4b87d4 100644
--- a/lib/server-test/src/test/java/org/apache/olingo/server/core/ODataHandlerTest.java
+++ b/lib/server-test/src/test/java/org/apache/olingo/server/core/ODataHandlerTest.java
@@ -318,17 +318,16 @@ public class ODataHandlerTest {
dispatch(HttpMethod.GET, "FICRTString()", primitiveProcessor);
verify(primitiveProcessor).readPrimitive(
any(ODataRequest.class), any(ODataResponse.class), any(UriInfo.class), any(ContentType.class));
-
+
+ // FINRTInt16 is not composable so /$value is not allowed
final String valueUri = "FINRTInt16()/$value";
final PrimitiveValueProcessor primitiveValueProcessor = mock(PrimitiveValueProcessor.class);
- dispatch(HttpMethod.GET, valueUri, primitiveValueProcessor);
- verify(primitiveValueProcessor).readPrimitiveValue(
- any(ODataRequest.class), any(ODataResponse.class), any(UriInfo.class), any(ContentType.class));
- dispatchMethodNotAllowed(HttpMethod.POST, valueUri, primitiveValueProcessor);
- dispatchMethodNotAllowed(HttpMethod.PATCH, valueUri, primitiveValueProcessor);
- dispatchMethodNotAllowed(HttpMethod.PUT, valueUri, primitiveValueProcessor);
- dispatchMethodNotAllowed(HttpMethod.DELETE, valueUri, primitiveValueProcessor);
-
+ dispatchMethodWithError(HttpMethod.GET, valueUri, primitiveValueProcessor, HttpStatusCode.BAD_REQUEST);
+ dispatchMethodWithError(HttpMethod.POST, valueUri, primitiveValueProcessor, HttpStatusCode.BAD_REQUEST);
+ dispatchMethodWithError(HttpMethod.PATCH, valueUri, primitiveValueProcessor, HttpStatusCode.BAD_REQUEST);
+ dispatchMethodWithError(HttpMethod.PUT, valueUri, primitiveValueProcessor, HttpStatusCode.BAD_REQUEST);
+ dispatchMethodWithError(HttpMethod.DELETE, valueUri, primitiveValueProcessor, HttpStatusCode.BAD_REQUEST);
+
final String primitiveCollectionUri = "FICRTCollString()";
PrimitiveCollectionProcessor primitiveCollectionProcessor = mock(PrimitiveCollectionProcessor.class);
dispatch(HttpMethod.GET, primitiveCollectionUri, primitiveCollectionProcessor);
@@ -759,4 +758,11 @@ public class ODataHandlerTest {
assertEquals(HttpStatusCode.METHOD_NOT_ALLOWED.getStatusCode(), response.getStatusCode());
assertNotNull(response.getContent());
}
+
+ private void dispatchMethodWithError(final HttpMethod method, final String path, final Processor processor,
+ final HttpStatusCode statusCode) {
+ final ODataResponse response = dispatch(method, path, processor);
+ assertEquals(statusCode.getStatusCode(), response.getStatusCode());
+ assertNotNull(response.getContent());
+ }
}
http://git-wip-us.apache.org/repos/asf/olingo-odata4/blob/b9403cd3/lib/server-test/src/test/java/org/apache/olingo/server/core/uri/antlr/TestFullResourcePath.java
----------------------------------------------------------------------
diff --git a/lib/server-test/src/test/java/org/apache/olingo/server/core/uri/antlr/TestFullResourcePath.java b/lib/server-test/src/test/java/org/apache/olingo/server/core/uri/antlr/TestFullResourcePath.java
index 9c859db..5c06e2c 100644
--- a/lib/server-test/src/test/java/org/apache/olingo/server/core/uri/antlr/TestFullResourcePath.java
+++ b/lib/server-test/src/test/java/org/apache/olingo/server/core/uri/antlr/TestFullResourcePath.java
@@ -1145,6 +1145,72 @@ public class TestFullResourcePath {
}
@Test
+ public void runNonComposableFunctions() throws Exception {
+ testUri.run("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')")
+ .isKind(UriInfoKind.resource)
+ .goPath().first()
+ .isFunctionImport("FICRTCollETMixPrimCollCompTwoParam")
+ .isFunction("UFCRTCollETMixPrimCollCompTwoParam")
+ .isParameter(0, "ParameterInt16", "1")
+ .isParameter(1, "ParameterString", "'1'");
+
+ testUri.run("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')(0)")
+ .isKind(UriInfoKind.resource)
+ .goPath().first()
+ .isFunctionImport("FICRTCollETMixPrimCollCompTwoParam")
+ .isFunction("UFCRTCollETMixPrimCollCompTwoParam")
+ .isParameter(0, "ParameterInt16", "1")
+ .isParameter(1, "ParameterString", "'1'");
+
+ testUri.runEx("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')(0)/PropertyInt16")
+ .isExValidation(UriValidationException.MessageKeys.UNALLOWED_RESOURCE_PATH);
+
+ testUri.runEx("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')", "$skip=1")
+ .isExValidation(UriValidationException.MessageKeys.SYSTEM_QUERY_OPTION_NOT_ALLOWED);
+
+ testUri.runEx("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')", "$top=1")
+ .isExValidation(UriValidationException.MessageKeys.SYSTEM_QUERY_OPTION_NOT_ALLOWED);
+
+ testUri.runEx("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')",
+ "$filter=PropertyInt16 eq 1")
+ .isExValidation(UriValidationException.MessageKeys.SYSTEM_QUERY_OPTION_NOT_ALLOWED);
+
+ testUri.runEx("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')", "$skip=1")
+ .isExValidation(UriValidationException.MessageKeys.SYSTEM_QUERY_OPTION_NOT_ALLOWED);
+
+ testUri.runEx("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')", "$count=true")
+ .isExValidation(UriValidationException.MessageKeys.SYSTEM_QUERY_OPTION_NOT_ALLOWED);
+
+ testUri.runEx("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')", "$skiptoken=5")
+ .isExValidation(UriValidationException.MessageKeys.SYSTEM_QUERY_OPTION_NOT_ALLOWED);
+
+ // $search is currently not implemented. Please change this exception if the implementation is done.
+ testUri.runEx("FICRTCollETMixPrimCollCompTwoParam(ParameterInt16=1,ParameterString='1')", "$search=test")
+ .isExSemantic(MessageKeys.NOT_IMPLEMENTED);
+
+ testUri.run("ESBaseTwoKeyNav/olingo.odata.test1.BFCESBaseTwoKeyNavRTESBaseTwoKey()")
+ .isKind(UriInfoKind.resource)
+ .goPath().first()
+ .isEntitySet("ESBaseTwoKeyNav")
+ .at(1)
+ .isFunction("BFCESBaseTwoKeyNavRTESBaseTwoKey");
+
+ testUri.run("ESBaseTwoKeyNav/olingo.odata.test1.BFCESBaseTwoKeyNavRTESBaseTwoKey()"
+ + "(PropertyInt16=1,PropertyString='1')")
+ .isKind(UriInfoKind.resource)
+ .goPath().first()
+ .isEntitySet("ESBaseTwoKeyNav")
+ .at(1)
+ .isFunction("BFCESBaseTwoKeyNavRTESBaseTwoKey")
+ .isKeyPredicate(0, "PropertyInt16", "1")
+ .isKeyPredicate(1, "PropertyString", "'1'");
+
+ testUri.runEx("ESBaseTwoKeyNav/olingo.odata.test1.BFCESBaseTwoKeyNavRTESBaseTwoKey()"
+ + "(PropertyInt16=1,PropertyString='1')/NavPropertyETBaseTwoKeyNavOne")
+ .isExValidation(UriValidationException.MessageKeys.UNALLOWED_RESOURCE_PATH);
+ }
+
+ @Test
public void runEsNameCast() throws Exception {
testUri.run("ESTwoPrim/olingo.odata.test1.ETBase")
.isKind(UriInfoKind.resource).goPath()