2 * Copyright © 2017-2018 AT&T Intellectual Property.
3 * Modifications Copyright © 2018-2019 IBM, Bell Canada.
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
18 package org.onap.ccsdk.cds.controllerblueprints.core.service
20 import com.fasterxml.jackson.databind.JsonNode
21 import com.fasterxml.jackson.databind.node.NullNode
22 import com.fasterxml.jackson.databind.node.ObjectNode
23 import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper
24 import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintConstants
25 import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintError
26 import org.onap.ccsdk.cds.controllerblueprints.core.BluePrintProcessorException
27 import org.onap.ccsdk.cds.controllerblueprints.core.asJsonNode
28 import org.onap.ccsdk.cds.controllerblueprints.core.asJsonType
29 import org.onap.ccsdk.cds.controllerblueprints.core.common.ApplicationConstants.LOG_REDACTED
30 import org.onap.ccsdk.cds.controllerblueprints.core.data.ArtifactDefinition
31 import org.onap.ccsdk.cds.controllerblueprints.core.data.NodeTemplate
32 import org.onap.ccsdk.cds.controllerblueprints.core.data.PropertyDefinition
33 import org.onap.ccsdk.cds.controllerblueprints.core.returnNullIfMissing
34 import org.onap.ccsdk.cds.controllerblueprints.core.rootFieldsToMap
35 import org.onap.ccsdk.cds.controllerblueprints.core.utils.BluePrintMetadataUtils
36 import org.onap.ccsdk.cds.controllerblueprints.core.utils.PropertyDefinitionUtils.Companion.hasLogProtect
37 import org.slf4j.LoggerFactory
40 interface BluePrintRuntimeService<T> {
44 fun bluePrintContext(): BluePrintContext
46 fun getExecutionContext(): T
48 fun setExecutionContext(executionContext: T)
50 fun put(key: String, value: JsonNode)
52 fun get(key: String): JsonNode?
54 fun check(key: String): Boolean
58 fun getAsString(key: String): String?
60 fun getAsBoolean(key: String): Boolean?
62 fun getAsInt(key: String): Int?
64 fun getAsDouble(key: String): Double?
66 fun getBluePrintError(): BluePrintError
68 fun setBluePrintError(bluePrintError: BluePrintError)
70 fun loadEnvironments(type: String, fileName: String)
72 fun resolveNodeTemplatePropertyAssignments(
73 nodeTemplateName: String,
74 propertyDefinitions: MutableMap<String, PropertyDefinition>,
75 propertyAssignments: MutableMap<String, JsonNode>
76 ): MutableMap<String, JsonNode>
78 fun resolvePropertyDefinitions(name: String, propertyDefinitions: MutableMap<String, PropertyDefinition>):
79 MutableMap<String, JsonNode>
81 fun resolvePropertyAssignments(name: String, propertyAssignments: MutableMap<String, JsonNode>):
82 MutableMap<String, JsonNode>
84 fun resolveNodeTemplateProperties(nodeTemplateName: String): MutableMap<String, JsonNode>
86 fun resolveNodeTemplateCapabilityProperties(nodeTemplateName: String, capabilityName: String): MutableMap<String,
89 fun resolveNodeTemplateInterfaceOperationInputs(
90 nodeTemplateName: String,
91 interfaceName: String,
93 ): MutableMap<String, JsonNode>
95 fun resolveNodeTemplateInterfaceOperationOutputs(
96 nodeTemplateName: String,
97 interfaceName: String,
99 ): MutableMap<String, JsonNode>
101 fun resolveNodeTemplateArtifact(nodeTemplateName: String, artifactName: String): String
103 fun resolveNodeTemplateArtifactDefinition(nodeTemplateName: String, artifactName: String): ArtifactDefinition
105 fun resolveRelationshipTemplateProperties(relationshipTemplateName: String): MutableMap<String, JsonNode>
107 fun resolveDSLExpression(dslPropertyName: String): JsonNode
109 fun setInputValue(propertyName: String, value: JsonNode)
111 fun setWorkflowInputValue(
112 workflowName: String,
113 propertyName: String,
114 propertyDefinition: PropertyDefinition,
118 fun setNodeTemplatePropertyValue(nodeTemplateName: String, propertyName: String, value: JsonNode)
120 fun setNodeTemplateAttributeValue(nodeTemplateName: String, attributeName: String, value: JsonNode)
122 fun setNodeTemplateOperationPropertyValue(
123 nodeTemplateName: String,
124 interfaceName: String,
125 operationName: String,
126 propertyName: String,
130 fun setNodeTemplateOperationInputValue(
131 nodeTemplateName: String,
132 interfaceName: String,
133 operationName: String,
134 propertyName: String,
138 fun setNodeTemplateOperationOutputValue(
139 nodeTemplateName: String,
140 interfaceName: String,
141 operationName: String,
142 propertyName: String,
146 fun getInputValue(propertyName: String): JsonNode
148 fun getNodeTemplateOperationOutputValue(
149 nodeTemplateName: String,
150 interfaceName: String,
151 operationName: String,
155 fun getNodeTemplatePropertyValue(nodeTemplateName: String, propertyName: String): JsonNode?
157 fun getNodeTemplateAttributeValue(nodeTemplateName: String, attributeName: String): JsonNode?
159 fun assignInputs(jsonNode: JsonNode)
161 fun assignWorkflowInputs(workflowName: String, jsonNode: JsonNode)
163 fun resolveWorkflowOutputs(workflowName: String): MutableMap<String, JsonNode>
165 fun getJsonForNodeTemplateAttributeProperties(nodeTemplateName: String, keys: List<String>): JsonNode
171 * @author Brinda Santh
173 open class DefaultBluePrintRuntimeService(private var id: String, private var bluePrintContext: BluePrintContext) :
174 BluePrintRuntimeService<MutableMap<String, JsonNode>> {
177 private val log = LoggerFactory.getLogger(BluePrintRuntimeService::class.toString())
179 private var store: MutableMap<String, JsonNode> = hashMapOf()
181 private var bluePrintError = BluePrintError()
185 * Load Blueprint Environments Properties
187 val absoluteEnvFilePath = bluePrintContext.rootPath.plus(File.separator)
188 .plus(BluePrintConstants.TOSCA_ENVIRONMENTS_DIR)
189 loadEnvironments(BluePrintConstants.PROPERTY_BPP, absoluteEnvFilePath)
192 override fun id(): String {
196 override fun bluePrintContext(): BluePrintContext {
197 return bluePrintContext
200 override fun getExecutionContext(): MutableMap<String, JsonNode> {
204 @Suppress("UNCHECKED_CAST")
205 override fun setExecutionContext(executionContext: MutableMap<String, JsonNode>) {
206 this.store = executionContext
209 override fun put(key: String, value: JsonNode) {
213 override fun get(key: String): JsonNode {
214 return store[key] ?: throw BluePrintProcessorException("failed to get execution property($key)")
217 override fun check(key: String): Boolean {
218 return store.containsKey(key)
221 override fun cleanRuntime() {
225 private fun getJsonNode(key: String): JsonNode {
229 override fun getAsString(key: String): String? {
230 return get(key).asText()
233 override fun getAsBoolean(key: String): Boolean? {
234 return get(key).asBoolean()
237 override fun getAsInt(key: String): Int? {
238 return get(key).asInt()
241 override fun getAsDouble(key: String): Double? {
242 return get(key).asDouble()
245 override fun getBluePrintError(): BluePrintError {
246 return this.bluePrintError
249 override fun setBluePrintError(bluePrintError: BluePrintError) {
250 this.bluePrintError = bluePrintError
253 override fun loadEnvironments(type: String, fileName: String) {
254 BluePrintMetadataUtils.environmentFileProperties(fileName).forEach { key, value ->
255 setNodeTemplateAttributeValue(type, key.toString(), value.asJsonType())
260 * Resolve any property assignments for the node
262 override fun resolveNodeTemplatePropertyAssignments(
263 nodeTemplateName: String,
264 propertyDefinitions: MutableMap<String, PropertyDefinition>,
265 propertyAssignments: MutableMap<String, JsonNode>
267 MutableMap<String, JsonNode> {
269 val propertyAssignmentValue: MutableMap<String, JsonNode> = hashMapOf()
271 propertyDefinitions.forEach { (nodeTypePropertyName, nodeTypeProperty) ->
272 // Get the Express or Value for the Node Template
273 val propertyAssignment: JsonNode? = propertyAssignments[nodeTypePropertyName]
275 var resolvedValue: JsonNode = NullNode.getInstance()
276 if (propertyAssignment != null) {
277 // Resolve the Expressing
278 val propertyAssignmentExpression = PropertyAssignmentService(this)
279 resolvedValue = propertyAssignmentExpression.resolveAssignmentExpression(
280 nodeTemplateName, nodeTypePropertyName, propertyAssignment
284 // Set default value if null
285 if (resolvedValue is NullNode) {
286 nodeTypeProperty.defaultValue?.let { resolvedValue = nodeTypeProperty.defaultValue!! }
289 /** If property is Map type, then resolve the property value, It may have expressiong */
290 if (nodeTypeProperty.type == BluePrintConstants.DATA_TYPE_MAP &&
291 resolvedValue.returnNullIfMissing() != null
293 val mapResolvedValue = resolvePropertyAssignments(nodeTemplateName, resolvedValue.rootFieldsToMap())
294 resolvedValue = mapResolvedValue.asJsonNode()
297 // Set for Return of method
298 propertyAssignmentValue[nodeTypePropertyName] = resolvedValue
300 return propertyAssignmentValue
303 override fun resolvePropertyDefinitions(name: String, propertyDefinitions: MutableMap<String, PropertyDefinition>):
304 MutableMap<String, JsonNode> {
305 val propertyAssignmentValue: MutableMap<String, JsonNode> = hashMapOf()
307 propertyDefinitions.forEach { propertyName, propertyDefinition ->
308 val propertyAssignmentExpression = PropertyAssignmentService(this)
309 val expression = propertyDefinition.value ?: propertyDefinition.defaultValue
310 if (expression != null) {
311 propertyAssignmentValue[propertyName] =
312 propertyAssignmentExpression.resolveAssignmentExpression(name, propertyName, expression)
315 return propertyAssignmentValue
318 override fun resolvePropertyAssignments(name: String, propertyAssignments: MutableMap<String, JsonNode>):
319 MutableMap<String, JsonNode> {
320 val propertyAssignmentValue: MutableMap<String, JsonNode> = hashMapOf()
322 propertyAssignments.forEach { (propertyName, propertyExpression) ->
323 val propertyAssignmentExpression = PropertyAssignmentService(this)
324 propertyAssignmentValue[propertyName] =
325 propertyAssignmentExpression.resolveAssignmentExpression(name, propertyName, propertyExpression)
327 return propertyAssignmentValue
330 override fun resolveNodeTemplateProperties(nodeTemplateName: String): MutableMap<String, JsonNode> {
331 log.info("resolveNodeTemplatePropertyValues for node template ({})", nodeTemplateName)
333 val nodeTemplate: NodeTemplate = bluePrintContext.nodeTemplateByName(nodeTemplateName)
335 val propertyAssignments: MutableMap<String, JsonNode> = nodeTemplate.properties!!
337 // Get the Node Type Definitions
338 val nodeTypePropertiesDefinitions: MutableMap<String, PropertyDefinition> = bluePrintContext
339 .nodeTypeChainedProperties(nodeTemplate.type)!!
342 * Resolve the NodeTemplate Property Assignment Values.
344 return resolveNodeTemplatePropertyAssignments(
346 nodeTypePropertiesDefinitions,
351 override fun resolveNodeTemplateCapabilityProperties(nodeTemplateName: String, capabilityName: String):
352 MutableMap<String, JsonNode> {
353 log.info("resolveNodeTemplateCapabilityProperties for node template($nodeTemplateName) capability($capabilityName)")
354 val nodeTemplate: NodeTemplate = bluePrintContext.nodeTemplateByName(nodeTemplateName)
356 val propertyAssignments = nodeTemplate.capabilities?.get(capabilityName)?.properties ?: hashMapOf()
358 val propertyDefinitions = bluePrintContext.nodeTemplateNodeType(nodeTemplateName)
359 .capabilities?.get(capabilityName)?.properties ?: hashMapOf()
362 * Resolve the Capability Property Assignment Values.
364 return resolveNodeTemplatePropertyAssignments(nodeTemplateName, propertyDefinitions, propertyAssignments)
367 override fun resolveNodeTemplateInterfaceOperationInputs(
368 nodeTemplateName: String,
369 interfaceName: String,
370 operationName: String
371 ): MutableMap<String, JsonNode> {
373 "resolveNodeTemplateInterfaceOperationInputs for node template ($nodeTemplateName), " +
374 "interface name($interfaceName), operationName($operationName)"
377 val propertyAssignments: MutableMap<String, JsonNode> =
378 bluePrintContext.nodeTemplateInterfaceOperationInputs(nodeTemplateName, interfaceName, operationName)
381 val nodeTypeName = bluePrintContext.nodeTemplateByName(nodeTemplateName).type
383 val nodeTypeInterfaceOperationInputs: MutableMap<String, PropertyDefinition> =
384 bluePrintContext.nodeTypeInterfaceOperationInputs(nodeTypeName, interfaceName, operationName)
387 log.info("input definition for node template ($nodeTemplateName), values ($propertyAssignments)")
390 * Resolve the Property Input Assignment Values.
392 return resolveNodeTemplatePropertyAssignments(
394 nodeTypeInterfaceOperationInputs,
399 override fun resolveNodeTemplateInterfaceOperationOutputs(
400 nodeTemplateName: String,
401 interfaceName: String,
402 operationName: String
403 ): MutableMap<String, JsonNode> {
405 "resolveNodeTemplateInterfaceOperationOutputs for node template ($nodeTemplateName),interface name " +
406 "($interfaceName), operationName($operationName)"
409 val propertyAssignments: MutableMap<String, JsonNode> =
410 bluePrintContext.nodeTemplateInterfaceOperationOutputs(nodeTemplateName, interfaceName, operationName)
413 val nodeTypeName = bluePrintContext.nodeTemplateByName(nodeTemplateName).type
415 val nodeTypeInterfaceOperationOutputs: MutableMap<String, PropertyDefinition> =
416 bluePrintContext.nodeTypeInterfaceOperationOutputs(nodeTypeName, interfaceName, operationName)
419 * Resolve the Property Output Assignment Values.
421 val propertyAssignmentValue =
422 resolveNodeTemplatePropertyAssignments(
424 nodeTypeInterfaceOperationOutputs,
428 // Store operation output values into context
429 propertyAssignmentValue.forEach { (key, value) ->
430 setNodeTemplateOperationOutputValue(nodeTemplateName, interfaceName, operationName, key, value)
432 return propertyAssignmentValue
435 override fun resolveNodeTemplateArtifact(nodeTemplateName: String, artifactName: String): String {
436 val artifactDefinition: ArtifactDefinition =
437 resolveNodeTemplateArtifactDefinition(nodeTemplateName, artifactName)
438 val propertyAssignmentExpression = PropertyAssignmentService(this)
439 return propertyAssignmentExpression.artifactContent(artifactDefinition)
442 override fun resolveNodeTemplateArtifactDefinition(
443 nodeTemplateName: String,
445 ): ArtifactDefinition {
446 val nodeTemplate = bluePrintContext.nodeTemplateByName(nodeTemplateName)
448 return nodeTemplate.artifacts?.get(artifactName)
449 ?: throw BluePrintProcessorException(
450 "failed to get artifact definition($artifactName) from the node template"
454 override fun resolveRelationshipTemplateProperties(relationshipTemplateName: String): MutableMap<String, JsonNode> {
455 log.info("resolveRelationshipTemplateProperties for relationship template ({})", relationshipTemplateName)
457 val relationshipTemplate = bluePrintContext.relationshipTemplateByName(relationshipTemplateName)
459 val propertyAssignments = relationshipTemplate.properties!!
461 // Get the Relationship Type Definitions
462 val propertiesDefinitions = bluePrintContext.relationshipTypeByName(relationshipTemplate.type).properties
463 ?: throw BluePrintProcessorException("failed to get ${relationshipTemplate.type} properties.")
466 * Resolve the RelationshipTemplate Property Assignment Values.
467 * TODO("Now it supports only input, node not SELF(propert, attribute, artifact) expressions, later it will support SELF expressions")
469 return resolveNodeTemplatePropertyAssignments(
471 propertiesDefinitions,
477 * Read the DSL Property reference, If there is any expression, then resolve those expression and return as Json
480 override fun resolveDSLExpression(dslPropertyName: String): JsonNode {
481 val propertyAssignments = bluePrintContext.dslPropertiesByName(dslPropertyName)
482 return if (BluePrintExpressionService.checkContainsExpression(propertyAssignments) &&
483 propertyAssignments is ObjectNode
486 val rootKeyMap = propertyAssignments.rootFieldsToMap()
487 val propertyAssignmentValue: MutableMap<String, JsonNode> = hashMapOf()
488 rootKeyMap.forEach { (propertyName, propertyValue) ->
489 val propertyAssignmentExpression = PropertyAssignmentService(this)
490 propertyAssignmentValue[propertyName] = propertyAssignmentExpression
491 .resolveAssignmentExpression("DSL", propertyName, propertyValue)
493 propertyAssignmentValue.asJsonNode()
499 override fun setInputValue(propertyName: String, value: JsonNode) {
500 val path = """${BluePrintConstants.PATH_INPUTS}${BluePrintConstants.PATH_DIVIDER}$propertyName"""
504 override fun setWorkflowInputValue(
505 workflowName: String,
506 propertyName: String,
507 propertyDefinition: PropertyDefinition,
510 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_WORKFLOWS)
511 .append(BluePrintConstants.PATH_DIVIDER).append(workflowName)
512 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_INPUTS)
513 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_PROPERTIES)
514 .append(BluePrintConstants.PATH_DIVIDER).append(propertyName).toString()
518 override fun setNodeTemplatePropertyValue(nodeTemplateName: String, propertyName: String, value: JsonNode) {
519 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
520 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
521 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_PROPERTIES)
522 .append(BluePrintConstants.PATH_DIVIDER).append(propertyName).toString()
526 override fun setNodeTemplateAttributeValue(nodeTemplateName: String, attributeName: String, value: JsonNode) {
527 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
528 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
529 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_ATTRIBUTES)
530 .append(BluePrintConstants.PATH_DIVIDER).append(attributeName).toString()
534 override fun setNodeTemplateOperationPropertyValue(
535 nodeTemplateName: String,
536 interfaceName: String,
537 operationName: String,
538 propertyName: String,
541 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
542 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
543 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_INTERFACES)
544 .append(BluePrintConstants.PATH_DIVIDER).append(interfaceName)
545 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_OPERATIONS)
546 .append(BluePrintConstants.PATH_DIVIDER).append(operationName)
547 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_PROPERTIES)
548 .append(BluePrintConstants.PATH_DIVIDER).append(propertyName).toString()
549 log.trace("setting operation property path ({}), values ({})", path, value)
553 override fun setNodeTemplateOperationInputValue(
554 nodeTemplateName: String,
555 interfaceName: String,
556 operationName: String,
557 propertyName: String,
560 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
561 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
562 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_INTERFACES)
563 .append(BluePrintConstants.PATH_DIVIDER).append(interfaceName)
564 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_OPERATIONS)
565 .append(BluePrintConstants.PATH_DIVIDER).append(operationName)
566 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_INPUTS)
567 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_PROPERTIES)
568 .append(BluePrintConstants.PATH_DIVIDER).append(propertyName).toString()
572 override fun setNodeTemplateOperationOutputValue(
573 nodeTemplateName: String,
574 interfaceName: String,
575 operationName: String,
576 propertyName: String,
579 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
580 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
581 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_INTERFACES)
582 .append(BluePrintConstants.PATH_DIVIDER).append(interfaceName)
583 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_OPERATIONS)
584 .append(BluePrintConstants.PATH_DIVIDER).append(operationName)
585 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_OUTPUTS)
586 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_PROPERTIES)
587 .append(BluePrintConstants.PATH_DIVIDER).append(propertyName).toString()
591 override fun getInputValue(propertyName: String): JsonNode {
592 val path = StringBuilder(BluePrintConstants.PATH_INPUTS)
593 .append(BluePrintConstants.PATH_DIVIDER).append(propertyName).toString()
594 return getJsonNode(path)
597 override fun getNodeTemplateOperationOutputValue(
598 nodeTemplateName: String,
599 interfaceName: String,
600 operationName: String,
603 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
604 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
605 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_INTERFACES)
606 .append(BluePrintConstants.PATH_DIVIDER).append(interfaceName)
607 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_OPERATIONS)
608 .append(BluePrintConstants.PATH_DIVIDER).append(operationName)
609 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_OUTPUTS)
610 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_PROPERTIES)
611 .append(BluePrintConstants.PATH_DIVIDER).append(propertyName).toString()
612 return getJsonNode(path)
615 override fun getNodeTemplatePropertyValue(nodeTemplateName: String, propertyName: String): JsonNode {
616 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
617 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
618 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_PROPERTIES)
619 .append(BluePrintConstants.PATH_DIVIDER).append(propertyName).toString()
620 return getJsonNode(path)
623 override fun getNodeTemplateAttributeValue(nodeTemplateName: String, attributeName: String): JsonNode {
624 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
625 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
626 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_ATTRIBUTES)
627 .append(BluePrintConstants.PATH_DIVIDER).append(attributeName).toString()
628 return getJsonNode(path)
631 override fun assignInputs(jsonNode: JsonNode) {
632 log.info("assignInputs from input JSON ({})", jsonNode.toString())
633 bluePrintContext.inputs()?.forEach { propertyName, property ->
634 val valueNode: JsonNode = jsonNode.at(BluePrintConstants.PATH_DIVIDER + propertyName)
635 ?: property.defaultValue
636 ?: NullNode.getInstance()
637 setInputValue(propertyName, valueNode)
641 override fun assignWorkflowInputs(workflowName: String, jsonNode: JsonNode) {
642 log.info("Deriving input data for workflow: ($workflowName)")
644 val dynamicInputPropertiesName = "$workflowName-properties"
646 bluePrintContext.workflowByName(workflowName).inputs
647 ?.filter { (propertyName, property) -> propertyName != dynamicInputPropertiesName }
648 ?.forEach { propertyName, property -> findAndSetInputValue(propertyName, property, jsonNode) }
649 // Load Dynamic data Types
650 jsonNode.get(dynamicInputPropertiesName)?.let {
651 bluePrintContext.dataTypeByName("dt-$dynamicInputPropertiesName")
653 ?.forEach { propertyName, property -> findAndSetInputValue(propertyName, property, it) }
657 private fun findAndSetInputValue(propertyName: String, property: PropertyDefinition, jsonNode: JsonNode) {
658 val valueNode = jsonNode.at(BluePrintConstants.PATH_DIVIDER + propertyName)
659 .returnNullIfMissing()
660 ?: property.defaultValue
661 ?: NullNode.getInstance()
662 val loggableValue = if (hasLogProtect(property)) LOG_REDACTED else valueNode.toString()
663 log.info("Setting input data - attribute:($propertyName) value:($loggableValue)")
664 setInputValue(propertyName, valueNode)
667 override fun resolveWorkflowOutputs(workflowName: String): MutableMap<String, JsonNode> {
668 log.info("resolveWorkflowOutputs for workflow($workflowName)")
669 val outputs = bluePrintContext.workflowByName(workflowName).outputs ?: mutableMapOf()
670 return resolvePropertyDefinitions("WORKFLOW", outputs)
673 override fun getJsonForNodeTemplateAttributeProperties(nodeTemplateName: String, keys: List<String>): JsonNode {
675 val jsonNode: ObjectNode = jacksonObjectMapper().createObjectNode()
676 val path: String = StringBuilder(BluePrintConstants.PATH_NODE_TEMPLATES)
677 .append(BluePrintConstants.PATH_DIVIDER).append(nodeTemplateName)
678 .append(BluePrintConstants.PATH_DIVIDER).append(BluePrintConstants.PATH_ATTRIBUTES)
679 .append(BluePrintConstants.PATH_DIVIDER).toString()
683 val key = it.replace(path, "")
684 if (keys.contains(key)) {
685 val value = store[it] as JsonNode
686 jsonNode.set(key, value)