2  * Copyright © 2017-2018 AT&T Intellectual Property.
 
   4  * Licensed under the Apache License, Version 2.0 (the "License");
 
   5  * you may not use this file except in compliance with the License.
 
   6  * You may obtain a copy of the License at
 
   8  *     http://www.apache.org/licenses/LICENSE-2.0
 
  10  * Unless required by applicable law or agreed to in writing, software
 
  11  * distributed under the License is distributed on an "AS IS" BASIS,
 
  12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 
  13  * See the License for the specific language governing permissions and
 
  14  * limitations under the License.
 
  17 package org.onap.ccsdk.apps.blueprintsprocessor.functions.python.executor
 
  19 import com.fasterxml.jackson.databind.node.ArrayNode
 
  20 import org.apache.commons.io.FilenameUtils
 
  21 import org.onap.ccsdk.apps.blueprintsprocessor.core.api.data.ExecutionServiceInput
 
  22 import org.onap.ccsdk.apps.blueprintsprocessor.functions.python.executor.utils.PythonExecutorUtils
 
  23 import org.onap.ccsdk.apps.blueprintsprocessor.services.execution.AbstractComponentFunction
 
  24 import org.onap.ccsdk.apps.controllerblueprints.core.BluePrintProcessorException
 
  25 import org.onap.ccsdk.apps.controllerblueprints.core.checkNotEmptyNThrow
 
  26 import org.onap.ccsdk.apps.controllerblueprints.core.data.OperationAssignment
 
  27 import org.slf4j.LoggerFactory
 
  28 import org.springframework.beans.factory.annotation.Autowired
 
  29 import org.springframework.beans.factory.config.ConfigurableBeanFactory
 
  30 import org.springframework.context.ApplicationContext
 
  31 import org.springframework.context.annotation.Scope
 
  32 import org.springframework.stereotype.Component
 
  34 @Component("component-jython-executor")
 
  35 @Scope(value = ConfigurableBeanFactory.SCOPE_PROTOTYPE)
 
  36 open class ComponentJythonExecutor(private val pythonExecutorProperty: PythonExecutorProperty) : AbstractComponentFunction() {
 
  38     private val log = LoggerFactory.getLogger(ComponentJythonExecutor::class.java)
 
  40     private var componentFunction: AbstractComponentFunction? = null
 
  43     lateinit var applicationContext: ApplicationContext
 
  45     fun populateJythonComponentInstance(executionServiceInput: ExecutionServiceInput) {
 
  46         val bluePrintContext = bluePrintRuntimeService.bluePrintContext()
 
  48         val operationAssignment: OperationAssignment = bluePrintContext
 
  49                 .nodeTemplateInterfaceOperation(nodeTemplateName, interfaceName, operationName)
 
  51         val blueprintBasePath: String = bluePrintContext.rootPath
 
  53         val artifactName: String = operationAssignment.implementation?.primary
 
  54                 ?: throw BluePrintProcessorException("missing primary field to get artifact name for node template ($nodeTemplateName)")
 
  56         val artifactDefinition = bluePrintRuntimeService.resolveNodeTemplateArtifactDefinition(nodeTemplateName, artifactName)
 
  58         val pythonFileName = artifactDefinition.file
 
  59                 ?: throw BluePrintProcessorException("missing file name for node template ($nodeTemplateName)'s artifactName($artifactName)")
 
  61         val pythonClassName = FilenameUtils.getBaseName(pythonFileName)
 
  63         val content: String? = bluePrintRuntimeService.resolveNodeTemplateArtifact(nodeTemplateName, artifactName)
 
  65         checkNotEmptyNThrow(content, "artifact ($artifactName) content is empty")
 
  67         val pythonPath: MutableList<String> = operationAssignment.implementation?.dependencies ?: arrayListOf()
 
  68         pythonPath.add(blueprintBasePath)
 
  69         pythonPath.addAll(pythonExecutorProperty.modulePaths)
 
  71         val jythonInstances: MutableMap<String, Any> = hashMapOf()
 
  72         jythonInstances["log"] = LoggerFactory.getLogger(nodeTemplateName)
 
  74         val instanceDependenciesNode: ArrayNode = operationInputs[PythonExecutorConstants.INPUT_INSTANCE_DEPENDENCIES] as? ArrayNode
 
  75                 ?: throw BluePrintProcessorException("Failed to get property(${PythonExecutorConstants.INPUT_INSTANCE_DEPENDENCIES})")
 
  77         instanceDependenciesNode.forEach { instanceName ->
 
  78             jythonInstances[instanceName.textValue()] = applicationContext.getBean(instanceName.textValue())
 
  81         componentFunction = PythonExecutorUtils.getPythonComponent(pythonExecutorProperty.executionPath,
 
  82                 pythonPath, content, pythonClassName, jythonInstances)
 
  86     override fun process(executionServiceInput: ExecutionServiceInput) {
 
  88         log.info("Processing : $operationInputs")
 
  89         checkNotNull(bluePrintRuntimeService) { "failed to get bluePrintRuntimeService" }
 
  91         // Populate Component Instance
 
  92         populateJythonComponentInstance(executionServiceInput)
 
  94         // Invoke Jython Component Script
 
  95         componentFunction!!.process(executionServiceInput)
 
  99     override fun recover(runtimeException: RuntimeException, executionRequest: ExecutionServiceInput) {
 
 100         componentFunction!!.recover(runtimeException, executionRequest)