diff options
author | ToineSiebelink <toine.siebelink@est.tech> | 2021-02-08 11:36:59 +0000 |
---|---|---|
committer | ToineSiebelink <toine.siebelink@est.tech> | 2021-02-09 12:44:20 +0000 |
commit | 1f64d85f1cd85653a34b8656c67f4cc2565808e7 (patch) | |
tree | 60593135797b572362fecfe77062226720a67576 | |
parent | 4ec225ce071d68c02cbc2388847d416c268bfa40 (diff) |
General groovy test improvements
- Use the power of Groovy (maps and collections)
- Improve data sample readability
- Split out Datanode get scenarios: Separate Leave test from children related tests
Issue-ID: CPS-160
Signed-off-by: ToineSiebelink <toine.siebelink@est.tech>
Change-Id: Ife40749525a931b23091b472680c233f012bc457
3 files changed, 78 insertions, 75 deletions
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 727a16e958..a79b5f440d 100644 --- 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 @@ -25,7 +25,6 @@ import static org.onap.cps.spi.FetchDescendantsOption.OMIT_DESCENDANTS import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post -import com.google.common.collect.ImmutableMap import org.modelmapper.ModelMapper import org.onap.cps.api.CpsAdminService import org.onap.cps.api.CpsDataService @@ -46,8 +45,6 @@ import spock.lang.Shared import spock.lang.Specification import spock.lang.Unroll -import javax.annotation.PostConstruct - @WebMvcTest class DataRestControllerSpec extends Specification { @@ -69,67 +66,83 @@ class DataRestControllerSpec extends Specification { @Value('${rest.api.cps-base-path}') def basePath - String dataNodeEndpoint + def dataNodeEndpoint def dataspaceName = 'my_dataspace' def anchorName = 'my_anchor' @Shared - static DataNode dataNodeNoChildren = new DataNodeBuilder().withXpath("/xpath") - .withLeaves(ImmutableMap.of("leaf", "value")).build() + static DataNode dataNodeWithLeavesNoChildren = new DataNodeBuilder().withXpath('/xpath') + .withLeaves([leaf:'value', leafList:['leaveListElement1','leaveListElement2']]).build() @Shared - static DataNode dataNodeWithChild = new DataNodeBuilder().withXpath("/parent") - .withChildDataNodes(Arrays.asList( - new DataNodeBuilder().withXpath("/parent/child").build() - )).build() + static DataNode dataNodeWithChild = new DataNodeBuilder().withXpath('/parent') + .withChildDataNodes([new DataNodeBuilder().withXpath("/parent/child").build()]).build() - @PostConstruct - def initEndpoints() { + def setup() { dataNodeEndpoint = "$basePath/v1/dataspaces/$dataspaceName/anchors/$anchorName/nodes" } def 'Create a node.'() { - given: 'an endpoint' + given: 'some json to create a data node' def json = 'some json (this is not validated)' - when: 'post is invoked' + when: 'post is invoked with datanode endpoint and json' def response = mvc.perform( post(dataNodeEndpoint).contentType(MediaType.APPLICATION_JSON).content(json) ).andReturn().response - then: 'the java API is called with the correct parameters' - 1 * mockCpsDataService.saveData(dataspaceName, anchorName, json) + then: 'a created response is returned' response.status == HttpStatus.CREATED.value() + then: 'the java API was called with the correct parameters' + 1 * mockCpsDataService.saveData(dataspaceName, anchorName, json) } @Unroll - def 'Get data node with #scenario.'() { - given: 'the service returns data node #scenario' - mockCpsDataService.getDataNode(dataspaceName, anchorName, xpath, fetchDescendantsOption) >> dataNode + def 'Get data node with leaves'() { + given: 'the service returns data node leaves' + def xpath = 'some xPath' + mockCpsDataService.getDataNode(dataspaceName, anchorName, xpath, OMIT_DESCENDANTS) >> dataNodeWithLeavesNoChildren when: 'get request is performed through REST API' def response = mvc.perform( get(dataNodeEndpoint) .param('cps-path', xpath) - .param('include-descendants', includeDescendants) ).andReturn().response - then: 'assert the success response returned' + then: 'a success response is returned' + response.status == HttpStatus.OK.value() + and: 'response contains expected leaf and value' + response.contentAsString.contains('"leaf":"value"') + and: 'response contains expected leaf-list and values' + response.contentAsString.contains('"leafList":["leaveListElement1","leaveListElement2"]') + } + + @Unroll + def 'Get data node with #scenario.'() { + given: 'the service returns data node with #scenario' + def xpath = 'some xPath' + mockCpsDataService.getDataNode(dataspaceName, anchorName, xpath, expectedCpsDataServiceOption) >> dataNode + when: 'get request is performed through REST API' + def response = mvc.perform(get(dataNodeEndpoint) + .param('cps-path', xpath) + .param('include-descendants', urlOption)) + .andReturn().response + then: 'a success response is returned' response.status == HttpStatus.OK.value() - and: 'response contains expected value' - response.contentAsString.contains(checkString) + and: 'the response contains child is #expectChildInResponse' + response.contentAsString.contains('"child"') == expectChildInResponse where: - scenario | dataNode | xpath | includeDescendants | fetchDescendantsOption || checkString - 'no descendants by default' | dataNodeNoChildren | '/xpath' | '' | OMIT_DESCENDANTS || '"leaf"' - 'no descendant explicitly' | dataNodeNoChildren | '/xpath' | 'false' | OMIT_DESCENDANTS || '"leaf"' - 'with descendants' | dataNodeWithChild | '/parent' | 'true' | INCLUDE_ALL_DESCENDANTS || '"child"' + scenario | dataNode | urlOption || expectedCpsDataServiceOption | expectChildInResponse + 'no descendants by default' | dataNodeWithLeavesNoChildren | '' || OMIT_DESCENDANTS | false + 'no descendant explicitly' | dataNodeWithLeavesNoChildren | 'false' || OMIT_DESCENDANTS | false + 'with descendants' | dataNodeWithChild | 'true' || INCLUDE_ALL_DESCENDANTS | true } @Unroll def 'Get data node error scenario: #scenario.'() { - given: 'the service returns throws an exception' + given: 'the service throws an exception' mockCpsDataService.getDataNode(dataspaceName, anchorName, xpath, _) >> { throw exception } when: 'get request is performed through REST API' def response = mvc.perform( get(dataNodeEndpoint).param("cps-path", xpath) ).andReturn().response - then: 'assert the success response returned' + then: 'a success response is returned' response.status == httpStatus.value() where: scenario | xpath | exception || httpStatus @@ -138,4 +151,4 @@ class DataRestControllerSpec extends Specification { 'no data' | '/x-path' | new DataNodeNotFoundException('', '', '') || HttpStatus.NOT_FOUND 'empty path' | '' | new IllegalStateException() || HttpStatus.NOT_IMPLEMENTED } -}
\ No newline at end of file +} diff --git a/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsAdminServiceImplSpec.groovy b/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsAdminServiceImplSpec.groovy index 7c0c6267a7..6631a20136 100755 --- a/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsAdminServiceImplSpec.groovy +++ b/cps-service/src/test/groovy/org/onap/cps/api/impl/CpsAdminServiceImplSpec.groovy @@ -48,17 +48,17 @@ class CpsAdminServiceImplSpec extends Specification { def 'Retrieve all anchors for dataspace.'() { given: 'that anchor is associated with the dataspace' - Collection<Anchor> anchorCollection = Arrays.asList(new Anchor()) - mockCpsAdminPersistenceService.getAnchors('someDataspace') >> { anchorCollection } + def anchors = [new Anchor()] + mockCpsAdminPersistenceService.getAnchors('someDataspace') >> anchors expect: 'the collection provided by persistence service is returned as result' - objectUnderTest.getAnchors('someDataspace') == anchorCollection + objectUnderTest.getAnchors('someDataspace') == anchors } - + def 'Retrieve anchor for dataspace and provided anchor name.'() { given: 'that anchor name is associated with the dataspace' Anchor anchor = new Anchor() - mockCpsAdminPersistenceService.getAnchor('someDataspace','someAnchor') >> anchor + mockCpsAdminPersistenceService.getAnchor('someDataspace','someAnchor') >> anchor expect: 'the anchor provided by persistence service is returned as result' objectUnderTest.getAnchor('someDataspace','someAnchor') == anchor - } -}
\ No newline at end of file + } +} diff --git a/cps-service/src/test/groovy/org/onap/cps/utils/DataMapUtilsSpec.groovy b/cps-service/src/test/groovy/org/onap/cps/utils/DataMapUtilsSpec.groovy index 61cfc37aa1..429ab40b90 100644 --- a/cps-service/src/test/groovy/org/onap/cps/utils/DataMapUtilsSpec.groovy +++ b/cps-service/src/test/groovy/org/onap/cps/utils/DataMapUtilsSpec.groovy @@ -1,6 +1,7 @@ /* * ============LICENSE_START======================================================= * Copyright (C) 2021 Pantheon.tech + * Modifications Copyright (C) 2020 Nordix Foundation * ================================================================================ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -19,56 +20,45 @@ package org.onap.cps.utils -import com.google.common.collect.ImmutableMap -import org.onap.cps.spi.model.DataNode import org.onap.cps.spi.model.DataNodeBuilder import spock.lang.Specification -import static java.util.Arrays.asList - class DataMapUtilsSpec extends Specification { - DataNode dataNode = buildDataNode( - "/parent", - ImmutableMap.<String, Object> of("a", "b", "c", asList("d", "e")), - asList( - buildDataNode( - "/parent/child-list[@name='x']", - ImmutableMap.<String, Object> of("name", "x"), - Collections.emptyList()), - buildDataNode( - "/parent/child-list[@name='y']", - ImmutableMap.<String, Object> of("name", "y"), - Collections.emptyList()), - buildDataNode( - "/parent/child-object", - ImmutableMap.<String, Object> of("m", "n"), - asList( - buildDataNode( - "/parent/child-object/grand-child", - ImmutableMap.<String, Object> of("o", "p"), - Collections.emptyList() - ) - ) - ), - )) + def noChildren = [] + + def dataNode = buildDataNode( + "/parent",[parentLeaf:'parentLeafValue', parentLeafList:['parentLeafListEntry1','parentLeafListEntry2']],[ + buildDataNode('/parent/child-list[@id=1]',[listElementLeaf:'listElement1leafValue'],noChildren), + buildDataNode('/parent/child-list[@id=2]',[listElementLeaf:'listElement2leafValue'],noChildren), + buildDataNode('/parent/child-object',[childLeaf:'childLeafValue'], + [buildDataNode('/parent/child-object/grand-child-object',[grandChildLeaf:'grandChildLeafValue'],noChildren)] + ), + ]) - static DataNode buildDataNode(String xpath, Map<String, Object> leaves, List<DataNode> children) { + static def buildDataNode(xpath, leaves, children) { return new DataNodeBuilder().withXpath(xpath).withLeaves(leaves).withChildDataNodes(children).build() } def 'Data node structure conversion to map.'() { - when: 'data node structure converted to map' - def result = DataMapUtils.toDataMap(dataNode) + when: 'data node structure is converted to a map' + Map result = DataMapUtils.toDataMap(dataNode) + then: 'root node leaves are top level elements' - assert result["a"] == "b" - assert ((Collection) result["c"]).containsAll("d", "e") + result.parentLeaf == 'parentLeafValue' + result.parentLeafList == ['parentLeafListEntry1','parentLeafListEntry2'] + and: 'leaves of child list element are listed as structures under common identifier' - assert ((Collection) result["child-list"]).size() == 2 - assert ((Collection) result["child-list"]).containsAll(["name": "x"], ["name": "y"]) - and: 'leaves for child and grand-child elements are populated under their node identifiers' - assert result["child-object"]["m"] == "n" - assert result["child-object"]["grand-child"]["o"] == "p" + result.'child-list'.collect().containsAll(['listElementLeaf': 'listElement1leafValue'], + ['listElementLeaf': 'listElement2leafValue']) + + and: 'leaves for child element is populated under its node identifier' + Map childObjectData = result.'child-object' + childObjectData.childLeaf == 'childLeafValue' + + and: 'leaves for grandchild element is populated under its node identifier' + Map grandChildObjectData = childObjectData.'grand-child-object' + grandChildObjectData.grandChildLeaf == 'grandChildLeafValue' } } |