Add remote python executor 21/84921/4
authorBrinda Santh <brindasanth@in.ibm.com>
Wed, 10 Apr 2019 18:05:29 +0000 (14:05 -0400)
committerAlexis de Talhouët <adetalhouet89@gmail.com>
Tue, 16 Apr 2019 14:38:50 +0000 (10:38 -0400)
Change-Id: I288e182847f250c8e26e9bc10b8f3124afc2f583
Issue-ID: CCSDK-1215
Signed-off-by: Brinda Santh <brindasanth@in.ibm.com>
components/model-catalog/definition-type/starter-type/node_type/component-remote-python-executor.json [new file with mode: 0644]
ms/blueprintsprocessor/functions/python-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/python/executor/ComponentRemotePythonExecutor.kt [new file with mode: 0644]
ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/api/data/BlueprintRemoteProcessorData.kt [new file with mode: 0644]
ms/blueprintsprocessor/modules/services/execution-service/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/execution/RemoteScriptExecutionService.kt [new file with mode: 0644]

diff --git a/components/model-catalog/definition-type/starter-type/node_type/component-remote-python-executor.json b/components/model-catalog/definition-type/starter-type/node_type/component-remote-python-executor.json
new file mode 100644 (file)
index 0000000..df2095c
--- /dev/null
@@ -0,0 +1,42 @@
+{
+  "description": "This is Jython Execution Component.",
+  "version": "1.0.0",
+  "capabilities": {
+    "component-node": {
+      "type": "tosca.capabilities.Node"
+    }
+  },
+  "interfaces": {
+    "ComponentRemotePythonExecutor": {
+      "operations": {
+        "process": {
+          "inputs": {
+            "endpoint-selector": {
+              "description": "Remote Container or Server selector name.",
+              "required": false,
+              "type": "string"
+            },
+            "dynamic-properties": {
+              "description": "Dynamic Json Content or DSL Json reference.",
+              "required": false,
+              "type": "json"
+            }
+          },
+          "outputs": {
+            "response-data": {
+              "description": "Execution Response Data in JSON format.",
+              "required": false,
+              "type": "json"
+            },
+            "status": {
+              "description": "Status of the Component Execution ( success or failure )",
+              "required": true,
+              "type": "string"
+            }
+          }
+        }
+      }
+    }
+  },
+  "derived_from": "tosca.nodes.Component"
+}
\ No newline at end of file
diff --git a/ms/blueprintsprocessor/functions/python-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/python/executor/ComponentRemotePythonExecutor.kt b/ms/blueprintsprocessor/functions/python-executor/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/functions/python/executor/ComponentRemotePythonExecutor.kt
new file mode 100644 (file)
index 0000000..1620b6d
--- /dev/null
@@ -0,0 +1,101 @@
+/*
+ *  Copyright © 2019 IBM.
+ *
+ *  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.
+ */
+
+package org.onap.ccsdk.cds.blueprintsprocessor.functions.python.executor
+
+import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.*
+import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.AbstractComponentFunction
+import org.onap.ccsdk.cds.blueprintsprocessor.services.execution.RemoteScriptExecutionService
+import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException
+import org.onap.ccsdk.cds.controllerblueprints.core.checkFileExists
+import org.onap.ccsdk.cds.controllerblueprints.core.checkNotBlank
+import org.onap.ccsdk.cds.controllerblueprints.core.data.OperationAssignment
+import org.onap.ccsdk.cds.controllerblueprints.core.normalizedFile
+import org.slf4j.LoggerFactory
+import org.springframework.beans.factory.config.ConfigurableBeanFactory
+import org.springframework.context.annotation.Scope
+import org.springframework.stereotype.Component
+
+
+@Component("component-remote-python-executor")
+@Scope(value = ConfigurableBeanFactory.SCOPE_PROTOTYPE)
+open class ComponentRemotePythonExecutor(private val remoteScriptExecutionService: RemoteScriptExecutionService)
+    : AbstractComponentFunction() {
+
+    private val log = LoggerFactory.getLogger(ComponentRemotePythonExecutor::class.java)
+
+    companion object {
+        const val INPUT_ENDPOINT_SELECTOR = "endpoint-selector"
+        const val INPUT_DYNAMIC_PROPERTIES = "dynamic-properties"
+    }
+
+    override suspend fun processNB(executionRequest: ExecutionServiceInput) {
+
+        log.info("Processing : $operationInputs")
+
+        val bluePrintContext = bluePrintRuntimeService.bluePrintContext()
+        val blueprintName = bluePrintContext.name()
+        val blueprintVersion = bluePrintContext.version()
+
+        val operationAssignment: OperationAssignment = bluePrintContext
+                .nodeTemplateInterfaceOperation(nodeTemplateName, interfaceName, operationName)
+
+        val artifactName: String = operationAssignment.implementation?.primary
+                ?: throw BluePrintProcessorException("missing primary field to get artifact name for node template ($nodeTemplateName)")
+
+        val artifactDefinition = bluePrintRuntimeService.resolveNodeTemplateArtifactDefinition(nodeTemplateName, artifactName)
+
+        checkNotBlank(artifactDefinition.file) { "couldn't get python script path($artifactName)" }
+
+        val pythonScript = normalizedFile(bluePrintContext.rootPath, artifactDefinition.file)
+
+        checkFileExists(pythonScript) { "python script(${pythonScript.absolutePath}) doesn't exists" }
+        //TODO ("Get the ENDPOINT SELECTOR and resolve the Remote Server")
+        val endPointSelector = getOperationInput(INPUT_ENDPOINT_SELECTOR)
+        val dynamicProperties = getOperationInput(INPUT_DYNAMIC_PROPERTIES)
+
+        // TODO("Python execution command and Resolve some expressions with dynamic properties")
+        val scriptCommand: String = pythonScript.absolutePath
+
+        val packages = operationAssignment.implementation?.dependencies
+        // If dependencies are defined, then install in remote server
+        if (packages != null && !packages.isEmpty()) {
+            val prepareEnvInput = PrepareRemoteEnvInput(requestId = processId,
+                    remoteScriptType = RemoteScriptType.PYTHON,
+                    packages = arrayListOf()
+            )
+            val prepareEnvOutput = remoteScriptExecutionService.prepareEnv(prepareEnvInput)
+            checkNotNull(prepareEnvOutput) {
+                "failed to get prepare remote env response for requestId(${prepareEnvInput.requestId})"
+            }
+        }
+
+        val remoteExecutionInput = RemoteScriptExecutionInput(
+                requestId = processId,
+                remoteIdentifier = RemoteIdentifier(blueprintName = blueprintName, blueprintVersion = blueprintVersion),
+                remoteScriptType = RemoteScriptType.PYTHON,
+                command = scriptCommand)
+        val remoteExecutionOutput = remoteScriptExecutionService.executeCommand(remoteExecutionInput)
+        checkNotNull(remoteExecutionOutput) {
+            "failed to get prepare remote command response for requestId(${remoteExecutionOutput.requestId})"
+        }
+    }
+
+    override suspend fun recoverNB(runtimeException: RuntimeException, executionRequest: ExecutionServiceInput) {
+        bluePrintRuntimeService.getBluePrintError()
+                .addError("Failed in ComponentJythonExecutor : ${runtimeException.message}")
+    }
+}
\ No newline at end of file
diff --git a/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/api/data/BlueprintRemoteProcessorData.kt b/ms/blueprintsprocessor/modules/commons/processor-core/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/core/api/data/BlueprintRemoteProcessorData.kt
new file mode 100644 (file)
index 0000000..90eb933
--- /dev/null
@@ -0,0 +1,45 @@
+/*
+ *  Copyright © 2019 IBM.
+ *
+ *  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.
+ */
+
+package org.onap.ccsdk.cds.blueprintsprocessor.core.api.data
+
+import com.fasterxml.jackson.databind.JsonNode
+
+enum class RemoteScriptType {
+    PYTHON, ANSIBLE, KOTLIN, SH
+}
+
+data class RemoteIdentifier(var blueprintName: String? = null,
+                            var blueprintVersion: String? = null)
+
+
+data class RemoteScriptExecutionInput(var requestId: String,
+                                      var remoteIdentifier: RemoteIdentifier? = null,
+                                      var remoteScriptType: RemoteScriptType,
+                                      var command: String,
+                                      var timeOut: Long = 30,
+                                      var properties: MutableMap<String, JsonNode> = hashMapOf()
+)
+
+
+data class RemoteScriptExecutionOutput(var requestId: String, var response: String)
+
+data class PrepareRemoteEnvInput(var requestId: String,
+                                 var remoteScriptType: RemoteScriptType,
+                                 var packages: MutableList<String>?,
+                                 var timeOut: Long = 120,
+                                 var properties: MutableMap<String, JsonNode> = hashMapOf()
+)
\ No newline at end of file
diff --git a/ms/blueprintsprocessor/modules/services/execution-service/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/execution/RemoteScriptExecutionService.kt b/ms/blueprintsprocessor/modules/services/execution-service/src/main/kotlin/org/onap/ccsdk/cds/blueprintsprocessor/services/execution/RemoteScriptExecutionService.kt
new file mode 100644 (file)
index 0000000..5d279ce
--- /dev/null
@@ -0,0 +1,27 @@
+/*
+ *  Copyright © 2019 IBM.
+ *
+ *  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.
+ */
+
+package org.onap.ccsdk.cds.blueprintsprocessor.services.execution
+
+import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.PrepareRemoteEnvInput
+import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.RemoteScriptExecutionInput
+import org.onap.ccsdk.cds.blueprintsprocessor.core.api.data.RemoteScriptExecutionOutput
+
+
+interface RemoteScriptExecutionService {
+    suspend fun prepareEnv(prepareEnvInput: PrepareRemoteEnvInput): RemoteScriptExecutionOutput
+    suspend fun executeCommand(remoteExecutionInput: RemoteScriptExecutionInput): RemoteScriptExecutionOutput
+}
\ No newline at end of file