From 1558273f521fdae0a6bf9ea9632befc93a97ae88 Mon Sep 17 00:00:00 2001 From: Christia Holzer Date: Tue, 8 Sep 2015 10:50:01 +0200 Subject: [PATCH] [OLINGO-713] Tutorial: Merged version of the tutorials added --- .../myservice/mynamespace/data/Storage.java | 139 +++++++++++- .../service/DemoEntityProcessor.java | 198 ++++++++++++++---- .../java/myservice/mynamespace/util/Util.java | 23 +- .../java/myservice/mynamespace/util/Util.java | 4 +- 4 files changed, 321 insertions(+), 43 deletions(-) diff --git a/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/data/Storage.java b/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/data/Storage.java index 2034fe6fd..04911e764 100644 --- a/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/data/Storage.java +++ b/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/data/Storage.java @@ -20,6 +20,7 @@ package myservice.mynamespace.data; import java.util.ArrayList; import java.util.List; +import java.util.Locale; import myservice.mynamespace.service.DemoEdmProvider; import myservice.mynamespace.util.Util; @@ -30,7 +31,11 @@ import org.apache.olingo.commons.api.data.Property; import org.apache.olingo.commons.api.data.ValueType; import org.apache.olingo.commons.api.edm.EdmEntitySet; import org.apache.olingo.commons.api.edm.EdmEntityType; +import org.apache.olingo.commons.api.edm.EdmKeyPropertyRef; import org.apache.olingo.commons.api.edm.FullQualifiedName; +import org.apache.olingo.commons.api.http.HttpMethod; +import org.apache.olingo.commons.api.http.HttpStatusCode; +import org.apache.olingo.server.api.ODataApplicationException; import org.apache.olingo.server.api.uri.UriParameter; public class Storage { @@ -132,7 +137,44 @@ public class Storage { return navigationTargetEntityCollection; } + + public Entity createEntityData(EdmEntitySet edmEntitySet, Entity entityToCreate) { + EdmEntityType edmEntityType = edmEntitySet.getEntityType(); + + // actually, this is only required if we have more than one Entity Type + if (edmEntityType.getName().equals(DemoEdmProvider.ET_PRODUCT_NAME)) { + return createProduct(edmEntityType, entityToCreate); + } + + return null; + } + + /** + * This method is invoked for PATCH or PUT requests + * */ + public void updateEntityData(EdmEntitySet edmEntitySet, List keyParams, Entity updateEntity, + HttpMethod httpMethod) throws ODataApplicationException { + + EdmEntityType edmEntityType = edmEntitySet.getEntityType(); + + // actually, this is only required if we have more than one Entity Type + if (edmEntityType.getName().equals(DemoEdmProvider.ET_PRODUCT_NAME)) { + updateProduct(edmEntityType, keyParams, updateEntity, httpMethod); + } + } + + public void deleteEntityData(EdmEntitySet edmEntitySet, List keyParams) + throws ODataApplicationException { + + EdmEntityType edmEntityType = edmEntitySet.getEntityType(); + + // actually, this is only required if we have more than one Entity Type + if (edmEntityType.getName().equals(DemoEdmProvider.ET_PRODUCT_NAME)) { + deleteProduct(edmEntityType, keyParams); + } + } + /* INTERNAL */ private EntityCollection getProducts() { @@ -172,9 +214,104 @@ public class Storage { /* generic approach to find the requested entity */ return Util.findEntity(edmEntityType, entitySet, keyParams); } + + private void updateProduct(EdmEntityType edmEntityType, List keyParams, Entity entity, + HttpMethod httpMethod) throws ODataApplicationException { + Entity productEntity = getProduct(edmEntityType, keyParams); + if (productEntity == null) { + throw new ODataApplicationException("Entity not found", HttpStatusCode.NOT_FOUND.getStatusCode(), Locale.ENGLISH); + } + + // loop over all properties and replace the values with the values of the given payload + // Note: ignoring ComplexType, as we don't have it in our odata model + List existingProperties = productEntity.getProperties(); + for (Property existingProp : existingProperties) { + String propName = existingProp.getName(); + + // ignore the key properties, they aren't updateable + if (isKey(edmEntityType, propName)) { + continue; + } + + Property updateProperty = entity.getProperty(propName); + // the request payload might not consider ALL properties, so it can be null + if (updateProperty == null) { + // if a property has NOT been added to the request payload + // depending on the HttpMethod, our behavior is different + if (httpMethod.equals(HttpMethod.PATCH)) { + // as of the OData spec, in case of PATCH, the existing property is not touched + continue; // do nothing + } else if (httpMethod.equals(HttpMethod.PUT)) { + // as of the OData spec, in case of PUT, the existing property is set to null (or to default value) + existingProp.setValue(existingProp.getValueType(), null); + continue; + } + } + + // change the value of the properties + existingProp.setValue(existingProp.getValueType(), updateProperty.getValue()); + } + } + + private void deleteProduct(EdmEntityType edmEntityType, List keyParams) + throws ODataApplicationException { + + Entity productEntity = getProduct(edmEntityType, keyParams); + if (productEntity == null) { + throw new ODataApplicationException("Entity not found", HttpStatusCode.NOT_FOUND.getStatusCode(), Locale.ENGLISH); + } + + this.productList.remove(productEntity); + } + + private Entity createProduct(EdmEntityType edmEntityType, Entity entity) { + + // the ID of the newly created product entity is generated automatically + int newId = 1; + while (productIdExists(newId)) { + newId++; + } + + Property idProperty = entity.getProperty("ID"); + if (idProperty != null) { + idProperty.setValue(ValueType.PRIMITIVE, new Integer(newId)); + } else { + // as of OData v4 spec, the key property can be omitted from the POST request body + entity.getProperties().add(new Property(null, "ID", ValueType.PRIMITIVE, newId)); + } + + this.productList.add(entity); + + return entity; + + } + + private boolean productIdExists(int id) { + + for (Entity entity : this.productList) { + Integer existingID = (Integer) entity.getProperty("ID").getValue(); + if (existingID.intValue() == id) { + return true; + } + } + + return false; + } + /* HELPER */ - + + private boolean isKey(EdmEntityType edmEntityType, String propertyName) { + List keyPropertyRefs = edmEntityType.getKeyPropertyRefs(); + for (EdmKeyPropertyRef propRef : keyPropertyRefs) { + String keyPropertyName = propRef.getName(); + if (keyPropertyName.equals(propertyName)) { + return true; + } + } + return false; + } + private void initProductSampleData() { Entity entity = new Entity(); diff --git a/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/service/DemoEntityProcessor.java b/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/service/DemoEntityProcessor.java index 6b623b08f..097e26d00 100644 --- a/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/service/DemoEntityProcessor.java +++ b/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/service/DemoEntityProcessor.java @@ -18,11 +18,10 @@ */ package myservice.mynamespace.service; +import java.io.InputStream; import java.util.List; import java.util.Locale; -import myservice.mynamespace.data.Storage; - import org.apache.olingo.commons.api.Constants; import org.apache.olingo.commons.api.data.ContextURL; import org.apache.olingo.commons.api.data.ContextURL.Suffix; @@ -36,6 +35,7 @@ import org.apache.olingo.commons.api.edm.EdmNavigationProperty; import org.apache.olingo.commons.api.edm.EdmNavigationPropertyBinding; import org.apache.olingo.commons.api.format.ContentType; import org.apache.olingo.commons.api.http.HttpHeader; +import org.apache.olingo.commons.api.http.HttpMethod; import org.apache.olingo.commons.api.http.HttpStatusCode; import org.apache.olingo.server.api.OData; import org.apache.olingo.server.api.ODataApplicationException; @@ -43,6 +43,8 @@ import org.apache.olingo.server.api.ODataRequest; import org.apache.olingo.server.api.ODataResponse; import org.apache.olingo.server.api.ServiceMetadata; import org.apache.olingo.server.api.deserializer.DeserializerException; +import org.apache.olingo.server.api.deserializer.DeserializerResult; +import org.apache.olingo.server.api.deserializer.ODataDeserializer; import org.apache.olingo.server.api.processor.EntityProcessor; import org.apache.olingo.server.api.serializer.EntitySerializerOptions; import org.apache.olingo.server.api.serializer.ODataSerializer; @@ -57,10 +59,13 @@ import org.apache.olingo.server.api.uri.queryoption.ExpandItem; import org.apache.olingo.server.api.uri.queryoption.ExpandOption; import org.apache.olingo.server.api.uri.queryoption.SelectOption; +import myservice.mynamespace.data.Storage; +import myservice.mynamespace.util.Util; + public class DemoEntityProcessor implements EntityProcessor { private OData odata; - private ServiceMetadata srvMetadata; + private ServiceMetadata serviceMetadata; private Storage storage; public DemoEntityProcessor(Storage storage) { @@ -69,21 +74,73 @@ public class DemoEntityProcessor implements EntityProcessor { public void init(OData odata, ServiceMetadata serviceMetadata) { this.odata = odata; - this.srvMetadata = serviceMetadata; + this.serviceMetadata = serviceMetadata; } public void readEntity(ODataRequest request, ODataResponse response, UriInfo uriInfo, ContentType responseFormat) throws ODataApplicationException, SerializerException { - // 1. retrieve the Entity Type - List resourcePaths = uriInfo.getUriResourceParts(); - // Note: only in our example we can assume that the first segment is the EntitySet - UriResourceEntitySet uriResourceEntitySet = (UriResourceEntitySet) resourcePaths.get(0); - EdmEntitySet edmEntitySet = uriResourceEntitySet.getEntitySet(); + EdmEntityType responseEdmEntityType = null; // we'll need this to build the ContextURL + Entity responseEntity = null; // required for serialization of the response body + EdmEntitySet responseEdmEntitySet = null; // we need this for building the contextUrl - // 2. retrieve the data from backend - List keyPredicates = uriResourceEntitySet.getKeyPredicates(); - Entity entity = storage.readEntityData(edmEntitySet, keyPredicates); + // 1st step: retrieve the requested Entity: can be "normal" read operation, or navigation (to-one) + List resourceParts = uriInfo.getUriResourceParts(); + int segmentCount = resourceParts.size(); + + UriResource uriResource = resourceParts.get(0); // in our example, the first segment is the EntitySet + if (!(uriResource instanceof UriResourceEntitySet)) { + throw new ODataApplicationException("Only EntitySet is supported", + HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ENGLISH); + } + + UriResourceEntitySet uriResourceEntitySet = (UriResourceEntitySet) uriResource; + EdmEntitySet startEdmEntitySet = uriResourceEntitySet.getEntitySet(); + + // Analyze the URI segments + if (segmentCount == 1) { // no navigation + responseEdmEntityType = startEdmEntitySet.getEntityType(); + responseEdmEntitySet = startEdmEntitySet; // since we have only one segment + + // 2. step: retrieve the data from backend + List keyPredicates = uriResourceEntitySet.getKeyPredicates(); + responseEntity = storage.readEntityData(startEdmEntitySet, keyPredicates); + } else if (segmentCount == 2) { // navigation + UriResource navSegment = resourceParts.get(1); // in our example we don't support more complex URIs + if (navSegment instanceof UriResourceNavigation) { + UriResourceNavigation uriResourceNavigation = (UriResourceNavigation) navSegment; + EdmNavigationProperty edmNavigationProperty = uriResourceNavigation.getProperty(); + responseEdmEntityType = edmNavigationProperty.getType(); + // contextURL displays the last segment + responseEdmEntitySet = Util.getNavigationTargetEntitySet(startEdmEntitySet, edmNavigationProperty); + + // 2nd: fetch the data from backend. + // e.g. for the URI: Products(1)/Category we have to find the correct Category entity + List keyPredicates = uriResourceEntitySet.getKeyPredicates(); + // e.g. for Products(1)/Category we have to find first the Products(1) + Entity sourceEntity = storage.readEntityData(startEdmEntitySet, keyPredicates); + + // now we have to check if the navigation is + // a) to-one: e.g. Products(1)/Category + // b) to-many with key: e.g. Categories(3)/Products(5) + // the key for nav is used in this case: Categories(3)/Products(5) + List navKeyPredicates = uriResourceNavigation.getKeyPredicates(); + + if (navKeyPredicates.isEmpty()) { // e.g. DemoService.svc/Products(1)/Category + responseEntity = storage.getRelatedEntity(sourceEntity, responseEdmEntityType); + } else { // e.g. DemoService.svc/Categories(3)/Products(5) + responseEntity = storage.getRelatedEntity(sourceEntity, responseEdmEntityType, navKeyPredicates); + } + } + } else { + // this would be the case for e.g. Products(1)/Category/Products(1)/Category + throw new ODataApplicationException("Not supported", HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ROOT); + } + + if (responseEntity == null) { + // this is the case for e.g. DemoService.svc/Categories(4) or DemoService.svc/Categories(3)/Products(999) + throw new ODataApplicationException("Nothing found.", HttpStatusCode.NOT_FOUND.getStatusCode(), Locale.ROOT); + } // 3. apply system query options @@ -102,13 +159,13 @@ public class DemoEntityProcessor implements EntityProcessor { EdmNavigationProperty edmNavigationProperty = null; ExpandItem expandItem = expandOption.getExpandItems().get(0); if(expandItem.isStar()) { - List bindings = edmEntitySet.getNavigationPropertyBindings(); + List bindings = responseEdmEntitySet.getNavigationPropertyBindings(); // we know that there are navigation bindings // however normally in this case a check if navigation bindings exists is done if(!bindings.isEmpty()) { // can in our case only be 'Category' or 'Products', so we can take the first EdmNavigationPropertyBinding binding = bindings.get(0); - EdmElement property = edmEntitySet.getEntityType().getProperty(binding.getPath()); + EdmElement property = responseEdmEntitySet.getEntityType().getProperty(binding.getPath()); // we don't need to handle error cases, as it is done in the Olingo library if(property instanceof EdmNavigationProperty) { edmNavigationProperty = (EdmNavigationProperty) property; @@ -116,10 +173,10 @@ public class DemoEntityProcessor implements EntityProcessor { } } else { // can be 'Category' or 'Products', no path supported - UriResource uriResource = expandItem.getResourcePath().getUriResourceParts().get(0); + UriResource expandUriResource = expandItem.getResourcePath().getUriResourceParts().get(0); // we don't need to handle error cases, as it is done in the Olingo library - if(uriResource instanceof UriResourceNavigation) { - edmNavigationProperty = ((UriResourceNavigation) uriResource).getProperty(); + if(expandUriResource instanceof UriResourceNavigation) { + edmNavigationProperty = ((UriResourceNavigation) expandUriResource).getProperty(); } } @@ -137,26 +194,26 @@ public class DemoEntityProcessor implements EntityProcessor { if(edmNavigationProperty.isCollection()){ // in case of Categories(1)/$expand=Products // fetch the data for the $expand (to-many navigation) from backend // here we get the data for the expand - EntityCollection expandEntityCollection = storage.getRelatedEntityCollection(entity, expandEdmEntityType); + EntityCollection expandEntityCollection = storage.getRelatedEntityCollection(responseEntity, expandEdmEntityType); link.setInlineEntitySet(expandEntityCollection); } else { // in case of Products(1)?$expand=Category // fetch the data for the $expand (to-one navigation) from backend // here we get the data for the expand - Entity expandEntity = storage.getRelatedEntity(entity, expandEdmEntityType); + Entity expandEntity = storage.getRelatedEntity(responseEntity, expandEdmEntityType); link.setInlineEntity(expandEntity); } // set the link - containing the expanded data - to the current entity - entity.getNavigationLinks().add(link); + responseEntity.getNavigationLinks().add(link); } } // 4. serialize - EdmEntityType edmEntityType = edmEntitySet.getEntityType(); + EdmEntityType edmEntityType = responseEdmEntitySet.getEntityType(); // we need the property names of the $select, in order to build the context URL String selectList = odata.createUriHelper().buildContextURLSelectList(edmEntityType, expandOption, selectOption); - ContextURL contextUrl = ContextURL.with().entitySet(edmEntitySet) + ContextURL contextUrl = ContextURL.with().entitySet(responseEdmEntitySet) .selectList(selectList) .suffix(Suffix.ENTITY).build(); @@ -169,34 +226,99 @@ public class DemoEntityProcessor implements EntityProcessor { .build(); ODataSerializer serializer = this.odata.createSerializer(responseFormat); - SerializerResult serializerResult = serializer.entity(srvMetadata, edmEntityType, entity, opts); + SerializerResult serializerResult = serializer.entity(serviceMetadata, edmEntityType, responseEntity, opts); // 5. configure the response object response.setContent(serializerResult.getContent()); response.setStatusCode(HttpStatusCode.OK.getStatusCode()); response.setHeader(HttpHeader.CONTENT_TYPE, responseFormat.toContentTypeString()); } - - - - /* - * These processor methods are not handled in this tutorial - */ - + + /* + * Example request: + * + * POST URL: http://localhost:8080/DemoService/DemoService.svc/Products + * Header: Content-Type: application/json; odata.metadata=minimal + * Request body: + { + "ID":3, + "Name":"Ergo Screen", + "Description":"17 Optimum Resolution 1024 x 768 @ 85Hz, resolution 1280 x 960" + } + * */ public void createEntity(ODataRequest request, ODataResponse response, UriInfo uriInfo, - ContentType requestFormat, ContentType responseFormat) - throws ODataApplicationException, DeserializerException, SerializerException { - throw new ODataApplicationException("Not supported.", HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ROOT); + ContentType requestFormat, ContentType responseFormat) + throws ODataApplicationException, DeserializerException, SerializerException { + + // 1. Retrieve the entity type from the URI + EdmEntitySet edmEntitySet = Util.getEdmEntitySet(uriInfo); + EdmEntityType edmEntityType = edmEntitySet.getEntityType(); + + // 2. create the data in backend + // 2.1. retrieve the payload from the POST request for the entity to create and deserialize it + InputStream requestInputStream = request.getBody(); + ODataDeserializer deserializer = this.odata.createDeserializer(requestFormat); + DeserializerResult result = deserializer.entity(requestInputStream, edmEntityType); + Entity requestEntity = result.getEntity(); + // 2.2 do the creation in backend, which returns the newly created entity + Entity createdEntity = storage.createEntityData(edmEntitySet, requestEntity); + + // 3. serialize the response (we have to return the created entity) + ContextURL contextUrl = ContextURL.with().entitySet(edmEntitySet).build(); + EntitySerializerOptions options = EntitySerializerOptions.with().contextURL(contextUrl).build(); // expand and select currently not supported + + ODataSerializer serializer = this.odata.createSerializer(responseFormat); + SerializerResult serializedResponse = serializer.entity(serviceMetadata, edmEntityType, createdEntity, options); + + //4. configure the response object + response.setContent(serializedResponse.getContent()); + response.setStatusCode(HttpStatusCode.CREATED.getStatusCode()); + response.setHeader(HttpHeader.CONTENT_TYPE, responseFormat.toContentTypeString()); } + public void updateEntity(ODataRequest request, ODataResponse response, UriInfo uriInfo, - ContentType requestFormat, ContentType responseFormat) - throws ODataApplicationException, DeserializerException, SerializerException { - throw new ODataApplicationException("Not supported.", HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ROOT); + ContentType requestFormat, ContentType responseFormat) + throws ODataApplicationException, DeserializerException, SerializerException { + + // 1. Retrieve the entity set which belongs to the requested entity + List resourcePaths = uriInfo.getUriResourceParts(); + // Note: only in our example we can assume that the first segment is the EntitySet + UriResourceEntitySet uriResourceEntitySet = (UriResourceEntitySet) resourcePaths.get(0); + EdmEntitySet edmEntitySet = uriResourceEntitySet.getEntitySet(); + EdmEntityType edmEntityType = edmEntitySet.getEntityType(); + + // 2. update the data in backend + // 2.1. retrieve the payload from the PUT request for the entity to be updated + InputStream requestInputStream = request.getBody(); + ODataDeserializer deserializer = this.odata.createDeserializer(requestFormat); + DeserializerResult result = deserializer.entity(requestInputStream, edmEntityType); + Entity requestEntity = result.getEntity(); + // 2.2 do the modification in backend + List keyPredicates = uriResourceEntitySet.getKeyPredicates(); + // Note that this updateEntity()-method is invoked for both PUT or PATCH operations + HttpMethod httpMethod = request.getMethod(); + storage.updateEntityData(edmEntitySet, keyPredicates, requestEntity, httpMethod); + + //3. configure the response object + response.setStatusCode(HttpStatusCode.NO_CONTENT.getStatusCode()); } + public void deleteEntity(ODataRequest request, ODataResponse response, UriInfo uriInfo) - throws ODataApplicationException { - throw new ODataApplicationException("Not supported.", HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ROOT); + throws ODataApplicationException { + + // 1. Retrieve the entity set which belongs to the requested entity + List resourcePaths = uriInfo.getUriResourceParts(); + // Note: only in our example we can assume that the first segment is the EntitySet + UriResourceEntitySet uriResourceEntitySet = (UriResourceEntitySet) resourcePaths.get(0); + EdmEntitySet edmEntitySet = uriResourceEntitySet.getEntitySet(); + + // 2. delete the data in backend + List keyPredicates = uriResourceEntitySet.getKeyPredicates(); + storage.deleteEntityData(edmEntitySet, keyPredicates); + + //3. configure the response object + response.setStatusCode(HttpStatusCode.NO_CONTENT.getStatusCode()); } } diff --git a/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/util/Util.java b/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/util/Util.java index f16360fc6..dfc166243 100644 --- a/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/util/Util.java +++ b/samples/tutorials/p0_all/src/main/java/myservice/mynamespace/util/Util.java @@ -33,10 +33,29 @@ import org.apache.olingo.commons.api.edm.EdmProperty; import org.apache.olingo.commons.api.edm.EdmType; import org.apache.olingo.commons.api.http.HttpStatusCode; import org.apache.olingo.server.api.ODataApplicationException; +import org.apache.olingo.server.api.uri.UriInfoResource; import org.apache.olingo.server.api.uri.UriParameter; +import org.apache.olingo.server.api.uri.UriResource; +import org.apache.olingo.server.api.uri.UriResourceEntitySet; public class Util { + + public static EdmEntitySet getEdmEntitySet(UriInfoResource uriInfo) throws ODataApplicationException { + List resourcePaths = uriInfo.getUriResourceParts(); + // To get the entity set we have to interpret all URI segments + if (!(resourcePaths.get(0) instanceof UriResourceEntitySet)) { + // Here we should interpret the whole URI but in this example we do not support navigation so we throw an + // exception + throw new ODataApplicationException("Invalid resource type for first segment.", HttpStatusCode.NOT_IMPLEMENTED + .getStatusCode(), Locale.ENGLISH); + } + + UriResourceEntitySet uriResource = (UriResourceEntitySet) resourcePaths.get(0); + + return uriResource.getEntitySet(); + } + public static Entity findEntity(EdmEntityType edmEntityType, EntityCollection entitySet, List keyParams) { @@ -123,14 +142,14 @@ public class Util { * The "Target" attribute specifies the target EntitySet * Therefore we need the startEntitySet "Categories" in order to retrieve the target EntitySet "Products" */ - public static EdmEntitySet getNavigationTargetEntitySet(EdmEntitySet startEntitySet, + public static EdmEntitySet getNavigationTargetEntitySet(EdmEntitySet startEdmEntitySet, EdmNavigationProperty edmNavigationProperty) throws ODataApplicationException { EdmEntitySet navigationTargetEntitySet = null; String navPropName = edmNavigationProperty.getName(); - EdmBindingTarget edmBindingTarget = startEntitySet.getRelatedBindingTarget(navPropName); + EdmBindingTarget edmBindingTarget = startEdmEntitySet.getRelatedBindingTarget(navPropName); if (edmBindingTarget == null) { throw new ODataApplicationException("Not supported.", HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ROOT); diff --git a/samples/tutorials/p4_navigation/src/main/java/myservice/mynamespace/util/Util.java b/samples/tutorials/p4_navigation/src/main/java/myservice/mynamespace/util/Util.java index 3320760dc..81c0e36cc 100755 --- a/samples/tutorials/p4_navigation/src/main/java/myservice/mynamespace/util/Util.java +++ b/samples/tutorials/p4_navigation/src/main/java/myservice/mynamespace/util/Util.java @@ -125,14 +125,14 @@ public class Util { * The "Target" attribute specifies the target EntitySet * Therefore we need the startEntitySet "Categories" in order to retrieve the target EntitySet "Products" */ - public static EdmEntitySet getNavigationTargetEntitySet(EdmEntitySet startEntitySet, + public static EdmEntitySet getNavigationTargetEntitySet(EdmEntitySet startEdmEntitySet, EdmNavigationProperty edmNavigationProperty) throws ODataApplicationException { EdmEntitySet navigationTargetEntitySet = null; String navPropName = edmNavigationProperty.getName(); - EdmBindingTarget edmBindingTarget = startEntitySet.getRelatedBindingTarget(navPropName); + EdmBindingTarget edmBindingTarget = startEdmEntitySet.getRelatedBindingTarget(navPropName); if (edmBindingTarget == null) { throw new ODataApplicationException("Not supported.", HttpStatusCode.NOT_IMPLEMENTED.getStatusCode(), Locale.ROOT);