diff options
Diffstat (limited to 'cps-rest')
4 files changed, 50 insertions, 12 deletions
diff --git a/cps-rest/docs/openapi/components.yml b/cps-rest/docs/openapi/components.yml index 40f0e170ff..728295fd31 100644 --- a/cps-rest/docs/openapi/components.yml +++ b/cps-rest/docs/openapi/components.yml @@ -293,7 +293,9 @@ components: description: Content type in header schema: type: string - example: 'application/json' + enum: + - application/json + - application/xml required: true descendantsInQuery: name: descendants diff --git a/cps-rest/docs/openapi/cpsDataV2.yml b/cps-rest/docs/openapi/cpsDataV2.yml index d5a8ef3891..999c5b2c19 100644 --- a/cps-rest/docs/openapi/cpsDataV2.yml +++ b/cps-rest/docs/openapi/cpsDataV2.yml @@ -28,6 +28,7 @@ nodeByDataspaceAndAnchor: - $ref: 'components.yml#/components/parameters/anchorNameInPath' - $ref: 'components.yml#/components/parameters/xpathInQuery' - $ref: 'components.yml#/components/parameters/descendantsInQuery' + - $ref: 'components.yml#/components/parameters/contentTypeInHeader' responses: '200': description: OK @@ -38,6 +39,14 @@ nodeByDataspaceAndAnchor: examples: dataSample: $ref: 'components.yml#/components/examples/dataSample' + application/xml: + schema: + type: object + xml: + name: stores + examples: + dataSample: + $ref: 'components.yml#/components/examples/dataSampleXml' '400': $ref: 'components.yml#/components/responses/BadRequest' '403': diff --git a/cps-rest/src/main/java/org/onap/cps/rest/controller/DataRestController.java b/cps-rest/src/main/java/org/onap/cps/rest/controller/DataRestController.java index 7390afcf98..6d22581845 100755 --- a/cps-rest/src/main/java/org/onap/cps/rest/controller/DataRestController.java +++ b/cps-rest/src/main/java/org/onap/cps/rest/controller/DataRestController.java @@ -48,8 +48,8 @@ import org.onap.cps.utils.ContentType; import org.onap.cps.utils.DataMapUtils; import org.onap.cps.utils.JsonObjectMapper; import org.onap.cps.utils.PrefixResolver; +import org.onap.cps.utils.XmlFileUtils; import org.springframework.http.HttpStatus; -import org.springframework.http.MediaType; import org.springframework.http.ResponseEntity; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; @@ -75,7 +75,7 @@ public class DataRestController implements CpsDataApi { final String contentTypeInHeader, final String nodeData, final String parentNodeXpath, final Boolean dryRunEnabled, final String observedTimestamp) { - final ContentType contentType = getContentTypeFromHeader(contentTypeInHeader); + final ContentType contentType = ContentType.fromString(contentTypeInHeader); if (Boolean.TRUE.equals(dryRunEnabled)) { cpsDataService.validateData(dataspaceName, anchorName, parentNodeXpath, nodeData, contentType); return ResponseEntity.ok().build(); @@ -105,7 +105,7 @@ public class DataRestController implements CpsDataApi { final String anchorName, final String parentNodeXpath, final String contentTypeInHeader, final String nodeData, final String observedTimestamp) { - final ContentType contentType = getContentTypeFromHeader(contentTypeInHeader); + final ContentType contentType = ContentType.fromString(contentTypeInHeader); cpsDataService.saveListElements(dataspaceName, anchorName, parentNodeXpath, nodeData, toOffsetDateTime(observedTimestamp), contentType); return new ResponseEntity<>(HttpStatus.CREATED); @@ -129,8 +129,9 @@ public class DataRestController implements CpsDataApi { @Timed(value = "cps.data.controller.datanode.get.v2", description = "Time taken to get data node") public ResponseEntity<Object> getNodeByDataspaceAndAnchorV2(final String dataspaceName, final String anchorName, - final String xpath, + final String contentTypeInHeader, final String xpath, final String fetchDescendantsOptionAsString) { + final ContentType contentType = ContentType.fromString(contentTypeInHeader); final FetchDescendantsOption fetchDescendantsOption = FetchDescendantsOption.getFetchDescendantsOption(fetchDescendantsOptionAsString); final Collection<DataNode> dataNodes = cpsDataService.getDataNodes(dataspaceName, anchorName, xpath, @@ -142,7 +143,7 @@ public class DataRestController implements CpsDataApi { final Map<String, Object> dataMap = DataMapUtils.toDataMapWithIdentifier(dataNode, prefix); dataMaps.add(dataMap); } - return new ResponseEntity<>(jsonObjectMapper.asJsonString(dataMaps), HttpStatus.OK); + return buildResponseEntity(dataMaps, contentType); } @Override @@ -150,7 +151,7 @@ public class DataRestController implements CpsDataApi { final String anchorName, final String contentTypeInHeader, final String nodeData, final String parentNodeXpath, final String observedTimestamp) { - final ContentType contentType = getContentTypeFromHeader(contentTypeInHeader); + final ContentType contentType = ContentType.fromString(contentTypeInHeader); cpsDataService.updateNodeLeaves(dataspaceName, anchorName, parentNodeXpath, nodeData, toOffsetDateTime(observedTimestamp), contentType); return new ResponseEntity<>(HttpStatus.OK); @@ -161,7 +162,7 @@ public class DataRestController implements CpsDataApi { final String anchorName, final String contentTypeInHeader, final String nodeData, final String parentNodeXpath, final String observedTimestamp) { - final ContentType contentType = getContentTypeFromHeader(contentTypeInHeader); + final ContentType contentType = ContentType.fromString(contentTypeInHeader); cpsDataService.updateDataNodeAndDescendants(dataspaceName, anchorName, parentNodeXpath, nodeData, toOffsetDateTime(observedTimestamp), contentType); return new ResponseEntity<>(HttpStatus.OK); @@ -219,12 +220,19 @@ public class DataRestController implements CpsDataApi { final List<DeltaReport> deltaBetweenAnchors = cpsDataService.getDeltaByDataspaceAndAnchors(dataspaceName, sourceAnchorName, - targetAnchorName, xpath, fetchDescendantsOption); + targetAnchorName, xpath, fetchDescendantsOption); return new ResponseEntity<>(jsonObjectMapper.asJsonString(deltaBetweenAnchors), HttpStatus.OK); } - private static ContentType getContentTypeFromHeader(final String contentTypeInHeader) { - return contentTypeInHeader.contains(MediaType.APPLICATION_XML_VALUE) ? ContentType.XML : ContentType.JSON; + ResponseEntity<Object> buildResponseEntity(final List<Map<String, Object>> dataMaps, + final ContentType contentType) { + final String responseData; + if (contentType == ContentType.XML) { + responseData = XmlFileUtils.convertDataMapsToXml(dataMaps); + } else { + responseData = jsonObjectMapper.asJsonString(dataMaps); + } + return new ResponseEntity<>(responseData, HttpStatus.OK); } private static boolean isRootXpath(final String xpath) { diff --git a/cps-rest/src/test/groovy/org/onap/cps/rest/controller/DataRestControllerSpec.groovy b/cps-rest/src/test/groovy/org/onap/cps/rest/controller/DataRestControllerSpec.groovy index 705c2fee91..27738b07c6 100755 --- a/cps-rest/src/test/groovy/org/onap/cps/rest/controller/DataRestControllerSpec.groovy +++ b/cps-rest/src/test/groovy/org/onap/cps/rest/controller/DataRestControllerSpec.groovy @@ -314,7 +314,9 @@ class DataRestControllerSpec extends Specification { mockCpsDataService.getDataNodes(dataspaceName, anchorName, xpath, OMIT_DESCENDANTS) >> [dataNodeWithLeavesNoChildren, dataNodeWithLeavesNoChildren2] when: 'V2 of get request is performed through REST API' def response = - mvc.perform(get(endpoint).param('xpath', xpath)) + mvc.perform(get(endpoint) + .contentType(MediaType.APPLICATION_JSON) + .param('xpath', xpath)) .andReturn().response then: 'a success response is returned' response.status == HttpStatus.OK.value() @@ -326,6 +328,21 @@ class DataRestControllerSpec extends Specification { assert numberOfDataTrees == 2 } + def 'Get all the data trees as XML with root node xPath using V2'() { + given: 'the service returns all data node leaves' + def xpath = '/' + def endpoint = "$dataNodeBaseEndpointV2/anchors/$anchorName/node" + mockCpsDataService.getDataNodes(dataspaceName, anchorName, xpath, OMIT_DESCENDANTS) >> [dataNodeWithLeavesNoChildren] + when: 'V2 of get request is performed through REST API with XML content type' + def response = + mvc.perform(get(endpoint).contentType(MediaType.APPLICATION_XML).param('xpath', xpath)) + .andReturn().response + then: 'a success response is returned' + response.status == HttpStatus.OK.value() + and: 'the response contains the datanode in XML format' + response.getContentAsString() == '<parent-1><leaf>value</leaf><leafList>leaveListElement1</leafList><leafList>leaveListElement2</leafList></parent-1>' + } + def 'Get data node with #scenario using V2.'() { given: 'the service returns data nodes with #scenario' def xpath = 'some xPath' @@ -335,6 +352,7 @@ class DataRestControllerSpec extends Specification { def response = mvc.perform( get(endpoint) + .contentType(MediaType.APPLICATION_JSON) .param('xpath', xpath) .param('descendants', includeDescendantsOption)) .andReturn().response @@ -361,6 +379,7 @@ class DataRestControllerSpec extends Specification { def response = mvc.perform( get(endpoint) + .contentType(MediaType.APPLICATION_JSON) .param('xpath', xpath) .param('descendants', '2')) .andReturn().response |