From 636bf03c2a813c889921ff9a223f23e623532e69 Mon Sep 17 00:00:00 2001 From: "Singal, Kapil (ks220y)" Date: Thu, 10 Jan 2019 12:50:06 -0500 Subject: [PATCH] Resource Resoulution Service Implement Input Resource Resolution Processor Service along with Resource Resolution Utilities Change-Id: Ibb4899e415f4b79cd6cd1b190b0f4969b09c3fe4 Issue-ID: CCSDK-936 Signed-off-by: Singal, Kapil (ks220y) --- .../python/executor/utils/PythonExecutorUtils.kt | 5 +- .../executor/utils/PythonExecutorUtilsTest.kt | 2 +- .../requests/sample-activate-request.json | 31 +++++ .../resolution/ResourceAssignmentRuntimeService.kt | 58 ++++++++++ .../processor/InputResourceAssignmentProcessor.kt | 17 +++ .../resolution/utils/ResourceResolutionUtils.kt | 127 ++++++++++++++++++++- .../resolution/ResourceResolutionServiceTest.kt | 9 ++ .../sample-resourceresolution-request.json | 5 +- 8 files changed, 249 insertions(+), 5 deletions(-) create mode 100644 ms/blueprintsprocessor/functions/python-executor/src/test/resources/requests/sample-activate-request.json create mode 100644 ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/ResourceAssignmentRuntimeService.kt diff --git a/ms/blueprintsprocessor/functions/python-executor/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/python/executor/utils/PythonExecutorUtils.kt b/ms/blueprintsprocessor/functions/python-executor/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/python/executor/utils/PythonExecutorUtils.kt index 66c919d4d..341ede585 100644 --- a/ms/blueprintsprocessor/functions/python-executor/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/python/executor/utils/PythonExecutorUtils.kt +++ b/ms/blueprintsprocessor/functions/python-executor/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/python/executor/utils/PythonExecutorUtils.kt @@ -20,6 +20,7 @@ import org.onap.ccsdk.apps.blueprintsprocessor.services.execution.AbstractCompon import org.python.core.PyObject import org.python.util.PythonInterpreter import org.slf4j.LoggerFactory +import java.io.File import java.util.* class PythonExecutorUtils { @@ -61,9 +62,9 @@ class PythonExecutorUtils { sb.append(System.getProperty("java.class.path")) for (p in pythonPath) { - sb.append(":").append(p) + sb.append(File.pathSeparator).append(p) } - log.debug("Paths : $sb") + log.debug("Python Paths : $sb") props["python.import.site"] = "true" props.setProperty("python.path", sb.toString()) diff --git a/ms/blueprintsprocessor/functions/python-executor/src/test/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/python/executor/utils/PythonExecutorUtilsTest.kt b/ms/blueprintsprocessor/functions/python-executor/src/test/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/python/executor/utils/PythonExecutorUtilsTest.kt index 431c6b820..c4fd54673 100644 --- a/ms/blueprintsprocessor/functions/python-executor/src/test/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/python/executor/utils/PythonExecutorUtilsTest.kt +++ b/ms/blueprintsprocessor/functions/python-executor/src/test/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/python/executor/utils/PythonExecutorUtilsTest.kt @@ -30,7 +30,7 @@ class PythonExecutorUtilsTest { @Test fun testGetPythonComponent() { - val pythonPath: MutableList = arrayListOf() + val pythonPath: MutableList = mutableListOf() pythonPath.add("./../../../../components/scripts/python/ccsdk_blueprints") val properties: MutableMap = hashMapOf() diff --git a/ms/blueprintsprocessor/functions/python-executor/src/test/resources/requests/sample-activate-request.json b/ms/blueprintsprocessor/functions/python-executor/src/test/resources/requests/sample-activate-request.json new file mode 100644 index 000000000..7142f0457 --- /dev/null +++ b/ms/blueprintsprocessor/functions/python-executor/src/test/resources/requests/sample-activate-request.json @@ -0,0 +1,31 @@ +{ + "actionIdentifiers": { + "actionName": "activate", + "blueprintName": "baseconfiguration", + "blueprintVersion": "1.0.0", + "mode": "sync" + }, + "commonHeader": { + "flags": { + "force": true, + "ttl": 3600 + }, + "originatorId": "sdnc", + "requestId": "123456-1000", + "subRequestId": "sub-123456-1000", + "timestamp": "2012-04-23T18:25:43.511Z" + }, + "payload": { + "resource-assignment-request": { + "resource-assignment-properties": { + "request-id": "1234", + "service-instance-id": "siid_1234", + "vnf-id": "vnf_1234", + "action-name": "assign-activate", + "scope-type": "vnf-type", + "hostname": "localhost", + "vnf_name": "temp_vnf" + } + } + } +} diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/ResourceAssignmentRuntimeService.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/ResourceAssignmentRuntimeService.kt new file mode 100644 index 000000000..9d6f4a6b5 --- /dev/null +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/ResourceAssignmentRuntimeService.kt @@ -0,0 +1,58 @@ +package org.onap.ccsdk.apps.blueprintsprocessor.functions.resource.resolution + +import com.fasterxml.jackson.databind.JsonNode +import org.onap.ccsdk.apps.controllerblueprints.core.BluePrintProcessorException +import org.onap.ccsdk.apps.controllerblueprints.core.service.BluePrintContext +import org.onap.ccsdk.apps.controllerblueprints.core.service.DefaultBluePrintRuntimeService + +class ResourceAssignmentRuntimeService(private var id: String, private var bluePrintContext: BluePrintContext) + : DefaultBluePrintRuntimeService(id, bluePrintContext){ + + private var resourceResolutionStore: MutableMap = hashMapOf() + + override fun getExecutionContext(): MutableMap { + return resourceResolutionStore + } + + @Suppress("UNCHECKED_CAST") + override fun setExecutionContext(executionContext: MutableMap) { + this.resourceResolutionStore = executionContext + } + + override fun put(key: String, value: JsonNode) { + resourceResolutionStore[key] = value + } + + override fun get(key: String): JsonNode { + return resourceResolutionStore[key] ?: throw BluePrintProcessorException("failed to get execution property($key)") + } + + override fun check(key: String): Boolean { + return resourceResolutionStore.containsKey(key) + } + + override fun cleanRuntime() { + resourceResolutionStore.clear() + } + + private fun getJsonNode(key: String): JsonNode { + return get(key) + } + + override fun getAsString(key: String): String? { + return get(key).asText() + } + + override fun getAsBoolean(key: String): Boolean? { + return get(key).asBoolean() + } + + override fun getAsInt(key: String): Int? { + return get(key).asInt() + } + + override fun getAsDouble(key: String): Double? { + return get(key).asDouble() + } + +} diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/processor/InputResourceAssignmentProcessor.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/processor/InputResourceAssignmentProcessor.kt index 9d476008f..ccf3aee1f 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/processor/InputResourceAssignmentProcessor.kt +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/processor/InputResourceAssignmentProcessor.kt @@ -17,8 +17,11 @@ package org.onap.ccsdk.apps.blueprintsprocessor.functions.resource.resolution.processor +import org.onap.ccsdk.apps.blueprintsprocessor.functions.resource.resolution.utils.ResourceResolutionUtils +import org.onap.ccsdk.apps.controllerblueprints.core.* import org.onap.ccsdk.apps.controllerblueprints.resource.dict.ResourceAssignment import org.springframework.stereotype.Service +import com.fasterxml.jackson.databind.node.NullNode /** * InputResourceAssignmentProcessor @@ -33,6 +36,20 @@ open class InputResourceAssignmentProcessor : ResourceAssignmentProcessor() { } override fun process(executionRequest: ResourceAssignment) { + try { + if (checkNotEmpty(executionRequest.name)) { + val value = bluePrintRuntimeService!!.getInputValue(executionRequest.name) + // if value is null don't call setResourceDataValue to populate the value + if (value != null && value !is NullNode) { + ResourceResolutionUtils.setResourceDataValue(executionRequest, value) + } + } + // Check the value has populated for mandatory case + ResourceResolutionUtils.assertTemplateKeyValueNotNull(executionRequest) + } catch (e: Exception) { + ResourceResolutionUtils.setFailedResourceDataValue(executionRequest, e.message) + throw BluePrintProcessorException("Failed in template key ($executionRequest) assignments with : (${e.message})", e) + } } override fun recover(runtimeException: RuntimeException, executionRequest: ResourceAssignment) { diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/utils/ResourceResolutionUtils.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/utils/ResourceResolutionUtils.kt index 6bcd21ba0..7c590883f 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/utils/ResourceResolutionUtils.kt +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/main/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/utils/ResourceResolutionUtils.kt @@ -16,17 +16,142 @@ package org.onap.ccsdk.apps.blueprintsprocessor.functions.resource.resolution.utils +import java.util.Date +import org.apache.commons.lang3.StringUtils +import com.att.eelf.configuration.EELFLogger +import com.att.eelf.configuration.EELFManager import com.fasterxml.jackson.databind.JsonNode -import org.onap.ccsdk.apps.controllerblueprints.core.BluePrintProcessorException +import com.fasterxml.jackson.databind.ObjectMapper +import com.fasterxml.jackson.databind.node.NullNode +import com.fasterxml.jackson.databind.node.ObjectNode +import org.onap.ccsdk.apps.controllerblueprints.core.* import org.onap.ccsdk.apps.controllerblueprints.core.utils.JacksonUtils +import org.onap.ccsdk.apps.controllerblueprints.resource.dict.ResourceAssignment class ResourceResolutionUtils { companion object { + private val logger: EELFLogger = EELFManager.getInstance().getLogger(ResourceResolutionUtils::class.toString()) + + @Synchronized + @Throws(BluePrintProcessorException::class) + fun setResourceDataValue(resourceAssignment: ResourceAssignment, value: Any?) { + + val resourceProp = checkNotNull(resourceAssignment.property) { "Failed in setting resource value for resource mapping $resourceAssignment" } + checkNotEmptyNThrow(resourceAssignment.name, "Failed in setting resource value for resource mapping $resourceAssignment") + + if (checkNotEmpty(resourceAssignment.dictionaryName)) { + resourceAssignment.dictionaryName = resourceAssignment.name + logger.warn("Missing dictionary key, setting with template key (${resourceAssignment.name}) as dictionary key (${resourceAssignment.dictionaryName})") + } + + try { + if (checkNotEmpty(resourceProp.type)) { + val convertedValue = convertResourceValue(resourceProp.type, value) + logger.info("Setting Resource Value ($convertedValue) for Resource Name (${resourceAssignment.dictionaryName}) of type (${resourceProp.type})") + resourceProp.value = convertedValue + resourceAssignment.updatedDate = Date() + resourceAssignment.updatedBy = BluePrintConstants.USER_SYSTEM + resourceAssignment.status = BluePrintConstants.STATUS_SUCCESS + } + } catch (e: Exception) { + throw BluePrintProcessorException("Failed in setting value for template key (%s) and " + + "dictionary key (${resourceAssignment.name}) of type (${resourceProp.type}) with error message (${e.message})", e) + } + } + + private fun convertResourceValue(type: String, value: Any?): JsonNode? { + var convertedValue: JsonNode? + + if (value == null || value is NullNode) { + logger.info("Returning {} value from convertResourceValue", value) + return null + } else if (BluePrintTypes.validPrimitiveTypes().contains(type) && value is String) { + convertedValue = JacksonUtils.convertPrimitiveResourceValue(type, value) + } else { + // Case where Resource is non-primitive type + if (value is String) { + convertedValue = JacksonUtils.jsonNode(value) + } else { + convertedValue = JacksonUtils.getJsonNode(value) + } + } + return convertedValue + } + + @Synchronized + fun setFailedResourceDataValue(resourceAssignment: ResourceAssignment, message: String?) { + if (checkNotEmpty(resourceAssignment.name)) { + resourceAssignment.updatedDate = Date() + resourceAssignment.updatedBy = BluePrintConstants.USER_SYSTEM + resourceAssignment.status = BluePrintConstants.STATUS_FAILURE + resourceAssignment.message = message + } + } + + @Synchronized + @Throws(BluePrintProcessorException::class) + fun assertTemplateKeyValueNotNull(resourceAssignment: ResourceAssignment) { + val resourceProp = checkNotNull(resourceAssignment.property) { "Failed to populate mandatory resource resource mapping $resourceAssignment" } + if (resourceProp.required != null && resourceProp.required!! && (resourceProp.value == null || resourceProp.value !is NullNode)) { + logger.error("failed to populate mandatory resource mapping ($resourceAssignment)") + throw BluePrintProcessorException("failed to populate mandatory resource mapping ($resourceAssignment)") + } + } + + @Synchronized + @Throws(BluePrintProcessorException::class) + fun generateResourceDataForAssignments(assignments: List): String { + var result = "{}" + try { + val mapper = ObjectMapper() + val root = mapper.readTree(result) + + assignments.forEach { + if (checkNotEmpty(it.name) && it.property != null) { + + val type = it.property?.type + val value = it.property?.value + logger.info("Generating Resource name ({}), type ({}), value ({})", it.name, type, + value) + if (value == null) { + (root as ObjectNode).set(it.name, null) + } else if (value is JsonNode) { + (root as ObjectNode).put(it.name, value as JsonNode) + } else if (BluePrintConstants.DATA_TYPE_STRING.equals(type, ignoreCase = true)) { + (root as ObjectNode).put(it.name, value as String) + } else if (BluePrintConstants.DATA_TYPE_BOOLEAN.equals(type, ignoreCase = true)) { + (root as ObjectNode).put(it.name, value as Boolean) + } else if (BluePrintConstants.DATA_TYPE_INTEGER.equals(type, ignoreCase = true)) { + (root as ObjectNode).put(it.name, value as Int) + } else if (BluePrintConstants.DATA_TYPE_FLOAT.equals(type, ignoreCase = true)) { + (root as ObjectNode).put(it.name, value as Float) + } else if (BluePrintConstants.DATA_TYPE_TIMESTAMP.equals(type, ignoreCase = true)) { + (root as ObjectNode).put(it.name, value as String) + } else { + val jsonNode = JacksonUtils.getJsonNode(value) + if (jsonNode != null) { + (root as ObjectNode).put(it.name, jsonNode) + } else { + (root as ObjectNode).set(it.name, null) + } + } + } + } + result = mapper.writerWithDefaultPrettyPrinter().writeValueAsString(root) + logger.info("Generated Resource Param Data ({})", result) + } catch (e: Exception) { + throw BluePrintProcessorException("kapil is failing with $e.message", e) + } + + return result + } + fun transformResourceSource(properties: MutableMap, classType: Class): T { val content = JacksonUtils.getJson(properties) return JacksonUtils.readValue(content, classType) ?: throw BluePrintProcessorException("failed to transform content($content) to type($classType)") } + } } \ No newline at end of file diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/ResourceResolutionServiceTest.kt b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/ResourceResolutionServiceTest.kt index 7f41ba12f..46ccb9745 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/ResourceResolutionServiceTest.kt +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/test/kotlin/org/onap/ccsdk/apps/blueprintsprocessor/functions/resource/resolution/ResourceResolutionServiceTest.kt @@ -19,8 +19,11 @@ package org.onap.ccsdk.apps.blueprintsprocessor.functions.resource.resolution import org.junit.Assert import org.junit.Test import org.junit.runner.RunWith +import org.onap.ccsdk.apps.blueprintsprocessor.core.api.data.ExecutionServiceInput +import org.onap.ccsdk.apps.blueprintsprocessor.core.utils.PayloadUtils import org.onap.ccsdk.apps.blueprintsprocessor.functions.resource.resolution.processor.* import org.onap.ccsdk.apps.controllerblueprints.core.utils.BluePrintMetadataUtils +import org.onap.ccsdk.apps.controllerblueprints.core.utils.JacksonUtils import org.slf4j.LoggerFactory import org.springframework.beans.factory.annotation.Autowired import org.springframework.test.context.ContextConfiguration @@ -62,6 +65,12 @@ class ResourceResolutionServiceTest { val bluePrintRuntimeService = BluePrintMetadataUtils.getBluePrintRuntime("1234", "./../../../../components/model-catalog/blueprint-model/starter-blueprint/baseconfiguration") + val executionServiceInput = JacksonUtils.readValueFromClassPathFile("payload/requests/sample-resourceresolution-request.json", + ExecutionServiceInput::class.java)!! + + // Prepare Inputs + PayloadUtils.prepareInputsFromWorkflowPayload(bluePrintRuntimeService, executionServiceInput.payload, "resource-assignment") + resourceResolutionService.resolveResources(bluePrintRuntimeService, "resource-assignment", "baseconfig") } diff --git a/ms/blueprintsprocessor/functions/resource-resolution/src/test/resources/payload/requests/sample-resourceresolution-request.json b/ms/blueprintsprocessor/functions/resource-resolution/src/test/resources/payload/requests/sample-resourceresolution-request.json index 7889a7e43..c4fe4eab5 100644 --- a/ms/blueprintsprocessor/functions/resource-resolution/src/test/resources/payload/requests/sample-resourceresolution-request.json +++ b/ms/blueprintsprocessor/functions/resource-resolution/src/test/resources/payload/requests/sample-resourceresolution-request.json @@ -19,9 +19,12 @@ "resource-assignment-request": { "resource-assignment-properties": { "request-id": "1234", + "service-instance-id": "siid_1234", + "vnf-id": "vnf_1234", "action-name": "assign-activate", "scope-type": "vnf-type", - "hostname": "localhost" + "hostname": "localhost", + "vnf_name": "temp_vnf" } } } -- 2.16.6