a5927a5b45434a6b36083a73cd4774426cf3b8c4
[sdc.git] / catalog-be / src / main / java / org / openecomp / sdc / be / components / csar / YamlTemplateParsingHandler.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * SDC
4  * ================================================================================
5  * Copyright (C) 2017 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  * Modifications copyright (c) 2019 Nokia
20  * ================================================================================
21  */
22
23 package org.openecomp.sdc.be.components.csar;
24
25 import static java.util.stream.Collectors.toList;
26 import static org.openecomp.sdc.be.components.impl.ImportUtils.Constants.QUOTE;
27 import static org.openecomp.sdc.be.components.impl.ImportUtils.ResultStatusEnum;
28 import static org.openecomp.sdc.be.components.impl.ImportUtils.ToscaElementTypeEnum;
29 import static org.openecomp.sdc.be.components.impl.ImportUtils.findFirstToscaListElement;
30 import static org.openecomp.sdc.be.components.impl.ImportUtils.findFirstToscaMapElement;
31 import static org.openecomp.sdc.be.components.impl.ImportUtils.findToscaElement;
32 import static org.openecomp.sdc.be.components.impl.ImportUtils.loadYamlAsStrictMap;
33 import static org.openecomp.sdc.be.model.tosca.ToscaType.STRING;
34 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.ARTIFACTS;
35 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.ATTRIBUTES;
36 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.CAPABILITIES;
37 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.CAPABILITY;
38 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.DEFAULT_VALUE;
39 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.DESCRIPTION;
40 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.FILE;
41 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.GET_INPUT;
42 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.GROUPS;
43 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.IMPLEMENTATION;
44 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.INPUTS;
45 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.INTERFACES;
46 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.IS_PASSWORD;
47 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.MEMBERS;
48 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.MILESTONES;
49 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.NODE;
50 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.NODE_TEMPLATES;
51 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.NODE_TYPE;
52 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.OPERATIONS;
53 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.OUTPUTS;
54 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.POLICIES;
55 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.PROPERTIES;
56 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.RELATIONSHIP;
57 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.RELATIONSHIP_TEMPLATES;
58 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.REQUIREMENTS;
59 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.SUBSTITUTION_FILTERS;
60 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.SUBSTITUTION_MAPPINGS;
61 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.TARGETS;
62 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.TOPOLOGY_TEMPLATE;
63 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.TYPE;
64 import static org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum.VALID_SOURCE_TYPES;
65
66 import com.att.aft.dme2.internal.gson.reflect.TypeToken;
67 import com.google.common.collect.Lists;
68 import com.google.common.collect.Maps;
69 import com.google.gson.Gson;
70 import fj.data.Either;
71 import java.lang.reflect.Type;
72 import java.util.ArrayList;
73 import java.util.Collection;
74 import java.util.Collections;
75 import java.util.EnumMap;
76 import java.util.HashMap;
77 import java.util.LinkedHashMap;
78 import java.util.List;
79 import java.util.Map;
80 import java.util.Map.Entry;
81 import java.util.Objects;
82 import java.util.Optional;
83 import java.util.Set;
84 import java.util.UUID;
85 import java.util.stream.Collectors;
86 import org.apache.commons.collections.CollectionUtils;
87 import org.apache.commons.collections.MapUtils;
88 import org.apache.commons.lang3.StringUtils;
89 import org.openecomp.sdc.be.components.impl.AnnotationBusinessLogic;
90 import org.openecomp.sdc.be.components.impl.GroupTypeBusinessLogic;
91 import org.openecomp.sdc.be.components.impl.ImportUtils;
92 import org.openecomp.sdc.be.components.impl.InterfaceDefinitionHandler;
93 import org.openecomp.sdc.be.components.impl.NodeFilterUploadCreator;
94 import org.openecomp.sdc.be.components.impl.PolicyTypeBusinessLogic;
95 import org.openecomp.sdc.be.components.impl.ServiceBusinessLogic;
96 import org.openecomp.sdc.be.components.impl.exceptions.ByActionStatusComponentException;
97 import org.openecomp.sdc.be.components.utils.PropertiesUtils;
98 import org.openecomp.sdc.be.config.BeEcompErrorManager;
99 import org.openecomp.sdc.be.dao.api.ActionStatus;
100 import org.openecomp.sdc.be.dao.janusgraph.JanusGraphDao;
101 import org.openecomp.sdc.be.datatypes.elements.ActivityDataDefinition;
102 import org.openecomp.sdc.be.datatypes.elements.ArtifactDataDefinition;
103 import org.openecomp.sdc.be.datatypes.elements.CapabilityDataDefinition;
104 import org.openecomp.sdc.be.datatypes.elements.FilterDataDefinition;
105 import org.openecomp.sdc.be.datatypes.elements.GetInputValueDataDefinition;
106 import org.openecomp.sdc.be.datatypes.elements.ListDataDefinition;
107 import org.openecomp.sdc.be.datatypes.elements.MilestoneDataDefinition;
108 import org.openecomp.sdc.be.datatypes.elements.OperationDataDefinition;
109 import org.openecomp.sdc.be.datatypes.elements.OperationInputDefinition;
110 import org.openecomp.sdc.be.datatypes.elements.PolicyTargetType;
111 import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
112 import org.openecomp.sdc.be.datatypes.elements.PropertyFilterConstraintDataDefinition;
113 import org.openecomp.sdc.be.datatypes.elements.SubPropertyToscaFunction;
114 import org.openecomp.sdc.be.datatypes.elements.SubstitutionFilterPropertyDataDefinition;
115 import org.openecomp.sdc.be.datatypes.elements.ToscaFunction;
116 import org.openecomp.sdc.be.datatypes.elements.ToscaFunctionType;
117 import org.openecomp.sdc.be.datatypes.enums.ActivityTypeEnum;
118 import org.openecomp.sdc.be.datatypes.enums.ConstraintType;
119 import org.openecomp.sdc.be.datatypes.enums.FilterValueType;
120 import org.openecomp.sdc.be.datatypes.enums.PropertyFilterTargetType;
121 import org.openecomp.sdc.be.model.CapabilityDefinition;
122 import org.openecomp.sdc.be.model.Component;
123 import org.openecomp.sdc.be.model.ComponentInstanceProperty;
124 import org.openecomp.sdc.be.model.GroupDefinition;
125 import org.openecomp.sdc.be.model.GroupTypeDefinition;
126 import org.openecomp.sdc.be.model.InputDefinition;
127 import org.openecomp.sdc.be.model.NodeTypeInfo;
128 import org.openecomp.sdc.be.model.OutputDefinition;
129 import org.openecomp.sdc.be.model.ParsedToscaYamlInfo;
130 import org.openecomp.sdc.be.model.PolicyDefinition;
131 import org.openecomp.sdc.be.model.PolicyTypeDefinition;
132 import org.openecomp.sdc.be.model.PropertyDefinition;
133 import org.openecomp.sdc.be.model.UploadArtifactInfo;
134 import org.openecomp.sdc.be.model.UploadAttributeInfo;
135 import org.openecomp.sdc.be.model.UploadCapInfo;
136 import org.openecomp.sdc.be.model.UploadComponentInstanceInfo;
137 import org.openecomp.sdc.be.model.UploadInterfaceInfo;
138 import org.openecomp.sdc.be.model.UploadPropInfo;
139 import org.openecomp.sdc.be.model.UploadReqInfo;
140 import org.openecomp.sdc.be.model.tosca.ToscaPropertyType;
141 import org.openecomp.sdc.be.tosca.model.ToscaInterfaceDefinition;
142 import org.openecomp.sdc.be.tosca.utils.OperationArtifactUtil;
143 import org.openecomp.sdc.be.ui.model.OperationUi;
144 import org.openecomp.sdc.be.ui.model.PropertyAssignmentUi;
145 import org.openecomp.sdc.be.utils.PropertyFilterConstraintDataDefinitionHelper;
146 import org.openecomp.sdc.be.utils.TypeUtils;
147 import org.openecomp.sdc.common.log.wrappers.Logger;
148 import org.yaml.snakeyaml.parser.ParserException;
149
150 /**
151  * A handler class designed to parse the YAML file of the service template for a JAVA object
152  */
153 @org.springframework.stereotype.Component
154 public class YamlTemplateParsingHandler {
155
156     private static final int SUB_MAPPING_CAPABILITY_OWNER_NAME_IDX = 0;
157     private static final int SUB_MAPPING_CAPABILITY_NAME_IDX = 1;
158     private static final Logger log = Logger.getLogger(YamlTemplateParsingHandler.class);
159     private final Gson gson = new Gson();
160     private final JanusGraphDao janusGraphDao;
161     private final GroupTypeBusinessLogic groupTypeBusinessLogic;
162     private final AnnotationBusinessLogic annotationBusinessLogic;
163     private final PolicyTypeBusinessLogic policyTypeBusinessLogic;
164     private final ServiceBusinessLogic serviceBusinessLogic;
165     private final ToscaFunctionYamlParsingHandler toscaFunctionYamlParsingHandler;
166     private final InterfaceDefinitionHandler interfaceDefinitionHandler;
167
168     public YamlTemplateParsingHandler(JanusGraphDao janusGraphDao,
169                                       GroupTypeBusinessLogic groupTypeBusinessLogic,
170                                       AnnotationBusinessLogic annotationBusinessLogic,
171                                       PolicyTypeBusinessLogic policyTypeBusinessLogic,
172                                       ServiceBusinessLogic serviceBusinessLogic,
173                                       final ToscaFunctionYamlParsingHandler toscaFunctionYamlParsingHandler,
174                                       final InterfaceDefinitionHandler interfaceDefinitionHandler
175     ) {
176         this.janusGraphDao = janusGraphDao;
177         this.groupTypeBusinessLogic = groupTypeBusinessLogic;
178         this.annotationBusinessLogic = annotationBusinessLogic;
179         this.policyTypeBusinessLogic = policyTypeBusinessLogic;
180         this.serviceBusinessLogic = serviceBusinessLogic;
181         this.toscaFunctionYamlParsingHandler = toscaFunctionYamlParsingHandler;
182         this.interfaceDefinitionHandler = interfaceDefinitionHandler;
183     }
184
185     public ParsedToscaYamlInfo parseResourceInfoFromYAML(String fileName, String resourceYml, Map<String, String> createdNodesToscaResourceNames,
186                                                          Map<String, NodeTypeInfo> nodeTypesInfo, String nodeName,
187                                                          Component component, String interfaceTemplateYaml) {
188         log.debug("#parseResourceInfoFromYAML - Going to parse yaml {} ", fileName);
189         Map<String, Object> mappedToscaTemplate = getMappedToscaTemplate(fileName, resourceYml, nodeTypesInfo, nodeName);
190         ParsedToscaYamlInfo parsedToscaYamlInfo = new ParsedToscaYamlInfo();
191         Map<String, Object> mappedTopologyTemplate = (Map<String, Object>) findToscaElement(mappedToscaTemplate, TOPOLOGY_TEMPLATE,
192             ToscaElementTypeEnum.ALL).left().on(err -> failIfNotTopologyTemplate(fileName));
193         final Map<String, Object> mappedTopologyTemplateInputs = mappedTopologyTemplate.entrySet().stream()
194             .filter(entry -> entry.getKey().equals(INPUTS.getElementName())).collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
195         final Map<String, Object> mappedTopologyTemplateOutputs = mappedTopologyTemplate.entrySet().stream()
196             .filter(entry -> entry.getKey().equals(OUTPUTS.getElementName())).collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
197         parsedToscaYamlInfo.setInputs(getInputs(mappedTopologyTemplateInputs));
198         parsedToscaYamlInfo.setOutputs(getOutputs(mappedTopologyTemplateOutputs));
199         parsedToscaYamlInfo.setInstances(getInstances(
200             mappedToscaTemplate,
201             createdNodesToscaResourceNames
202         ));
203         associateRelationshipTemplatesToInstances(parsedToscaYamlInfo.getInstances(), mappedTopologyTemplate);
204         parsedToscaYamlInfo.setGroups(getGroups(mappedToscaTemplate, component.getModel()));
205         parsedToscaYamlInfo.setPolicies(getPolicies(mappedToscaTemplate, component.getModel()));
206         Map<String, Object> substitutionMappings = getSubstitutionMappings(mappedToscaTemplate);
207         if (substitutionMappings != null) {
208             if (component.isService()) {
209                 if (interfaceTemplateYaml.isEmpty()) {
210                     component.setDerivedFromGenericType((String) substitutionMappings.get(NODE_TYPE.getElementName()));
211                     List<PropertyDefinition> properties = serviceBusinessLogic.fetchDerivedFromGenericType(component, null).getProperties();
212                     parsedToscaYamlInfo.setProperties(properties.stream().collect(Collectors.toMap(PropertyDefinition::getName, prop -> prop)));
213                 } else {
214                     parsedToscaYamlInfo.setProperties(getProperties(loadYamlAsStrictMap(interfaceTemplateYaml)));
215                 }
216                 parsedToscaYamlInfo.setSubstitutionFilterProperties(getSubstitutionFilterProperties(mappedToscaTemplate));
217             }
218             if (substitutionMappings.get("properties") != null) {
219                 parsedToscaYamlInfo.setSubstitutionMappingProperties((Map<String, List<String>>) substitutionMappings.get("properties"));
220             }
221             parsedToscaYamlInfo.setSubstitutionMappingNodeType((String) substitutionMappings.get(NODE_TYPE.getElementName()));
222         }
223         log.debug("#parseResourceInfoFromYAML - The yaml {} has been parsed ", fileName);
224         return parsedToscaYamlInfo;
225     }
226
227     private Map<String, Object> getMappedToscaTemplate(String fileName, String resourceYml, Map<String, NodeTypeInfo> nodeTypesInfo,
228                                                        String nodeName) {
229         Map<String, Object> mappedToscaTemplate;
230         if (isNodeExist(nodeTypesInfo, nodeName)) {
231             mappedToscaTemplate = nodeTypesInfo.get(nodeName).getMappedToscaTemplate();
232         } else {
233             mappedToscaTemplate = loadYaml(fileName, resourceYml);
234         }
235         return mappedToscaTemplate;
236     }
237
238     private Map<String, Object> loadYaml(String fileName, String resourceYml) {
239         Map<String, Object> mappedToscaTemplate = null;
240         try {
241             mappedToscaTemplate = loadYamlAsStrictMap(resourceYml);
242         } catch (ParserException e) {
243             log.debug("#getMappedToscaTemplate - Failed to load YAML file {}", fileName, e);
244             rollbackWithException(ActionStatus.TOSCA_PARSE_ERROR, fileName, e.getMessage());
245         }
246         return mappedToscaTemplate;
247     }
248
249     private boolean isNodeExist(Map<String, NodeTypeInfo> nodeTypesInfo, String nodeName) {
250         return nodeTypesInfo != null && nodeName != null && nodeTypesInfo.containsKey(nodeName);
251     }
252
253     private Map<String, InputDefinition> getInputs(Map<String, Object> toscaJson) {
254         Map<String, InputDefinition> inputs = ImportUtils.getInputs(toscaJson, annotationBusinessLogic.getAnnotationTypeOperations()).left()
255             .on(err -> new HashMap<>());
256         annotationBusinessLogic.validateAndMergeAnnotationsAndAssignToInput(inputs);
257         return inputs;
258     }
259
260     private Map<String, OutputDefinition> getOutputs(Map<String, Object> toscaJson) {
261         return ImportUtils.getOutputs(toscaJson).left().on(err -> new HashMap<>());
262     }
263
264     private Map<String, PropertyDefinition> getProperties(Map<String, Object> toscaJson) {
265         return ImportUtils.getProperties(toscaJson).left().on(err -> new HashMap<>());
266     }
267
268     private ListDataDefinition<SubstitutionFilterPropertyDataDefinition> getSubstitutionFilterProperties(final Map<String, Object> toscaJson) {
269         final ListDataDefinition<SubstitutionFilterPropertyDataDefinition> propertyList = new ListDataDefinition<>();
270         final Map<String, Object> substitutionFilters = findFirstToscaMapElement(toscaJson, SUBSTITUTION_FILTERS).left().on(err -> new HashMap<>());
271         if (MapUtils.isEmpty(substitutionFilters)) {
272             return propertyList;
273         }
274         final List<Map<String, Object>> substitutionFilterProperties = (List<Map<String, Object>>) substitutionFilters.get("properties");
275         if (CollectionUtils.isEmpty(substitutionFilterProperties)) {
276             return propertyList;
277         }
278         for (final Map<String, Object> filterProps : substitutionFilterProperties) {
279             for (final Map.Entry<String, Object> propertyFilterEntry : filterProps.entrySet()) {
280                 final String propertyName = propertyFilterEntry.getKey();
281                 final Object value = propertyFilterEntry.getValue();
282                 if (value instanceof List) {
283                     final List<Map<String, Object>> propertyFilterEntryValue = (List<Map<String, Object>>) value;
284                     for (final Map<String, Object> filterValueMap : propertyFilterEntryValue) {
285                         final var substitutionFilterPropertyDataDefinition = new SubstitutionFilterPropertyDataDefinition();
286                         substitutionFilterPropertyDataDefinition.setName(propertyName);
287                         substitutionFilterPropertyDataDefinition.setConstraints(createSubstitutionFilterConstraints(propertyName, filterValueMap));
288                         propertyList.add(substitutionFilterPropertyDataDefinition);
289                     }
290                 } else if (value instanceof Map) {
291                     final Map<String, Object> filterValueMap = (Map<String, Object>) value;
292                     final var substitutionFilterPropertyDataDefinition = new SubstitutionFilterPropertyDataDefinition();
293                     substitutionFilterPropertyDataDefinition.setName(propertyName);
294                     substitutionFilterPropertyDataDefinition.setConstraints(createSubstitutionFilterConstraints(propertyName, filterValueMap));
295                     propertyList.add(substitutionFilterPropertyDataDefinition);
296                 }
297             }
298         }
299         return propertyList;
300     }
301
302     private List<PropertyFilterConstraintDataDefinition> createSubstitutionFilterConstraints(final String name, final Map<String, Object> value) {
303         final List<PropertyFilterConstraintDataDefinition> constraints = new ArrayList<>();
304         for (final Map.Entry<String, Object> valueEntry : value.entrySet()) {
305             final var propertyFilterConstraint = new PropertyFilterConstraintDataDefinition();
306             propertyFilterConstraint.setPropertyName(name);
307             propertyFilterConstraint.setOperator(ConstraintType.findByType(valueEntry.getKey()).orElse(null));
308             propertyFilterConstraint.setTargetType(PropertyFilterTargetType.PROPERTY);
309             final Optional<ToscaFunction> toscaFunction = PropertyFilterConstraintDataDefinitionHelper
310                 .createToscaFunctionFromLegacyConstraintValue(valueEntry.getValue());
311             if (toscaFunction.isPresent()) {
312                 final ToscaFunction toscaFunction1 = toscaFunction.get();
313                 propertyFilterConstraint.setValue(toscaFunction1);
314                 propertyFilterConstraint.setValueType(
315                     PropertyFilterConstraintDataDefinitionHelper.convertFromToscaFunctionType(toscaFunction1.getType()).orElse(null)
316                 );
317             } else {
318                 propertyFilterConstraint.setValue(valueEntry.getValue());
319                 propertyFilterConstraint.setValueType(FilterValueType.STATIC);
320             }
321             constraints.add(propertyFilterConstraint);
322         }
323
324         return constraints;
325     }
326
327     private Map<String, PolicyDefinition> getPolicies(Map<String, Object> toscaJson, String model) {
328         Map<String, Object> mappedTopologyTemplate = (Map<String, Object>) findToscaElement(toscaJson, TOPOLOGY_TEMPLATE, ToscaElementTypeEnum.ALL)
329             .left().on(err -> new HashMap<>());
330         Map<String, Object> foundPolicies = (Map<String, Object>) mappedTopologyTemplate.get(POLICIES.getElementName());
331         if (MapUtils.isNotEmpty(foundPolicies)) {
332             return foundPolicies.entrySet().stream().map(policyToCreate -> createPolicy(policyToCreate, model))
333                 .collect(Collectors.toMap(PolicyDefinition::getName, p -> p));
334         }
335         return Collections.emptyMap();
336     }
337
338     private PolicyDefinition createPolicy(Map.Entry<String, Object> policyNameValue, String model) {
339         PolicyDefinition emptyPolicyDef = new PolicyDefinition();
340         String policyName = policyNameValue.getKey();
341         emptyPolicyDef.setName(policyName);
342         try {
343             // There's no need to null test in conjunction with an instanceof test. null is not an instanceof anything, so a null check is redundant.
344             if (policyNameValue.getValue() instanceof Map) {
345                 Map<String, Object> policyTemplateJsonMap = (Map<String, Object>) policyNameValue.getValue();
346                 validateAndFillPolicy(emptyPolicyDef, policyTemplateJsonMap, model);
347             } else {
348                 rollbackWithException(ActionStatus.NOT_TOPOLOGY_TOSCA_TEMPLATE);
349             }
350         } catch (ClassCastException e) {
351             log.debug("#createPolicy - Failed to create the policy {}. The exception occurred", policyName, e);
352             rollbackWithException(ActionStatus.INVALID_YAML);
353         }
354         return emptyPolicyDef;
355     }
356
357     private void validateAndFillPolicy(PolicyDefinition emptyPolicyDefinition, Map<String, Object> policyTemplateJsonMap, String model) {
358         String policyTypeName = (String) policyTemplateJsonMap.get(TYPE.getElementName());
359         if (StringUtils.isEmpty(policyTypeName)) {
360             log.debug("#validateAndFillPolicy - The 'type' member is not found under policy {}", emptyPolicyDefinition.getName());
361             rollbackWithException(ActionStatus.POLICY_MISSING_POLICY_TYPE, emptyPolicyDefinition.getName());
362         }
363         emptyPolicyDefinition.setType(policyTypeName);
364         // set policy targets
365         emptyPolicyDefinition.setTargets(validateFillPolicyTargets(policyTemplateJsonMap));
366         PolicyTypeDefinition policyTypeDefinition = validateGetPolicyTypeDefinition(policyTypeName, model);
367         // set policy properties
368         emptyPolicyDefinition.setProperties(validateFillPolicyProperties(policyTypeDefinition, policyTemplateJsonMap));
369     }
370
371     private PolicyTypeDefinition validateGetPolicyTypeDefinition(String policyType, String modelName) {
372         PolicyTypeDefinition policyTypeDefinition = policyTypeBusinessLogic.getLatestPolicyTypeByType(policyType, modelName);
373         if (policyTypeDefinition == null) {
374             log.debug("#validateAndFillPolicy - The policy type {} not found", policyType);
375             rollbackWithException(ActionStatus.POLICY_TYPE_IS_INVALID, policyType);
376         }
377         return policyTypeDefinition;
378     }
379
380     private List<PropertyDataDefinition> validateFillPolicyProperties(final PolicyTypeDefinition policyTypeDefinition,
381                                                                       final Map<String, Object> policyTemplateJsonMap) {
382         if (policyTypeDefinition == null || CollectionUtils.isEmpty(policyTypeDefinition.getProperties())
383             || MapUtils.isEmpty(policyTemplateJsonMap)) {
384             return Collections.emptyList();
385         }
386         final Map<String, Object> propertiesJsonMap = (Map<String, Object>) policyTemplateJsonMap.get(PROPERTIES.getElementName());
387         if (MapUtils.isEmpty(propertiesJsonMap)) {
388             return Collections.emptyList();
389         }
390         return propertiesJsonMap.entrySet().stream()
391             .map(propertyJson -> {
392                 final PropertyDefinition originalProperty =
393                     policyTypeDefinition.getProperties().stream()
394                         .filter(propertyDefinition -> propertyDefinition.getName().equals(propertyJson.getKey()))
395                         .findFirst()
396                         .orElse(null);
397                 if (originalProperty == null) {
398                     return null;
399                 }
400                 final UploadPropInfo uploadPropInfo = buildProperty(propertyJson.getKey(), propertyJson.getValue());
401                 final PropertyDefinition propertyDefinition = new PropertyDefinition(originalProperty);
402                 propertyDefinition.setToscaFunction(uploadPropInfo.getToscaFunction());
403                 propertyDefinition.setSubPropertyToscaFunctions(uploadPropInfo.getSubPropertyToscaFunctions());
404                 propertyDefinition.setGetInputValues(uploadPropInfo.getGet_input());
405                 propertyDefinition.setDescription(uploadPropInfo.getDescription());
406                 String propertyValue = gson.toJson(uploadPropInfo.getValue());
407                 if (!propertyDefinition.isToscaFunction()) {
408                     propertyValue = PropertiesUtils.trimQuotes(propertyValue);
409                 }
410                 propertyDefinition.setValue(propertyValue);
411                 return propertyDefinition;
412             })
413             .filter(Objects::nonNull)
414             .collect(Collectors.toList());
415     }
416
417     private Map<PolicyTargetType, List<String>> validateFillPolicyTargets(Map<String, Object> policyTemplateJson) {
418         Map<PolicyTargetType, List<String>> targets = new EnumMap<>(PolicyTargetType.class);
419         if (policyTemplateJson.containsKey(TARGETS.getElementName()) && policyTemplateJson.get(TARGETS.getElementName()) instanceof List) {
420             List<String> targetsElement = (List<String>) policyTemplateJson.get(TARGETS.getElementName());
421             targets.put(PolicyTargetType.COMPONENT_INSTANCES, targetsElement);
422         }
423         return targets;
424     }
425
426     private Map<String, UploadComponentInstanceInfo> getInstances(
427         Map<String, Object> toscaJson,
428         Map<String, String> createdNodesToscaResourceNames
429     ) {
430         Map<String, Object> nodeTemplates = findFirstToscaMapElement(toscaJson, NODE_TEMPLATES)
431             .left().on(err -> new HashMap<>());
432         if (nodeTemplates.isEmpty()) {
433             return Collections.emptyMap();
434         }
435         return getInstances(
436             toscaJson,
437             createdNodesToscaResourceNames,
438             nodeTemplates
439         );
440     }
441
442     private Map<String, UploadComponentInstanceInfo> getInstances(
443         Map<String, Object> toscaJson,
444         Map<String, String> createdNodesToscaResourceNames,
445         Map<String, Object> nodeTemplates
446     ) {
447         Map<String, Object> substitutionMappings = getSubstitutionMappings(toscaJson);
448         return nodeTemplates.entrySet().stream()
449             .map(node -> buildModuleComponentInstanceInfo(
450                 node,
451                 substitutionMappings,
452                 createdNodesToscaResourceNames
453             ))
454             .collect(Collectors.toMap(UploadComponentInstanceInfo::getName, i -> i));
455     }
456
457     private Map<String, Object> getSubstitutionMappings(Map<String, Object> toscaJson) {
458         Either<Map<String, Object>, ResultStatusEnum> eitherSubstitutionMappings = findFirstToscaMapElement(toscaJson, SUBSTITUTION_MAPPINGS);
459         if (eitherSubstitutionMappings.isLeft()) {
460             return eitherSubstitutionMappings.left().value();
461         }
462         return null;
463     }
464
465     private void associateRelationshipTemplatesToInstances(final Map<String, UploadComponentInstanceInfo> instances,
466                                                            final Map<String, Object> toscaJson) {
467         if (MapUtils.isEmpty(instances)) {
468             return;
469         }
470         for (UploadComponentInstanceInfo instance : instances.values()) {
471             final Map<String, List<OperationUi>> operations = new HashMap<>();
472             final Map<String, List<UploadReqInfo>> requirements = instance.getRequirements();
473             if (MapUtils.isNotEmpty(requirements)) {
474                 requirements.values()
475                     .forEach(requirementInfoList -> requirementInfoList.stream()
476                         .filter(requirement -> StringUtils.isNotEmpty(requirement.getRelationshipTemplate()))
477                         .forEach(requirement -> operations.put(requirement.getRelationshipTemplate(),
478                             getOperationsFromRelationshipTemplate(toscaJson, requirement.getRelationshipTemplate()))));
479             }
480             instance.setOperations(operations);
481         }
482     }
483
484     private Map<String, Object> getRelationshipTemplates(final Map<String, Object> toscaJson, final String relationshipTemplate) {
485         final Either<Map<String, Object>, ResultStatusEnum> eitherRelationshipTemplates = findFirstToscaMapElement(toscaJson, RELATIONSHIP_TEMPLATES);
486         if (eitherRelationshipTemplates.isRight()) {
487             throw new ByActionStatusComponentException(ActionStatus.RELATIONSHIP_TEMPLATE_NOT_FOUND);
488         }
489         final Map<String, Object> relationshipTemplateMap = eitherRelationshipTemplates.left().value();
490         final Map<String, Map<String, Object>> relationship = (Map<String, Map<String, Object>>) relationshipTemplateMap.get(relationshipTemplate);
491         if (relationship == null) {
492             throw new ByActionStatusComponentException(ActionStatus.RELATIONSHIP_TEMPLATE_DEFINITION_NOT_FOUND);
493         }
494         return relationship.get(INTERFACES.getElementName());
495     }
496
497     private List<ToscaInterfaceDefinition> buildToscaInterfacesFromRelationship(final Map<String, Object> interfaces) {
498         return interfaces.entrySet().stream()
499             .map(entry -> {
500                 final var toscaInterfaceDefinition = new ToscaInterfaceDefinition();
501                 toscaInterfaceDefinition.setType(entry.getKey());
502                 final Map<String, Object> toscaInterfaceMap = (Map<String, Object>) entry.getValue();
503                 toscaInterfaceDefinition.setOperations((Map<String, Object>) toscaInterfaceMap.get(OPERATIONS.getElementName()));
504                 return toscaInterfaceDefinition;
505             })
506             .collect(toList());
507     }
508
509     private Optional<Object> getImplementation(final Map<String, Object> operationToscaMap) {
510         if (MapUtils.isEmpty(operationToscaMap) || !operationToscaMap.containsKey(IMPLEMENTATION.getElementName())) {
511             return Optional.empty();
512         }
513         return Optional.ofNullable(operationToscaMap.get(IMPLEMENTATION.getElementName()));
514     }
515
516     private List<PropertyAssignmentUi> getOperationsInputs(final Map<String, Object> operationToscaMap) {
517         if (MapUtils.isEmpty(operationToscaMap) || !operationToscaMap.containsKey(INPUTS.getElementName())) {
518             return Collections.emptyList();
519         }
520         final Map<String, Object> inputsMap = (Map<String, Object>) operationToscaMap.get(INPUTS.getElementName());
521         return inputsMap.entrySet().stream().map(this::buildInputAssignment).collect(toList());
522     }
523
524     private PropertyAssignmentUi buildInputAssignment(final Entry<String, Object> inputAssignmentMap) {
525         var propertyAssignmentUi = new PropertyAssignmentUi();
526         propertyAssignmentUi.setName(inputAssignmentMap.getKey());
527         propertyAssignmentUi.setValue(inputAssignmentMap.getValue().toString());
528         propertyAssignmentUi.setType(STRING.getType());
529         return propertyAssignmentUi;
530     }
531
532     private List<OperationUi> getOperationsFromRelationshipTemplate(final Map<String, Object> toscaJson, final String relationshipTemplate) {
533         final List<OperationUi> operationUiList = new ArrayList<>();
534         final List<ToscaInterfaceDefinition> interfaces =
535             buildToscaInterfacesFromRelationship(getRelationshipTemplates(toscaJson, relationshipTemplate));
536         interfaces.stream()
537             .filter(interfaceDefinition -> MapUtils.isNotEmpty(interfaceDefinition.getOperations()))
538             .forEach(interfaceDefinition ->
539                 interfaceDefinition.getOperations()
540                     .forEach((operationType, operationValue) ->
541                         operationUiList.add(buildOperation(interfaceDefinition.getType(), operationType, (Map<String, Object>) operationValue))
542                     ));
543         return operationUiList;
544     }
545
546     private OperationUi buildOperation(final String interfaceType, final String operationType, final Map<String, Object> operationToscaMap) {
547         var operationUi = new OperationUi();
548         operationUi.setInterfaceType(interfaceType);
549         operationUi.setOperationType(operationType);
550         getImplementation(operationToscaMap).ifPresent(operationUi::setImplementation);
551         final List<PropertyAssignmentUi> operationsInputs = getOperationsInputs(operationToscaMap);
552         if (CollectionUtils.isNotEmpty(operationsInputs)) {
553             operationUi.setInputs(operationsInputs);
554         }
555         return operationUi;
556     }
557
558     @SuppressWarnings("unchecked")
559     private Map<String, GroupDefinition> getGroups(Map<String, Object> toscaJson, String model) {
560         Map<String, Object> mappedTopologyTemplate = (Map<String, Object>) findToscaElement(toscaJson, TOPOLOGY_TEMPLATE, ToscaElementTypeEnum.ALL)
561             .left().on(err -> new HashMap<>());
562         Map<String, Object> foundGroups = (Map<String, Object>) mappedTopologyTemplate.get(GROUPS.getElementName());
563         if (MapUtils.isNotEmpty(foundGroups)) {
564             Map<String, GroupDefinition> groups = foundGroups.entrySet().stream().map(groupToCreate -> createGroup(groupToCreate, model))
565                 .collect(Collectors.toMap(GroupDefinition::getName, g -> g));
566             Map<String, Object> substitutionMappings = getSubstitutionMappings(toscaJson);
567             if (capabilitiesSubstitutionMappingsExist(substitutionMappings)) {
568                 groups.forEach((key, value) -> updateCapabilitiesNames(value,
569                     getNamesToUpdate(key, (Map<String, List<String>>) substitutionMappings.get(CAPABILITIES.getElementName()))));
570             }
571             return groups;
572         }
573         return new HashMap<>();
574     }
575
576     private void updateCapabilitiesNames(GroupDefinition group, Map<String, String> capabilityNames) {
577         if (MapUtils.isNotEmpty(group.getCapabilities())) {
578             group.getCapabilities().values().stream().flatMap(Collection::stream).filter(cap -> capabilityNames.containsKey(cap.getName()))
579                 .forEach(cap -> cap.setName(capabilityNames.get(cap.getName())));
580         }
581     }
582
583     private Map<String, String> getNamesToUpdate(String name, Map<String, List<String>> pair) {
584         return pair.entrySet().stream().filter(e -> e.getValue().get(SUB_MAPPING_CAPABILITY_OWNER_NAME_IDX).equalsIgnoreCase(name))
585             .collect(Collectors.toMap(e -> e.getValue().get(SUB_MAPPING_CAPABILITY_NAME_IDX), Map.Entry::getKey, (n1, n2) -> n1));
586     }
587
588     private boolean capabilitiesSubstitutionMappingsExist(Map<String, Object> substitutionMappings) {
589         return substitutionMappings != null && substitutionMappings.containsKey(CAPABILITIES.getElementName());
590     }
591
592     private GroupDefinition createGroup(Map.Entry<String, Object> groupNameValue, String model) {
593         GroupDefinition group = new GroupDefinition();
594         group.setName(groupNameValue.getKey());
595         try {
596             if (groupNameValue.getValue() instanceof Map) {
597                 Map<String, Object> groupTemplateJsonMap = (Map<String, Object>) groupNameValue.getValue();
598                 validateAndFillGroup(group, groupTemplateJsonMap, model);
599                 validateUpdateGroupProperties(group, groupTemplateJsonMap);
600                 validateUpdateGroupCapabilities(group, groupTemplateJsonMap);
601             } else {
602                 rollbackWithException(ActionStatus.NOT_TOPOLOGY_TOSCA_TEMPLATE);
603             }
604         } catch (ClassCastException e) {
605             log.debug("#createGroup - Failed to create the group {}. The exception occurres", groupNameValue.getKey(), e);
606             rollbackWithException(ActionStatus.INVALID_YAML);
607         }
608         return group;
609     }
610
611     private Map<String, CapabilityDefinition> addCapabilities(Map<String, CapabilityDefinition> cap, Map<String, CapabilityDefinition> otherCap) {
612         cap.putAll(otherCap);
613         return cap;
614     }
615
616     private Map<String, CapabilityDefinition> addCapability(CapabilityDefinition cap) {
617         Map<String, CapabilityDefinition> map = Maps.newHashMap();
618         map.put(cap.getName(), cap);
619         return map;
620     }
621
622     private void setMembers(GroupDefinition groupInfo, Map<String, Object> groupTemplateJsonMap) {
623         if (groupTemplateJsonMap.containsKey(MEMBERS.getElementName())) {
624             Object members = groupTemplateJsonMap.get(MEMBERS.getElementName());
625             if (members != null) {
626                 if (members instanceof List) {
627                     setMembersFromList(groupInfo, (List<?>) members);
628                 } else {
629                     log.debug("The 'members' member is not of type list under group {}", groupInfo.getName());
630                     rollbackWithException(ActionStatus.NOT_TOPOLOGY_TOSCA_TEMPLATE);
631                 }
632             }
633         }
634     }
635
636     private void setMembersFromList(GroupDefinition groupInfo, List<?> membersAsList) {
637         groupInfo.setMembers(membersAsList.stream().collect(Collectors.toMap(Object::toString, member -> "")));
638     }
639
640     @SuppressWarnings("unchecked")
641     private void validateUpdateGroupProperties(GroupDefinition groupInfo, Map<String, Object> groupTemplateJsonMap) {
642         if (groupTemplateJsonMap.containsKey(PROPERTIES.getElementName())) {
643             Object propertiesElement = groupTemplateJsonMap.get(PROPERTIES.getElementName());
644             if (propertiesElement instanceof Map) {
645                 mergeGroupProperties(groupInfo, (Map<String, Object>) propertiesElement);
646             }
647         }
648     }
649
650     private void mergeGroupProperties(final GroupDefinition groupDefinition, final Map<String, Object> parsedProperties) {
651         if (CollectionUtils.isEmpty(groupDefinition.getProperties())) {
652             return;
653         }
654         validateGroupProperties(parsedProperties, groupDefinition);
655         groupDefinition.getProperties().stream()
656             .filter(property -> parsedProperties.containsKey(property.getName()))
657             .forEach(property -> mergeGroupProperty(property, parsedProperties.get(property.getName())));
658     }
659
660     private void mergeGroupProperty(final PropertyDataDefinition property, final Object propertyYaml) {
661         final UploadPropInfo uploadPropInfo = buildProperty(property.getName(), propertyYaml);
662         property.setToscaFunction(uploadPropInfo.getToscaFunction());
663         property.setSubPropertyToscaFunctions(uploadPropInfo.getSubPropertyToscaFunctions());
664         property.setValue(convertPropertyValue(ToscaPropertyType.isValidType(property.getType()), uploadPropInfo.getValue()));
665         property.setGetInputValues(uploadPropInfo.getGet_input());
666     }
667
668     private String convertPropertyValue(ToscaPropertyType type, Object value) {
669         String convertedValue = null;
670         if (value != null) {
671             if (type == null || value instanceof Map || value instanceof List) {
672                 convertedValue = gson.toJson(value);
673             } else {
674                 convertedValue = value.toString();
675             }
676         }
677         return convertedValue;
678     }
679
680     private void setDescription(GroupDefinition groupInfo, Map<String, Object> groupTemplateJsonMap) {
681         if (groupTemplateJsonMap.containsKey(DESCRIPTION.getElementName())) {
682             groupInfo.setDescription((String) groupTemplateJsonMap.get(DESCRIPTION.getElementName()));
683         }
684     }
685
686     private void validateAndFillGroup(GroupDefinition groupInfo, Map<String, Object> groupTemplateJsonMap, String model) {
687         String type = (String) groupTemplateJsonMap.get(TYPE.getElementName());
688         if (StringUtils.isEmpty(type)) {
689             log.debug("#validateAndFillGroup - The 'type' member is not found under group {}", groupInfo.getName());
690             rollbackWithException(ActionStatus.GROUP_MISSING_GROUP_TYPE, groupInfo.getName());
691         }
692         groupInfo.setType(type);
693         GroupTypeDefinition groupType = groupTypeBusinessLogic.getLatestGroupTypeByType(type, model);
694         if (groupType == null) {
695             log.debug("#validateAndFillGroup - The group type {} not found", groupInfo.getName());
696             rollbackWithException(ActionStatus.GROUP_TYPE_IS_INVALID, type);
697         }
698         groupInfo.convertFromGroupProperties(groupType.getProperties());
699         groupInfo.convertCapabilityDefinitions(groupType.getCapabilities());
700         setDescription(groupInfo, groupTemplateJsonMap);
701         setMembers(groupInfo, groupTemplateJsonMap);
702     }
703
704     @SuppressWarnings("unchecked")
705     private void validateUpdateGroupCapabilities(GroupDefinition groupInfo, Map<String, Object> groupTemplateJsonMap) {
706         if (groupTemplateJsonMap.containsKey(CAPABILITIES.getElementName())) {
707             Object capabilities = groupTemplateJsonMap.get(CAPABILITIES.getElementName());
708             if (capabilities instanceof List) {
709                 validateUpdateCapabilities(groupInfo, ((List<Object>) capabilities).stream().map(o -> buildGroupCapability(groupInfo, o))
710                     .collect(Collectors.toMap(CapabilityDefinition::getType, this::addCapability, this::addCapabilities)));
711             } else if (capabilities instanceof Map) {
712                 validateUpdateCapabilities(groupInfo,
713                     ((Map<String, Object>) capabilities).entrySet().stream().map(e -> buildGroupCapability(groupInfo, e))
714                         .collect(Collectors.toMap(CapabilityDefinition::getType, this::addCapability, this::addCapabilities)));
715             } else {
716                 log.debug("#setCapabilities - Failed to import the capabilities of the group {}. ", groupInfo.getName());
717                 rollbackWithException(ActionStatus.INVALID_YAML);
718             }
719         }
720     }
721
722     private void validateUpdateCapabilities(GroupDefinition groupInfo, Map<String, Map<String, CapabilityDefinition>> capabilityInfo) {
723         validateGroupCapabilities(groupInfo, capabilityInfo);
724         groupInfo.updateCapabilitiesProperties(capabilityInfo);
725     }
726
727     private void validateGroupCapabilities(GroupDefinition group, Map<String, Map<String, CapabilityDefinition>> parsedCapabilities) {
728         if (MapUtils.isNotEmpty(parsedCapabilities)) {
729             if (MapUtils.isEmpty(group.getCapabilities())) {
730                 failOnMissingCapabilityTypes(group, Lists.newArrayList(parsedCapabilities.keySet()));
731             }
732             List<String> missingCapTypes = parsedCapabilities.keySet().stream().filter(ct -> !group.getCapabilities().containsKey(ct))
733                 .collect(toList());
734             if (CollectionUtils.isNotEmpty(missingCapTypes)) {
735                 failOnMissingCapabilityTypes(group, missingCapTypes);
736             }
737             group.getCapabilities().entrySet().forEach(e -> validateCapabilities(group, e.getValue(), parsedCapabilities.get(e.getKey())));
738         }
739     }
740
741     private void validateCapabilities(GroupDefinition group, List<CapabilityDefinition> capabilities,
742                                       Map<String, CapabilityDefinition> parsedCapabilities) {
743         List<String> allowedCapNames = capabilities.stream().map(CapabilityDefinition::getName).distinct().collect(toList());
744         List<String> missingCapNames = parsedCapabilities.keySet().stream().filter(c -> !allowedCapNames.contains(c)).collect(toList());
745         if (CollectionUtils.isNotEmpty(missingCapNames)) {
746             failOnMissingCapabilityNames(group, missingCapNames);
747         }
748         validateCapabilitiesProperties(capabilities, parsedCapabilities);
749     }
750
751     private void validateCapabilitiesProperties(List<CapabilityDefinition> capabilities, Map<String, CapabilityDefinition> parsedCapabilities) {
752         capabilities.forEach(c -> validateCapabilityProperties(c, parsedCapabilities.get(c.getName())));
753     }
754
755     private void validateCapabilityProperties(CapabilityDefinition capability, CapabilityDefinition parsedCapability) {
756         if (parsedCapability != null && parsedCapability.getProperties() != null) {
757             List<String> parsedPropertiesNames = parsedCapability.getProperties().stream().map(ComponentInstanceProperty::getName).collect(toList());
758             validateProperties(capability.getProperties().stream().map(PropertyDataDefinition::getName).collect(toList()), parsedPropertiesNames,
759                 ActionStatus.PROPERTY_NOT_FOUND, capability.getName(), capability.getType());
760         }
761     }
762
763     private void validateGroupProperties(Map<String, Object> parsedProperties, GroupDefinition groupInfo) {
764         List<String> parsedPropertiesNames = new ArrayList<>(parsedProperties.keySet());
765         validateProperties(groupInfo.getProperties().stream().map(PropertyDataDefinition::getName).collect(toList()), parsedPropertiesNames,
766             ActionStatus.GROUP_PROPERTY_NOT_FOUND, groupInfo.getName(), groupInfo.getType());
767     }
768
769     private void validateProperties(List<String> validProperties, List<String> parsedProperties, ActionStatus actionStatus, String name,
770                                     String type) {
771         if (CollectionUtils.isNotEmpty(parsedProperties)) {
772             verifyMissingProperties(actionStatus, name, type, parsedProperties.stream().filter(n -> !validProperties.contains(n)).collect(toList()));
773         }
774     }
775
776     private void verifyMissingProperties(ActionStatus actionStatus, String name, String type, List<String> missingProperties) {
777         if (CollectionUtils.isNotEmpty(missingProperties)) {
778             if (log.isDebugEnabled()) {
779                 log.debug("#validateProperties - Failed to validate properties. The properties {} are missing on {} of the type {}. ",
780                     missingProperties.toString(), name, type);
781             }
782             rollbackWithException(actionStatus, missingProperties.toString(), missingProperties.toString(), name, type);
783         }
784     }
785
786     @SuppressWarnings("unchecked")
787     private CapabilityDefinition buildGroupCapability(GroupDefinition groupInfo, Object capObject) {
788         if (!(capObject instanceof Map)) {
789             log.debug("#convertToGroupCapability - Failed to import the capability {}. ", capObject);
790             rollbackWithException(ActionStatus.INVALID_YAML);
791         }
792         return buildGroupCapability(groupInfo, ((Map<String, Object>) capObject).entrySet().iterator().next());
793     }
794
795     @SuppressWarnings("unchecked")
796     private CapabilityDefinition buildGroupCapability(GroupDefinition groupInfo, Map.Entry<String, Object> capEntry) {
797         CapabilityDefinition capability = new CapabilityDefinition();
798         capability.setOwnerType(CapabilityDataDefinition.OwnerType.GROUP);
799         capability.setName(capEntry.getKey());
800         capability.setParentName(capEntry.getKey());
801         capability.setOwnerId(groupInfo.getName());
802         if (!(capEntry.getValue() instanceof Map)) {
803             log.debug("#convertMapEntryToCapabilityDefinition - Failed to import the capability {}. ", capEntry.getKey());
804             rollbackWithException(ActionStatus.INVALID_YAML);
805         }
806         Map<String, Object> capabilityValue = (Map<String, Object>) capEntry.getValue();
807         String type = (String) capabilityValue.get(TYPE.getElementName());
808         if (StringUtils.isEmpty(type)) {
809             log.debug("#convertMapEntryToCapabilityDefinition - Failed to import the capability {}. Missing capability type. ", capEntry.getKey());
810             rollbackWithException(ActionStatus.INVALID_YAML);
811         }
812         capability.setType(type);
813         if (!(capabilityValue.get(PROPERTIES.getElementName()) instanceof Map)) {
814             log.debug("#convertMapEntryToCapabilityDefinition - Failed to import the capability {}. ", capEntry.getKey());
815             rollbackWithException(ActionStatus.INVALID_YAML);
816         }
817         Map<String, Object> properties = (Map<String, Object>) capabilityValue.get(PROPERTIES.getElementName());
818         capability.setProperties(properties.entrySet().stream().map(this::convertToProperty).collect(toList()));
819         return capability;
820     }
821
822     private ComponentInstanceProperty convertToProperty(Map.Entry<String, Object> e) {
823         ComponentInstanceProperty property = new ComponentInstanceProperty();
824         property.setName(e.getKey());
825         property.setValue((String) e.getValue());
826         return property;
827     }
828
829     @SuppressWarnings("unchecked")
830     private UploadComponentInstanceInfo buildModuleComponentInstanceInfo(
831         Map.Entry<String, Object> nodeTemplateJsonEntry,
832         Map<String, Object> substitutionMappings,
833         Map<String, String> createdNodesToscaResourceNames
834     ) {
835         UploadComponentInstanceInfo nodeTemplateInfo = new UploadComponentInstanceInfo();
836         nodeTemplateInfo.setName(nodeTemplateJsonEntry.getKey());
837         try {
838             if (nodeTemplateJsonEntry.getValue() instanceof String) {
839                 String nodeTemplateJsonString = (String) nodeTemplateJsonEntry.getValue();
840                 nodeTemplateInfo.setType(nodeTemplateJsonString);
841             } else if (nodeTemplateJsonEntry.getValue() instanceof Map) {
842                 Map<String, Object> nodeTemplateJsonMap = (Map<String, Object>) nodeTemplateJsonEntry.getValue();
843                 setToscaResourceType(createdNodesToscaResourceNames, nodeTemplateInfo, nodeTemplateJsonMap);
844                 setRequirements(nodeTemplateInfo, nodeTemplateJsonMap);
845                 setCapabilities(nodeTemplateInfo, nodeTemplateJsonMap);
846                 setArtifacts(nodeTemplateInfo, nodeTemplateJsonMap);
847                 updateProperties(nodeTemplateInfo, nodeTemplateJsonMap);
848                 updateAttributes(nodeTemplateInfo, nodeTemplateJsonMap);
849                 updateInterfaces(nodeTemplateInfo, nodeTemplateJsonMap);
850                 setDirectives(nodeTemplateInfo, nodeTemplateJsonMap);
851                 setNodeFilter(nodeTemplateInfo, nodeTemplateJsonMap);
852                 setSubstitutions(substitutionMappings, nodeTemplateInfo);
853                 setOccurrencesAndInstanceCount(nodeTemplateInfo, nodeTemplateJsonMap);
854             } else {
855                 rollbackWithException(ActionStatus.NOT_TOPOLOGY_TOSCA_TEMPLATE);
856             }
857         } catch (ClassCastException e) {
858             BeEcompErrorManager.getInstance().logBeSystemError("Import Resource - create capability");
859             log.debug("error when creating capability, message:{}", e.getMessage(), e);
860             rollbackWithException(ActionStatus.INVALID_YAML);
861         }
862         return nodeTemplateInfo;
863     }
864
865     @SuppressWarnings("unchecked")
866     private void setSubstitutions(Map<String, Object> substitutionMappings, UploadComponentInstanceInfo nodeTemplateInfo) {
867         if (substitutionMappings != null) {
868             if (substitutionMappings.containsKey(CAPABILITIES.getElementName())) {
869                 nodeTemplateInfo.setCapabilitiesNamesToUpdate(getNamesToUpdate(nodeTemplateInfo.getName(),
870                     (Map<String, List<String>>) substitutionMappings.get(CAPABILITIES.getElementName())));
871             }
872             if (substitutionMappings.containsKey(REQUIREMENTS.getElementName())) {
873                 nodeTemplateInfo.setRequirementsNamesToUpdate(getNamesToUpdate(nodeTemplateInfo.getName(),
874                     (Map<String, List<String>>) substitutionMappings.get(REQUIREMENTS.getElementName())));
875             }
876         }
877     }
878
879     private void updateProperties(UploadComponentInstanceInfo nodeTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
880         if (nodeTemplateJsonMap.containsKey(PROPERTIES.getElementName())) {
881             Map<String, List<UploadPropInfo>> properties =
882                 buildPropModuleFromYaml((Map<String, Object>) nodeTemplateJsonMap.get(PROPERTIES.getElementName()));
883             if (!properties.isEmpty()) {
884                 nodeTemplateInfo.setProperties(properties);
885             }
886         }
887     }
888
889     private void updateAttributes(UploadComponentInstanceInfo nodeTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
890         if (nodeTemplateJsonMap.containsKey(ATTRIBUTES.getElementName())) {
891             Map<String, UploadAttributeInfo> attributes = buildAttributeModuleFromYaml(nodeTemplateJsonMap);
892             if (!attributes.isEmpty()) {
893                 nodeTemplateInfo.setAttributes(attributes);
894             }
895         }
896     }
897
898     private void updateInterfaces(
899         UploadComponentInstanceInfo nodeTemplateInfo,
900         Map<String, Object> nodeTemplateJsonMap
901     ) {
902         if (nodeTemplateJsonMap.containsKey(INTERFACES.getElementName())) {
903             Map<String, UploadInterfaceInfo> interfaces = buildInterfacesModuleFromYaml(
904                 nodeTemplateJsonMap
905             );
906             if (!interfaces.isEmpty()) {
907                 nodeTemplateInfo.setInterfaces(interfaces);
908             }
909         }
910     }
911
912     private void setCapabilities(UploadComponentInstanceInfo nodeTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
913         if (nodeTemplateJsonMap.containsKey(CAPABILITIES.getElementName())) {
914             Map<String, List<UploadCapInfo>> eitherCapRes = createCapModuleFromYaml(nodeTemplateJsonMap);
915             if (!eitherCapRes.isEmpty()) {
916                 nodeTemplateInfo.setCapabilities(eitherCapRes);
917             }
918         }
919     }
920
921     private void setArtifacts(UploadComponentInstanceInfo nodeTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
922         if (nodeTemplateJsonMap.containsKey(ARTIFACTS.getElementName())) {
923             Map<String, Map<String, UploadArtifactInfo>> eitherArtifactsRes = createArtifactsModuleFromYaml(nodeTemplateJsonMap);
924             if (!eitherArtifactsRes.isEmpty()) {
925                 nodeTemplateInfo.setArtifacts(eitherArtifactsRes);
926             }
927         }
928     }
929
930     private void setRequirements(UploadComponentInstanceInfo nodeTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
931         if (nodeTemplateJsonMap.containsKey(REQUIREMENTS.getElementName())) {
932             Map<String, List<UploadReqInfo>> regResponse = createReqModuleFromYaml(nodeTemplateJsonMap, nodeTemplateInfo.getName());
933             if (!regResponse.isEmpty()) {
934                 nodeTemplateInfo.setRequirements(regResponse);
935             }
936         }
937     }
938
939     private void setToscaResourceType(Map<String, String> createdNodesToscaResourceNames, UploadComponentInstanceInfo nodeTemplateInfo,
940                                       Map<String, Object> nodeTemplateJsonMap) {
941         if (nodeTemplateJsonMap.containsKey(TYPE.getElementName())) {
942             String toscaResourceType = (String) nodeTemplateJsonMap.get(TYPE.getElementName());
943             if (createdNodesToscaResourceNames.containsKey(toscaResourceType)) {
944                 toscaResourceType = createdNodesToscaResourceNames.get(toscaResourceType);
945             }
946             nodeTemplateInfo.setType(toscaResourceType);
947         }
948     }
949
950     private void setDirectives(UploadComponentInstanceInfo nodeTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
951         List<String> directives = (List<String>) nodeTemplateJsonMap.get(TypeUtils.ToscaTagNamesEnum.DIRECTIVES.getElementName());
952         nodeTemplateInfo.setDirectives(directives);
953     }
954
955     private void setNodeFilter(UploadComponentInstanceInfo nodeTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
956         if (nodeTemplateJsonMap.containsKey(TypeUtils.ToscaTagNamesEnum.NODE_FILTER.getElementName())) {
957             nodeTemplateInfo.setUploadNodeFilterInfo(new NodeFilterUploadCreator()
958                 .createNodeFilterData(nodeTemplateJsonMap.get(TypeUtils.ToscaTagNamesEnum.NODE_FILTER.getElementName())));
959         }
960     }
961
962     @SuppressWarnings("unchecked")
963     private void setOccurrencesAndInstanceCount(UploadComponentInstanceInfo nodeTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
964         if (nodeTemplateJsonMap.containsKey(TypeUtils.ToscaTagNamesEnum.OCCURRENCES.getElementName())) {
965             List<Object> occurrences = (List<Object>) nodeTemplateJsonMap.get(TypeUtils.ToscaTagNamesEnum.OCCURRENCES.getElementName());
966             nodeTemplateInfo.setMinOccurrences(occurrences.get(0).toString());
967             nodeTemplateInfo.setMaxOccurrences(occurrences.get(1).toString());
968         }
969         if (nodeTemplateJsonMap.containsKey(TypeUtils.ToscaTagNamesEnum.INSTANCE_COUNT.getElementName())) {
970             Object instanceCount = nodeTemplateJsonMap.get(TypeUtils.ToscaTagNamesEnum.INSTANCE_COUNT.getElementName());
971             if (instanceCount instanceof Map) {
972                 String instanceCountAsString = "{get_input:" + (String)((Map)instanceCount).get("get_input") + "}";
973                 nodeTemplateInfo.setInstanceCount(instanceCountAsString);
974             } else {
975                 nodeTemplateInfo.setInstanceCount(instanceCount.toString());
976             }
977         }
978     }
979
980     @SuppressWarnings("unchecked")
981     private Map<String, List<UploadReqInfo>> createReqModuleFromYaml(Map<String, Object> nodeTemplateJsonMap, String nodeName) {
982         Map<String, List<UploadReqInfo>> moduleRequirements = new HashMap<>();
983         Either<List<Object>, ResultStatusEnum> requirementsListRes = findFirstToscaListElement(nodeTemplateJsonMap, REQUIREMENTS);
984         if (requirementsListRes.isLeft()) {
985             for (Object jsonReqObj : requirementsListRes.left().value()) {
986                 String reqName = ((Map<String, Object>) jsonReqObj).keySet().iterator().next();
987                 Object reqJson = ((Map<String, Object>) jsonReqObj).get(reqName);
988                 addModuleNodeTemplateReq(moduleRequirements, reqJson, reqName, nodeName);
989             }
990         } else {
991             Either<Map<String, Object>, ResultStatusEnum> requirementsMapRes = findFirstToscaMapElement(nodeTemplateJsonMap, REQUIREMENTS);
992             if (requirementsMapRes.isLeft()) {
993                 for (Map.Entry<String, Object> entry : requirementsMapRes.left().value().entrySet()) {
994                     String reqName = entry.getKey();
995                     Object reqJson = entry.getValue();
996                     addModuleNodeTemplateReq(moduleRequirements, reqJson, reqName, nodeName);
997                 }
998             }
999         }
1000         return moduleRequirements;
1001     }
1002
1003     private void addModuleNodeTemplateReq(Map<String, List<UploadReqInfo>> moduleRequirements, Object requirementJson, String requirementName,
1004                                           String nodeName) {
1005         UploadReqInfo requirement = buildModuleNodeTemplateReg(requirementJson, nodeName);
1006         requirement.setName(requirementName);
1007         if (moduleRequirements.containsKey(requirementName)) {
1008             moduleRequirements.get(requirementName).add(requirement);
1009         } else {
1010             List<UploadReqInfo> list = new ArrayList<>();
1011             list.add(requirement);
1012             moduleRequirements.put(requirementName, list);
1013         }
1014     }
1015
1016     @SuppressWarnings("unchecked")
1017     private Map<String, Map<String, UploadArtifactInfo>> createArtifactsModuleFromYaml(Map<String, Object> nodeTemplateJsonMap) {
1018         Map<String, Map<String, UploadArtifactInfo>> moduleArtifacts = new HashMap<>();
1019         Either<List<Object>, ResultStatusEnum> artifactsListRes = findFirstToscaListElement(nodeTemplateJsonMap, ARTIFACTS);
1020         if (artifactsListRes.isLeft()) {
1021             for (Object jsonArtifactObj : artifactsListRes.left().value()) {
1022                 String key = ((Map<String, Object>) jsonArtifactObj).keySet().iterator().next();
1023                 Object artifactJson = ((Map<String, Object>) jsonArtifactObj).get(key);
1024                 addModuleNodeTemplateArtifacts(moduleArtifacts, artifactJson, key);
1025             }
1026         } else {
1027             Either<Map<String, Map<String, Object>>, ResultStatusEnum> artifactsMapRes = findFirstToscaMapElement(nodeTemplateJsonMap, ARTIFACTS);
1028             if (artifactsMapRes.isLeft()) {
1029                 for (Map.Entry<String, Map<String, Object>> entry : artifactsMapRes.left().value().entrySet()) {
1030                     String artifactName = entry.getKey();
1031                     Object artifactJson = entry.getValue();
1032                     addModuleNodeTemplateArtifacts(moduleArtifacts, artifactJson, artifactName);
1033                 }
1034             }
1035         }
1036         return moduleArtifacts;
1037     }
1038
1039     private void addModuleNodeTemplateArtifacts(Map<String, Map<String, UploadArtifactInfo>> moduleArtifacts, Object artifactJson,
1040                                                 String artifactName) {
1041         UploadArtifactInfo artifact = buildModuleNodeTemplateArtifact(artifactJson);
1042         artifact.setName(artifactName);
1043         if (moduleArtifacts.containsKey(ARTIFACTS.getElementName())) {
1044             moduleArtifacts.get(ARTIFACTS.getElementName()).put(artifactName, artifact);
1045         } else {
1046             Map<String, UploadArtifactInfo> map = new HashMap<>();
1047             map.put(artifactName, artifact);
1048             moduleArtifacts.put(ARTIFACTS.getElementName(), map);
1049         }
1050     }
1051
1052     @SuppressWarnings("unchecked")
1053     private UploadArtifactInfo buildModuleNodeTemplateArtifact(Object artifactObject) {
1054         UploadArtifactInfo artifactTemplateInfo = new UploadArtifactInfo();
1055         if (artifactObject instanceof Map) {
1056             fillArtifact(artifactTemplateInfo, (Map<String, Object>) artifactObject);
1057         }
1058         return artifactTemplateInfo;
1059     }
1060
1061     private void fillArtifact(UploadArtifactInfo artifactTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
1062         if (nodeTemplateJsonMap.containsKey(TYPE.getElementName())) {
1063             artifactTemplateInfo.setType((String) nodeTemplateJsonMap.get(TYPE.getElementName()));
1064         }
1065         if (nodeTemplateJsonMap.containsKey(FILE.getElementName())) {
1066             artifactTemplateInfo.setFile((String) nodeTemplateJsonMap.get(FILE.getElementName()));
1067         }
1068         if (nodeTemplateJsonMap.containsKey(PROPERTIES.getElementName())) {
1069             Map<String, List<UploadPropInfo>> props =
1070                 buildPropModuleFromYaml((Map<String, Object>) nodeTemplateJsonMap.get(PROPERTIES.getElementName()));
1071             if (!props.isEmpty()) {
1072                 List<UploadPropInfo> properties = props.values().stream().flatMap(Collection::stream).collect(toList());
1073                 artifactTemplateInfo.setProperties(properties);
1074             }
1075         }
1076     }
1077
1078     @SuppressWarnings("unchecked")
1079     private Map<String, List<UploadCapInfo>> createCapModuleFromYaml(Map<String, Object> nodeTemplateJsonMap) {
1080         Map<String, List<UploadCapInfo>> moduleCap = new HashMap<>();
1081         Map<String, Object> capabilities = (Map<String, Object>) nodeTemplateJsonMap.get(CAPABILITIES.getElementName());
1082         if (MapUtils.isNotEmpty(capabilities)) {
1083             for (Map.Entry<String, Object> entry : capabilities.entrySet()) {
1084                 String capName = entry.getKey();
1085                 Object capJson = entry.getValue();
1086                 addModuleNodeTemplateCap(moduleCap, capJson, capName);
1087             }
1088         }
1089         return moduleCap;
1090     }
1091
1092     private void addModuleNodeTemplateCap(Map<String, List<UploadCapInfo>> moduleCap, Object capJson, String key) {
1093         UploadCapInfo capabilityDef = buildModuleNodeTemplateCap(capJson);
1094         capabilityDef.setKey(key);
1095         if (moduleCap.containsKey(key)) {
1096             moduleCap.get(key).add(capabilityDef);
1097         } else {
1098             List<UploadCapInfo> list = new ArrayList<>();
1099             list.add(capabilityDef);
1100             moduleCap.put(key, list);
1101         }
1102     }
1103
1104     @SuppressWarnings("unchecked")
1105     private UploadCapInfo buildModuleNodeTemplateCap(Object capObject) {
1106         UploadCapInfo capTemplateInfo = new UploadCapInfo();
1107         if (capObject instanceof String) {
1108             String nodeTemplateJsonString = (String) capObject;
1109             capTemplateInfo.setNode(nodeTemplateJsonString);
1110         } else if (capObject instanceof Map) {
1111             fillCapability(capTemplateInfo, (Map<String, Object>) capObject);
1112         }
1113         return capTemplateInfo;
1114     }
1115
1116     private void fillCapability(UploadCapInfo capTemplateInfo, Map<String, Object> nodeTemplateJsonMap) {
1117         if (nodeTemplateJsonMap.containsKey(NODE.getElementName())) {
1118             capTemplateInfo.setNode((String) nodeTemplateJsonMap.get(NODE.getElementName()));
1119         }
1120         if (nodeTemplateJsonMap.containsKey(TYPE.getElementName())) {
1121             capTemplateInfo.setType((String) nodeTemplateJsonMap.get(TYPE.getElementName()));
1122         }
1123         if (nodeTemplateJsonMap.containsKey(VALID_SOURCE_TYPES.getElementName())) {
1124             Either<List<Object>, ResultStatusEnum> validSourceTypesRes = findFirstToscaListElement(nodeTemplateJsonMap, VALID_SOURCE_TYPES);
1125             if (validSourceTypesRes.isLeft()) {
1126                 capTemplateInfo.setValidSourceTypes(validSourceTypesRes.left().value().stream().map(Object::toString).collect(toList()));
1127             }
1128         }
1129         if (nodeTemplateJsonMap.containsKey(PROPERTIES.getElementName())) {
1130             Map<String, List<UploadPropInfo>> props =
1131                 buildPropModuleFromYaml((Map<String, Object>) nodeTemplateJsonMap.get(PROPERTIES.getElementName()));
1132             if (!props.isEmpty()) {
1133                 List<UploadPropInfo> properties = props.values().stream().flatMap(Collection::stream).collect(toList());
1134                 capTemplateInfo.setProperties(properties);
1135             }
1136         }
1137     }
1138
1139     @SuppressWarnings("unchecked")
1140     private UploadReqInfo buildModuleNodeTemplateReg(Object regObject, String nodeName) {
1141         UploadReqInfo regTemplateInfo = new UploadReqInfo();
1142         if (regObject instanceof String) {
1143             String nodeTemplateJsonString = (String) regObject;
1144             regTemplateInfo.setNode(nodeTemplateJsonString);
1145         } else if (regObject instanceof Map) {
1146             Map<String, Object> nodeTemplateJsonMap = (Map<String, Object>) regObject;
1147             if (nodeTemplateJsonMap.containsKey(NODE.getElementName())) {
1148                 regTemplateInfo.setNode((String) nodeTemplateJsonMap.get(NODE.getElementName()));
1149             }
1150             if (nodeTemplateJsonMap.containsKey(CAPABILITY.getElementName())) {
1151                 regTemplateInfo.setCapabilityName((String) nodeTemplateJsonMap.get(CAPABILITY.getElementName()));
1152             }
1153             if (nodeTemplateJsonMap.containsKey(RELATIONSHIP.getElementName())) {
1154                 final String template = (String) nodeTemplateJsonMap.get(RELATIONSHIP.getElementName());
1155                 if (StringUtils.isNotEmpty(nodeName) && template.contains(nodeName)) {
1156                     regTemplateInfo.setRelationshipTemplate(template);
1157                 }
1158             }
1159         }
1160         return regTemplateInfo;
1161     }
1162
1163     private Map<String, UploadAttributeInfo> buildAttributeModuleFromYaml(
1164         Map<String, Object> nodeTemplateJsonMap) {
1165         Map<String, UploadAttributeInfo> moduleAttribute = new HashMap<>();
1166         Either<Map<String, Object>, ResultStatusEnum> toscaAttributes = findFirstToscaMapElement(nodeTemplateJsonMap, ATTRIBUTES);
1167         if (toscaAttributes.isLeft()) {
1168             Map<String, Object> jsonAttributes = toscaAttributes.left().value();
1169             for (Map.Entry<String, Object> jsonAttributeObj : jsonAttributes.entrySet()) {
1170                 UploadAttributeInfo attributeDef = buildAttribute(jsonAttributeObj.getKey(), jsonAttributeObj.getValue());
1171                 moduleAttribute.put(attributeDef.getName(), attributeDef);
1172             }
1173         }
1174         return moduleAttribute;
1175     }
1176
1177     private UploadAttributeInfo buildAttribute(String attributeName, Object attributeValue) {
1178         UploadAttributeInfo attributeDef = new UploadAttributeInfo();
1179         attributeDef.setValue(attributeValue);
1180         attributeDef.setName(attributeName);
1181         return attributeDef;
1182     }
1183
1184     private Map<String, List<UploadPropInfo>> buildPropModuleFromYaml(final Map<String, Object> propertyMap) {
1185         final Map<String, List<UploadPropInfo>> moduleProp = new HashMap<>();
1186         propertyMap.entrySet().forEach(propertyMapEntry -> addProperty(moduleProp, propertyMapEntry));
1187         return moduleProp;
1188     }
1189
1190     private Map<String, UploadInterfaceInfo> buildInterfacesModuleFromYaml(
1191         Map<String, Object> nodeTemplateJsonMap
1192     ) {
1193         Map<String, UploadInterfaceInfo> moduleInterfaces = new HashMap<>();
1194         Either<Map<String, Object>, ResultStatusEnum> toscaInterfaces = findFirstToscaMapElement(nodeTemplateJsonMap, INTERFACES);
1195         if (toscaInterfaces.isLeft()) {
1196             Map<String, Object> jsonInterfaces = toscaInterfaces.left().value();
1197             for (Map.Entry<String, Object> jsonInterfacesObj : jsonInterfaces.entrySet()) {
1198                 addInterfaces(moduleInterfaces, jsonInterfacesObj);
1199             }
1200         }
1201         return moduleInterfaces;
1202     }
1203
1204     private void addProperty(Map<String, List<UploadPropInfo>> moduleProp, Map.Entry<String, Object> jsonPropObj) {
1205         UploadPropInfo propertyDef = buildProperty(jsonPropObj.getKey(), jsonPropObj.getValue());
1206         if (moduleProp.containsKey(propertyDef.getName())) {
1207             moduleProp.get(propertyDef.getName()).add(propertyDef);
1208         } else {
1209             List<UploadPropInfo> list = new ArrayList<>();
1210             list.add(propertyDef);
1211             moduleProp.put(propertyDef.getName(), list);
1212         }
1213     }
1214
1215     private void addInterfaces(Map<String, UploadInterfaceInfo> moduleInterface, Map.Entry<String, Object> jsonPropObj) {
1216         UploadInterfaceInfo interfaceInfo = buildInterface(jsonPropObj.getKey(), jsonPropObj.getValue());
1217         moduleInterface.put(jsonPropObj.getKey(), interfaceInfo);
1218     }
1219
1220     @SuppressWarnings("unchecked")
1221     private UploadPropInfo buildProperty(String propName, Object propValueObj) {
1222         final var propertyDef = new UploadPropInfo();
1223         propertyDef.setValue(propValueObj);
1224         propertyDef.setName(propName);
1225         if (propValueObj instanceof Map) {
1226             final Map<String, Object> propValueMap = (Map<String, Object>) propValueObj;
1227             if (propValueMap.containsKey(TYPE.getElementName())) {
1228                 propertyDef.setType(propValueMap.get(TYPE.getElementName()).toString());
1229             }
1230             if (containsGetInput(propValueObj)) {
1231                 fillInputRecursively(propName, propValueMap, propertyDef);
1232             }
1233             if (toscaFunctionYamlParsingHandler.isPropertyValueToscaFunction(propValueObj)) {
1234                 toscaFunctionYamlParsingHandler.buildToscaFunctionBasedOnPropertyValue(propValueMap).ifPresent(propertyDef::setToscaFunction);
1235             } else {
1236                 final Collection<SubPropertyToscaFunction> subPropertyToscaFunctions =
1237                     buildSubPropertyToscaFunctions(propValueMap, new ArrayList<>());
1238                 if (CollectionUtils.isNotEmpty(subPropertyToscaFunctions)) {
1239                     Collection<SubPropertyToscaFunction> existingSubPropertyToscaFunctions = propertyDef.getSubPropertyToscaFunctions();
1240                     if (existingSubPropertyToscaFunctions == null) {
1241                         propertyDef.setSubPropertyToscaFunctions(subPropertyToscaFunctions);
1242                     } else {
1243                         propertyDef.getSubPropertyToscaFunctions().addAll(subPropertyToscaFunctions);
1244                     }
1245                 }
1246             }
1247             if (propValueMap.containsKey(DESCRIPTION.getElementName())) {
1248                 propertyDef.setDescription((propValueMap).get(DESCRIPTION.getElementName()).toString());
1249             }
1250             if (propValueMap.containsKey(DEFAULT_VALUE.getElementName())) {
1251                 propertyDef.setValue(propValueMap.get(DEFAULT_VALUE.getElementName()));
1252             }
1253             if (propValueMap.containsKey(IS_PASSWORD.getElementName())) {
1254                 propertyDef.setPassword(Boolean.getBoolean(propValueMap.get(IS_PASSWORD.getElementName()).toString()));
1255             } else {
1256                 propertyDef.setValue(propValueObj);
1257             }
1258         } else if (propValueObj instanceof List) {
1259             fillInputsListRecursively(propertyDef, (List<Object>) propValueObj);
1260             propertyDef.setValue(propValueObj);
1261         }
1262         return propertyDef;
1263     }
1264
1265     private Collection<SubPropertyToscaFunction> buildSubPropertyToscaFunctions(final Map<String, Object> propValueMap, final List<String> path) {
1266         Collection<SubPropertyToscaFunction> subPropertyToscaFunctions = new ArrayList<>();
1267         propValueMap.entrySet().stream().filter(entry -> entry.getValue() instanceof Map).forEach(entry -> {
1268             List<String> subPropertyPath = new ArrayList<>(path);
1269             subPropertyPath.add(entry.getKey());
1270             if (ToscaFunctionType.findType(((Map<String, Object>) entry.getValue()).keySet().iterator().next()).isPresent()) {
1271                 Optional<ToscaFunction> toscaFunction =
1272                     toscaFunctionYamlParsingHandler.buildToscaFunctionBasedOnPropertyValue((Map) entry.getValue());
1273                 if (toscaFunction.isPresent()) {
1274                     SubPropertyToscaFunction subPropertyToscaFunction = new SubPropertyToscaFunction();
1275                     subPropertyToscaFunction.setToscaFunction(toscaFunction.get());
1276                     subPropertyToscaFunction.setSubPropertyPath(subPropertyPath);
1277                     subPropertyToscaFunctions.add(subPropertyToscaFunction);
1278                 }
1279             } else {
1280                 subPropertyToscaFunctions.addAll(buildSubPropertyToscaFunctions((Map<String, Object>) entry.getValue(), subPropertyPath));
1281             }
1282         });
1283         return subPropertyToscaFunctions;
1284     }
1285
1286     private UploadInterfaceInfo buildInterface(String interfaceName, Object interfaceValue) {
1287         UploadInterfaceInfo interfaceDef = new UploadInterfaceInfo();
1288         interfaceDef.setValue(interfaceValue);
1289         interfaceDef.setName(interfaceName);
1290         interfaceDef.setKey(interfaceName);
1291         Map<String, OperationDataDefinition> operations = new HashMap<>();
1292         if (interfaceValue instanceof Map) {
1293             Map<String, Object> operationsMap = (Map<String, Object>) interfaceValue;
1294             for (Map.Entry<String, Object> operationEntry : operationsMap.entrySet()) {
1295                 OperationDataDefinition operationDef = new OperationDataDefinition();
1296                 operationDef.setName(operationEntry.getKey());
1297                 Map<String, Object> operationValue = (Map<String, Object>) operationEntry.getValue();
1298                 if (operationValue.containsKey(DESCRIPTION.getElementName())) {
1299                     operationDef.setDescription(operationValue.get(DESCRIPTION.getElementName()).toString());
1300                 }
1301                 operationDef.setImplementation(handleOperationImplementation(operationValue).orElse(new ArtifactDataDefinition()));
1302                 if (operationValue.containsKey(INPUTS.getElementName())) {
1303                     final Map<String, Object> interfaceInputs = (Map<String, Object>) operationValue.get(INPUTS.getElementName());
1304                     operationDef.setInputs(handleInterfaceOperationInputs(interfaceInputs));
1305                 }
1306                 if (operationValue.containsKey(MILESTONES.getElementName())) {
1307                     final Map<String, Object> interfaceMilestones = (Map<String, Object>) operationValue.get(MILESTONES.getElementName());
1308                     operationDef.setMilestones(interfaceDefinitionHandler.handleInterfaceOperationMilestones(interfaceMilestones));
1309                 }
1310                 operations.put(operationEntry.getKey(), operationDef);
1311             }
1312             interfaceDef.setOperations(operations);
1313             if (operationsMap.containsKey(TYPE.getElementName())) {
1314                 interfaceDef.setType(((Map<String, Object>) interfaceValue).get(TYPE.getElementName()).toString());
1315             }
1316         }
1317         return interfaceDef;
1318     }
1319
1320     private ListDataDefinition<OperationInputDefinition> handleInterfaceOperationInputs(final Map<String, Object> interfaceInputs) {
1321         final ListDataDefinition<OperationInputDefinition> inputs = new ListDataDefinition<>();
1322         for (final Entry<String, Object> interfaceInput : interfaceInputs.entrySet()) {
1323             final OperationInputDefinition operationInput = new OperationInputDefinition();
1324             operationInput.setUniqueId(UUID.randomUUID().toString());
1325             operationInput.setInputId(operationInput.getUniqueId());
1326             operationInput.setName(interfaceInput.getKey());
1327
1328             handleInputToscaDefinition(interfaceInput.getKey(), interfaceInput.getValue(), operationInput);
1329             inputs.add(operationInput);
1330         }
1331         return inputs;
1332     }
1333
1334     private void handleInputToscaDefinition(
1335         final String inputName,
1336         final Object value,
1337         final OperationInputDefinition operationInput
1338     ) {
1339         if (value instanceof Map) {
1340             final Map<String, Object> valueMap = (Map<String, Object>) value;
1341             log.debug("Creating interface operation input '{}'", inputName);
1342             Type type = new TypeToken<LinkedHashMap<String, Object>>() {
1343             }.getType();
1344             String stringValue = gson.toJson(value, type);
1345             if (toscaFunctionYamlParsingHandler.isPropertyValueToscaFunction(value)) {
1346                 toscaFunctionYamlParsingHandler.buildToscaFunctionBasedOnPropertyValue((Map<String, Object>) value)
1347                     .ifPresent(operationInput::setToscaFunction);
1348             } else {
1349                 final Collection<SubPropertyToscaFunction> subPropertyToscaFunctions = buildSubPropertyToscaFunctions(valueMap, new ArrayList<>());
1350                 if (CollectionUtils.isNotEmpty(subPropertyToscaFunctions)) {
1351                     Collection<SubPropertyToscaFunction> existingSubPropertyToscaFunctions = operationInput.getSubPropertyToscaFunctions();
1352                     if (existingSubPropertyToscaFunctions == null) {
1353                         operationInput.setSubPropertyToscaFunctions(subPropertyToscaFunctions);
1354                     } else {
1355                         operationInput.getSubPropertyToscaFunctions().addAll(subPropertyToscaFunctions);
1356                     }
1357                 }
1358             }
1359             operationInput.setValue(stringValue);
1360         }
1361         if (value instanceof String) {
1362             final String stringValue = (String) value;
1363             operationInput.setDefaultValue(stringValue);
1364             operationInput.setToscaDefaultValue(stringValue);
1365             operationInput.setValue(stringValue);
1366         }
1367         operationInput.setType("string");
1368         if (operationInput.getValue() == null) {
1369             operationInput.setValue(String.valueOf(value));
1370         }
1371     }
1372
1373     private Optional<ArtifactDataDefinition> handleOperationImplementation(
1374         final Map<String, Object> operationDefinitionMap
1375     ) {
1376         if (!operationDefinitionMap.containsKey(IMPLEMENTATION.getElementName())) {
1377             return Optional.empty();
1378         }
1379         final ArtifactDataDefinition artifactDataDefinition = new ArtifactDataDefinition();
1380         if (operationDefinitionMap.get(IMPLEMENTATION.getElementName()) instanceof Map &&
1381             ((Map) operationDefinitionMap.get(IMPLEMENTATION.getElementName())).containsKey("primary")) {
1382
1383             final Object primary = ((Map) operationDefinitionMap.get(IMPLEMENTATION.getElementName())).get("primary");
1384             if (primary instanceof Map) {
1385                 Map<String, Object> implDetails = (Map) primary;
1386
1387                 if (implDetails.get("file") != null) {
1388                     final String file = implDetails.get("file").toString();
1389                     artifactDataDefinition.setArtifactName(generateArtifactName(file));
1390                 }
1391                 if (implDetails.get("type") != null) {
1392                     artifactDataDefinition.setArtifactType(implDetails.get("type").toString());
1393                 }
1394                 if (implDetails.get("artifact_version") != null) {
1395                     artifactDataDefinition.setArtifactVersion(implDetails.get("artifact_version").toString());
1396                 }
1397
1398                 if (implDetails.get("properties") instanceof Map) {
1399                     Map<String, Object> properties = (Map<String, Object>) implDetails.get("properties");
1400                     properties.forEach((k, v) -> {
1401                         ToscaPropertyType type = getTypeFromObject(v);
1402                         if (type != null) {
1403                             PropertyDataDefinition propertyDef = new PropertyDataDefinition();
1404                             propertyDef.setName(k);
1405                             propertyDef.setValue(v.toString());
1406                             artifactDataDefinition.addProperty(propertyDef);
1407                         }
1408                     });
1409                 }
1410             } else {
1411                 artifactDataDefinition.setArtifactName(generateArtifactName(primary.toString()));
1412             }
1413         }
1414
1415         if (operationDefinitionMap.get(IMPLEMENTATION.getElementName()) instanceof Map &&
1416             ((Map) operationDefinitionMap.get(IMPLEMENTATION.getElementName())).containsKey("timeout")) {
1417             final Object timeOut = ((Map) operationDefinitionMap.get(IMPLEMENTATION.getElementName())).get("timeout");
1418             artifactDataDefinition.setTimeout((Integer)timeOut);
1419         }
1420
1421         if (operationDefinitionMap.get(IMPLEMENTATION.getElementName()) instanceof String) {
1422             final String implementation = (String) operationDefinitionMap.get(IMPLEMENTATION.getElementName());
1423             artifactDataDefinition.setArtifactName(generateArtifactName(implementation));
1424         }
1425         return Optional.of(artifactDataDefinition);
1426     }
1427
1428     private String generateArtifactName(final String name) {
1429         if (OperationArtifactUtil.artifactNameIsALiteralValue(name)) {
1430             return name;
1431         } else {
1432             return QUOTE + name + QUOTE;
1433         }
1434     }
1435
1436     private ToscaPropertyType getTypeFromObject(final Object value) {
1437         if (value instanceof String) {
1438             return ToscaPropertyType.STRING;
1439         }
1440         if (value instanceof Integer) {
1441             return ToscaPropertyType.INTEGER;
1442         }
1443         if (value instanceof Boolean) {
1444             return ToscaPropertyType.BOOLEAN;
1445         }
1446         if (value instanceof Float || value instanceof Double) {
1447             return ToscaPropertyType.FLOAT;
1448         }
1449         return null;
1450     }
1451
1452     @SuppressWarnings("unchecked")
1453     private boolean containsGetInput(Object propValue) {
1454         return ((Map<String, Object>) propValue).containsKey(GET_INPUT.getElementName()) || ImportUtils.containsGetInput(propValue);
1455     }
1456
1457     @SuppressWarnings("unchecked")
1458     private void fillInputsListRecursively(UploadPropInfo propertyDef, List<Object> propValueList) {
1459         int index = 0;
1460         for (Object objValue : propValueList) {
1461             if (objValue instanceof Map) {
1462                 Map<String, Object> objMap = (Map<String, Object>) objValue;
1463                 Map<String, Object> propValueMap = new HashMap<>();
1464                 propValueMap.put(String.valueOf(index), objValue);
1465                 final Collection<SubPropertyToscaFunction> subPropertyToscaFunctions =
1466                     buildSubPropertyToscaFunctions(propValueMap, new ArrayList<>());
1467                 if (CollectionUtils.isNotEmpty(subPropertyToscaFunctions)) {
1468                     Collection<SubPropertyToscaFunction> existingSubPropertyToscaFunctions = propertyDef.getSubPropertyToscaFunctions();
1469                     if (existingSubPropertyToscaFunctions == null) {
1470                         propertyDef.setSubPropertyToscaFunctions(subPropertyToscaFunctions);
1471                     } else {
1472                         propertyDef.getSubPropertyToscaFunctions().addAll(subPropertyToscaFunctions);
1473                     }
1474                 }
1475                 if (objMap.containsKey(GET_INPUT.getElementName())) {
1476                     fillInputRecursively(propertyDef.getName(), objMap, propertyDef);
1477                 } else {
1478                     Set<String> keys = objMap.keySet();
1479                     findAndFillInputsListRecursively(propertyDef, objMap, keys);
1480                 }
1481             } else if (objValue instanceof List) {
1482                 List<Object> propSubValueList = (List<Object>) objValue;
1483                 fillInputsListRecursively(propertyDef, propSubValueList);
1484             }
1485             index++;
1486         }
1487     }
1488
1489     @SuppressWarnings("unchecked")
1490     private void findAndFillInputsListRecursively(UploadPropInfo propertyDef, Map<String, Object> objMap, Set<String> keys) {
1491         for (String key : keys) {
1492             Object value = objMap.get(key);
1493             if (value instanceof Map) {
1494                 fillInputRecursively(key, (Map<String, Object>) value, propertyDef);
1495             } else if (value instanceof List) {
1496                 List<Object> propSubValueList = (List<Object>) value;
1497                 fillInputsListRecursively(propertyDef, propSubValueList);
1498             }
1499         }
1500     }
1501
1502     private void fillInputRecursively(String propName, Map<String, Object> propValue, UploadPropInfo propertyDef) {
1503         if (propValue.containsKey(GET_INPUT.getElementName())) {
1504             Object getInput = propValue.get(GET_INPUT.getElementName());
1505             GetInputValueDataDefinition getInputInfo = new GetInputValueDataDefinition();
1506             List<GetInputValueDataDefinition> getInputs = propertyDef.getGet_input();
1507             if (getInputs == null) {
1508                 getInputs = new ArrayList<>();
1509             }
1510             if (getInput instanceof String) {
1511                 getInputInfo.setInputName((String) getInput);
1512                 getInputInfo.setPropName(propName);
1513             } else if (getInput instanceof List) {
1514                 fillInput(propName, getInput, getInputInfo);
1515             }
1516             getInputs.add(getInputInfo);
1517             propertyDef.setGet_input(getInputs);
1518             propertyDef.setValue(propValue);
1519         } else {
1520             findAndFillInputRecursively(propValue, propertyDef);
1521         }
1522     }
1523
1524     @SuppressWarnings("unchecked")
1525     private void findAndFillInputRecursively(Map<String, Object> propValue, UploadPropInfo propertyDef) {
1526         for (Map.Entry<String, Object> entry : propValue.entrySet()) {
1527             String propName = entry.getKey();
1528             Object value = entry.getValue();
1529             if (value instanceof Map) {
1530                 fillInputRecursively(propName, (Map<String, Object>) value, propertyDef);
1531             } else if (value instanceof List) {
1532                 fillInputsRecursively(propertyDef, propName, (List<Object>) value);
1533             }
1534         }
1535     }
1536
1537     private void fillInputsRecursively(UploadPropInfo propertyDef, String propName, List<Object> inputs) {
1538         inputs.stream().filter(Map.class::isInstance).forEach(o -> fillInputRecursively(propName, (Map<String, Object>) o, propertyDef));
1539     }
1540
1541     @SuppressWarnings("unchecked")
1542     private void fillInput(String propName, Object getInput, GetInputValueDataDefinition getInputInfo) {
1543         List<Object> getInputList = (List<Object>) getInput;
1544         getInputInfo.setPropName(propName);
1545         getInputInfo.setInputName((String) getInputList.get(0));
1546         if (getInputList.size() > 1) {
1547             Object indexObj = getInputList.get(1);
1548             if (indexObj instanceof Integer) {
1549                 getInputInfo.setIndexValue((Integer) indexObj);
1550             } else if (indexObj instanceof Float) {
1551                 int index = ((Float) indexObj).intValue();
1552                 getInputInfo.setIndexValue(index);
1553             } else if (indexObj instanceof Map && ((Map<String, Object>) indexObj).containsKey(GET_INPUT.getElementName())) {
1554                 Object index = ((Map<String, Object>) indexObj).get(GET_INPUT.getElementName());
1555                 GetInputValueDataDefinition getInputInfoIndex = new GetInputValueDataDefinition();
1556                 getInputInfoIndex.setInputName((String) index);
1557                 getInputInfoIndex.setPropName(propName);
1558                 getInputInfo.setGetInputIndex(getInputInfoIndex);
1559             }
1560             getInputInfo.setList(true);
1561         }
1562     }
1563
1564     private Object failIfNotTopologyTemplate(String fileName) {
1565         janusGraphDao.rollback();
1566         throw new ByActionStatusComponentException(ActionStatus.NOT_TOPOLOGY_TOSCA_TEMPLATE, fileName);
1567     }
1568
1569     private void rollbackWithException(ActionStatus actionStatus, String... params) {
1570         janusGraphDao.rollback();
1571         throw new ByActionStatusComponentException(actionStatus, params);
1572     }
1573
1574     private void failOnMissingCapabilityTypes(GroupDefinition groupDefinition, List<String> missingCapTypes) {
1575         if (log.isDebugEnabled()) {
1576             log.debug(
1577                 "#failOnMissingCapabilityTypes - Failed to validate the capabilities of the group {}. The capability types {} are missing on the group type {}. ",
1578                 groupDefinition.getName(), missingCapTypes.toString(), groupDefinition.getType());
1579         }
1580         if (CollectionUtils.isNotEmpty(missingCapTypes)) {
1581             rollbackWithException(ActionStatus.MISSING_CAPABILITY_TYPE, missingCapTypes.toString());
1582         }
1583     }
1584
1585     private void failOnMissingCapabilityNames(GroupDefinition groupDefinition, List<String> missingCapNames) {
1586         if (log.isDebugEnabled()) {
1587             log.debug(
1588                 "#failOnMissingCapabilityNames - Failed to validate the capabilities of the group {}. The capabilities with the names {} are missing on the group type {}. ",
1589                 groupDefinition.getName(), missingCapNames.toString(), groupDefinition.getType());
1590         }
1591         rollbackWithException(ActionStatus.MISSING_CAPABILITIES, missingCapNames.toString(), CapabilityDataDefinition.OwnerType.GROUP.getValue(),
1592             groupDefinition.getName());
1593     }
1594 }