From 5e1e26053d13c9e693762c69b43eff3093c34d29 Mon Sep 17 00:00:00 2001 From: ottero Date: Tue, 28 May 2019 09:25:45 +0000 Subject: Returning null for unresolved variables When Blueprints Processor was not able to evaluate a variable, it would set its value to null. The expected behaviour would be to set the value to the default repres- entation in the formal notation as defined by Apache Velocity, which is a dollar followed by the name of the variable between curly braces. For example, if the value of the variable pnf-id could not be evaluated in runtime, its value would be defined as the string "${pnf-id}". The problem happened during evaluation of the variables that would be later sent to the template-meshing code for processing. The fix was to add a check before the value was assigned to the varia- ble; if the was not null, the assignment will happen normally. Otherwi- se, if the evaluation resolves to null, the variable receives the defa- ult value (string "${}"). Besides the tests that were put in place to test the code changed for this fix, two tests were added to the existing test case of the templa- te meshing code, to act as regression test. Change-Id: I635afb1eba4c0d45b821811f0119fa6c87ea9542 Issue-ID: CCSDK-1358 Signed-off-by: ottero --- .../resolution/utils/ResourceAssignmentUtils.kt | 12 +++- .../utils/ResourceAssignmentUtilsTest.kt | 79 ++++++++++++++++++++++ .../service/BluePrintVelocityTemplateService.kt | 1 - .../core/service/BluePrintTemplateServiceTest.kt | 35 ++++++++++ .../templates/default-variable-value-data.json | 3 + .../default-variable-value-velocity-template.vtl | 2 + 6 files changed, 130 insertions(+), 2 deletions(-) create mode 100644 ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/utils/ResourceAssignmentUtilsTest.kt create mode 100755 ms/controllerblueprints/modules/blueprint-core/src/test/resources/templates/default-variable-value-data.json create mode 100755 ms/controllerblueprints/modules/blueprint-core/src/test/resources/templates/default-variable-value-velocity-template.vtl diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/utils/ResourceAssignmentUtils.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/utils/ResourceAssignmentUtils.kt index 656e86169..1a943d110 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/utils/ResourceAssignmentUtils.kt +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/utils/ResourceAssignmentUtils.kt @@ -21,6 +21,7 @@ import com.fasterxml.jackson.databind.JsonNode import com.fasterxml.jackson.databind.ObjectMapper import com.fasterxml.jackson.databind.node.NullNode import com.fasterxml.jackson.databind.node.ObjectNode +import com.fasterxml.jackson.databind.node.TextNode import org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.ResourceAssignmentRuntimeService import org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.ResourceResolutionConstants import org.onap.ccsdk.cds.controllerblueprints.core.* @@ -122,7 +123,7 @@ class ResourceAssignmentUtils { if (isNotEmpty(it.name) && it.property != null) { val rName = it.name val type = nullToEmpty(it.property?.type).toLowerCase() - val value = it.property?.value + val value = useDefaultValueIfNull(it, rName) logger.info("Generating Resource name ($rName), type ($type), value ($value)") root.set(rName, value) } @@ -136,6 +137,15 @@ class ResourceAssignmentUtils { return result } + private fun useDefaultValueIfNull(resourceAssignment: ResourceAssignment, resourceAssignmentName: String): JsonNode { + if (resourceAssignment.property?.value == null) { + val defaultValue = "\${$resourceAssignmentName}" + return TextNode(defaultValue) + } else { + return resourceAssignment.property!!.value!! + } + } + fun transformToRARuntimeService(blueprintRuntimeService: BluePrintRuntimeService<*>, templateArtifactName: String): ResourceAssignmentRuntimeService { diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/utils/ResourceAssignmentUtilsTest.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/utils/ResourceAssignmentUtilsTest.kt new file mode 100644 index 000000000..9b87c12eb --- /dev/null +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/resource/resolution/utils/ResourceAssignmentUtilsTest.kt @@ -0,0 +1,79 @@ +/*- + * ============LICENSE_START======================================================= + * Copyright (C) 2019 Nordix Foundation. + * ================================================================================ + * Licensed 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. + * + * SPDX-License-Identifier: Apache-2.0 + * ============LICENSE_END========================================================= + */ + + +package org.onap.ccsdk.cds.blueprintsprocessor.functions.resource.resolution.utils + +import com.fasterxml.jackson.databind.node.TextNode +import org.junit.Test +import org.onap.ccsdk.cds.controllerblueprints.core.data.PropertyDefinition +import org.onap.ccsdk.cds.controllerblueprints.resource.dict.ResourceAssignment +import kotlin.test.assertEquals + +class ResourceAssignmentUtilsTest { + + @Test + fun `generateResourceDataForAssignments - positive test`() { + //given a valid resource assignment + val validResourceAssignment = createResourceAssignmentForTest("valid_value") + + //and a list containing that resource assignment + val resourceAssignmentList = listOf(validResourceAssignment) + + //when the values of the resources are evaluated + val outcome = ResourceAssignmentUtils.generateResourceDataForAssignments(resourceAssignmentList) + + //then the assignment should produce a valid result + val expected = "{\n" + " \"pnf-id\" : \"valid_value\"\n" + "}" + assertEquals(expected, outcome, "unexpected outcome generated") + + } + + @Test + fun `generateResourceDataForAssignments - resource without value is not resolved as null`() { + //given a valid resource assignment + val resourceAssignmentWithNullValue = createResourceAssignmentForTest(null) + + //and a list containing that resource assignment + val resourceAssignmentList = listOf(resourceAssignmentWithNullValue) + + //when the values of the resources are evaluated + val outcome = ResourceAssignmentUtils.generateResourceDataForAssignments(resourceAssignmentList) + + //then the assignment should produce a valid result + val expected = "{\n" + " \"pnf-id\" : \"\${pnf-id}\"\n" + "}" + assertEquals(expected, outcome, "unexpected outcome generated") + + } + + private fun createResourceAssignmentForTest(resourceValue: String?): ResourceAssignment { + val valueForTest = if (resourceValue == null) null else TextNode(resourceValue) + val resourceAssignmentForTest = ResourceAssignment().apply { + name = "pnf-id" + dictionaryName = "pnf-id" + dictionarySource = "input" + property = PropertyDefinition().apply { + type = "string" + value = valueForTest + } + } + return resourceAssignmentForTest + } +} \ No newline at end of file diff --git a/ms/controllerblueprints/modules/blueprint-core/src/main/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/service/BluePrintVelocityTemplateService.kt b/ms/controllerblueprints/modules/blueprint-core/src/main/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/service/BluePrintVelocityTemplateService.kt index 496182ee7..43e6d221f 100644 --- a/ms/controllerblueprints/modules/blueprint-core/src/main/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/service/BluePrintVelocityTemplateService.kt +++ b/ms/controllerblueprints/modules/blueprint-core/src/main/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/service/BluePrintVelocityTemplateService.kt @@ -82,4 +82,3 @@ object BluePrintVelocityTemplateService { } } - diff --git a/ms/controllerblueprints/modules/blueprint-core/src/test/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/service/BluePrintTemplateServiceTest.kt b/ms/controllerblueprints/modules/blueprint-core/src/test/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/service/BluePrintTemplateServiceTest.kt index 02505acad..6f961c8ed 100644 --- a/ms/controllerblueprints/modules/blueprint-core/src/test/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/service/BluePrintTemplateServiceTest.kt +++ b/ms/controllerblueprints/modules/blueprint-core/src/test/kotlin/org/onap/ccsdk/cds/controllerblueprints/core/service/BluePrintTemplateServiceTest.kt @@ -26,6 +26,7 @@ import org.onap.ccsdk.cds.controllerblueprints.core.utils.BluePrintMetadataUtils import org.onap.ccsdk.cds.controllerblueprints.core.utils.JacksonUtils import org.springframework.test.context.junit4.SpringRunner import kotlin.test.BeforeTest +import kotlin.test.assertEquals import kotlin.test.assertNotNull @RunWith(SpringRunner::class) @@ -97,5 +98,39 @@ class BluePrintTemplateServiceTest { assertNotNull(content, "failed to generate content for velocity template") } } + + @Test + fun `no value variable should evaluate to default value - standalone template mesh test`() { + runBlocking { + val template = JacksonUtils.getClassPathFileContent("templates/default-variable-value-velocity-template.vtl") + val json = JacksonUtils.getClassPathFileContent("templates/default-variable-value-data.json") + + val content = BluePrintVelocityTemplateService.generateContent(template, json) + //first line represents a variable whose value was successfully retrieved, second line contains a variable + // whose value could not be evaluated + val expected = "sample-hostname\n\${node0_backup_router_address}" + assertEquals(expected, content, "No value variable should use default value") + } + } + + @Test + fun `no value variable should evaluate to default value - blueprint processing test`() { + runBlocking { + val bluePrintTemplateService = BluePrintTemplateService() + + val templateFile = "templates/default-variable-value-velocity-template.vtl" + val jsonFile = "templates/default-variable-value-data.json" + + val content = bluePrintTemplateService.generateContentFromFiles(templateFile, + BluePrintConstants.ARTIFACT_VELOCITY_TYPE_NAME, jsonFile, false, mutableMapOf()) + + //first line represents a variable whose value was successfully retrieved, second line contains a variable + // whose value could not be evaluated + val expected = "sample-hostname\n\${node0_backup_router_address}" + assertEquals(expected, content, "No value variable should use default value") + } + + } + } diff --git a/ms/controllerblueprints/modules/blueprint-core/src/test/resources/templates/default-variable-value-data.json b/ms/controllerblueprints/modules/blueprint-core/src/test/resources/templates/default-variable-value-data.json new file mode 100755 index 000000000..940ca8d73 --- /dev/null +++ b/ms/controllerblueprints/modules/blueprint-core/src/test/resources/templates/default-variable-value-data.json @@ -0,0 +1,3 @@ +{ + "node0_hostname": "sample-hostname" +} diff --git a/ms/controllerblueprints/modules/blueprint-core/src/test/resources/templates/default-variable-value-velocity-template.vtl b/ms/controllerblueprints/modules/blueprint-core/src/test/resources/templates/default-variable-value-velocity-template.vtl new file mode 100755 index 000000000..ce2458e2e --- /dev/null +++ b/ms/controllerblueprints/modules/blueprint-core/src/test/resources/templates/default-variable-value-velocity-template.vtl @@ -0,0 +1,2 @@ +$node0_hostname +${node0_backup_router_address} \ No newline at end of file -- cgit 1.2.3-korg