e79aaaeb9bc12bcf1fd19a7cd2a0a2f0ce86772c
[sdc.git] /
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  */
20
21 package org.openecomp.sdc.translator.services.heattotosca;
22
23 import org.apache.commons.collections.map.HashedMap;
24 import org.apache.commons.collections4.CollectionUtils;
25 import org.apache.commons.collections4.MapUtils;
26 import org.apache.commons.lang3.StringUtils;
27 import org.apache.commons.lang3.tuple.ImmutablePair;
28 import org.apache.commons.lang3.tuple.Pair;
29 import org.openecomp.config.api.Configuration;
30 import org.openecomp.config.api.ConfigurationManager;
31 import org.openecomp.core.utilities.CommonMethods;
32 import org.openecomp.sdc.datatypes.configuration.ImplementationConfiguration;
33 import org.openecomp.sdc.heat.services.HeatConstants;
34 import org.openecomp.sdc.logging.api.Logger;
35 import org.openecomp.sdc.logging.api.LoggerFactory;
36 import org.openecomp.sdc.logging.context.impl.MdcDataDebugMessage;
37 import org.openecomp.sdc.tosca.datatypes.ToscaFunctions;
38 import org.openecomp.sdc.tosca.datatypes.ToscaGroupType;
39 import org.openecomp.sdc.tosca.datatypes.ToscaNodeType;
40 import org.openecomp.sdc.tosca.datatypes.ToscaRelationshipType;
41 import org.openecomp.sdc.tosca.datatypes.model.AttributeDefinition;
42 import org.openecomp.sdc.tosca.datatypes.model.CapabilityDefinition;
43 import org.openecomp.sdc.tosca.datatypes.model.Constraint;
44 import org.openecomp.sdc.tosca.datatypes.model.EntrySchema;
45 import org.openecomp.sdc.tosca.datatypes.model.GroupDefinition;
46 import org.openecomp.sdc.tosca.datatypes.model.NodeTemplate;
47 import org.openecomp.sdc.tosca.datatypes.model.NodeType;
48 import org.openecomp.sdc.tosca.datatypes.model.ParameterDefinition;
49 import org.openecomp.sdc.tosca.datatypes.model.PropertyDefinition;
50 import org.openecomp.sdc.tosca.datatypes.model.PropertyType;
51 import org.openecomp.sdc.tosca.datatypes.model.RelationshipTemplate;
52 import org.openecomp.sdc.tosca.datatypes.model.RequirementAssignment;
53 import org.openecomp.sdc.tosca.datatypes.model.RequirementDefinition;
54 import org.openecomp.sdc.tosca.datatypes.model.ServiceTemplate;
55 import org.openecomp.sdc.tosca.datatypes.model.SubstitutionMapping;
56 import org.openecomp.sdc.tosca.datatypes.model.heatextend.PropertyTypeExt;
57 import org.openecomp.sdc.tosca.services.DataModelUtil;
58 import org.openecomp.sdc.tosca.services.ToscaAnalyzerService;
59 import org.openecomp.sdc.tosca.services.ToscaConstants;
60 import org.openecomp.sdc.tosca.services.ToscaUtil;
61 import org.openecomp.sdc.tosca.services.impl.ToscaAnalyzerServiceImpl;
62 import org.openecomp.sdc.translator.datatypes.heattotosca.TranslationContext;
63 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.composition.UnifiedCompositionData;
64 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.composition.UnifiedCompositionEntity;
65 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.composition.UnifiedCompositionMode;
66 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.composition.UnifiedSubstitutionData;
67 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.ComputeTemplateConsolidationData;
68 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.ConsolidationData;
69 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.EntityConsolidationData;
70 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.FileComputeConsolidationData;
71 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.FilePortConsolidationData;
72 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.GetAttrFuncData;
73 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.NestedTemplateConsolidationData;
74 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.PortTemplateConsolidationData;
75 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.RequirementAssignmentData;
76 import org.openecomp.sdc.translator.datatypes.heattotosca.unifiedmodel.consolidation.TypeComputeConsolidationData;
77
78 import java.util.ArrayList;
79 import java.util.Arrays;
80 import java.util.Collection;
81 import java.util.HashMap;
82 import java.util.HashSet;
83 import java.util.LinkedHashMap;
84 import java.util.List;
85 import java.util.Map;
86 import java.util.Objects;
87 import java.util.Optional;
88 import java.util.Set;
89 import java.util.regex.Pattern;
90
91 import static org.openecomp.sdc.tosca.services.DataModelUtil.getClonedObject;
92 import static org.openecomp.sdc.translator.services.heattotosca.Constants.ABSTRACT_NODE_TEMPLATE_ID_PREFIX;
93 import static org.openecomp.sdc.translator.services.heattotosca.Constants.COMPUTE_IDENTICAL_VALUE_PROPERTY_PREFIX;
94 import static org.openecomp.sdc.translator.services.heattotosca.Constants.COMPUTE_IDENTICAL_VALUE_PROPERTY_SUFFIX;
95 import static org.openecomp.sdc.translator.services.heattotosca.Constants.PORT_IDENTICAL_VALUE_PROPERTY_PREFIX;
96
97 public class UnifiedCompositionService {
98
99   protected static Logger logger =
100       (Logger) LoggerFactory.getLogger(UnifiedCompositionService.class);
101   protected static MdcDataDebugMessage mdcDataDebugMessage = new MdcDataDebugMessage();
102   private static Map<String, ImplementationConfiguration> unifiedCompositionImplMap;
103
104   static {
105     Configuration config = ConfigurationManager.lookup();
106     unifiedCompositionImplMap =
107         config.populateMap(ConfigConstants.MANDATORY_UNIFIED_MODEL_NAMESPACE,
108             ConfigConstants.UNIFIED_COMPOSITION_IMPL_KEY, ImplementationConfiguration.class);
109
110   }
111
112   private ConsolidationService consolidationService = new ConsolidationService();
113
114   private static List<EntityConsolidationData> getPortConsolidationDataList(
115       List<String> portIds,
116       List<UnifiedCompositionData> unifiedCompositionDataList) {
117     List<EntityConsolidationData> portConsolidationDataList = new ArrayList<>();
118     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
119       for (PortTemplateConsolidationData portTemplateConsolidationData : unifiedCompositionData
120           .getPortTemplateConsolidationDataList()) {
121         if (portIds.contains(portTemplateConsolidationData.getNodeTemplateId())) {
122           portConsolidationDataList.add(portTemplateConsolidationData);
123         }
124       }
125     }
126     return portConsolidationDataList;
127   }
128
129   /**
130    * Create unified composition.
131    *
132    * @param serviceTemplate            the service template
133    * @param nestedServiceTemplate      the nested service template
134    * @param unifiedCompositionDataList the unified composition data list. In case no consolidation,
135    *                                   one entry will be in this list, in case of having
136    *                                   consolidation, all entries in the list are the once which
137    *                                   need to be consolidated.
138    * @param mode                       the mode
139    * @param context                    the context
140    */
141   public void createUnifiedComposition(ServiceTemplate serviceTemplate,
142                                        ServiceTemplate nestedServiceTemplate,
143                                        List<UnifiedCompositionData> unifiedCompositionDataList,
144                                        UnifiedCompositionMode mode, TranslationContext context) {
145     mdcDataDebugMessage.debugEntryMessage(null, null);
146     Optional<UnifiedComposition> unifiedCompositionInstance = getUnifiedCompositionInstance(mode);
147     if (!unifiedCompositionInstance.isPresent()) {
148       return;
149     }
150     unifiedCompositionInstance.get()
151         .createUnifiedComposition(serviceTemplate, nestedServiceTemplate,
152             unifiedCompositionDataList, context);
153     mdcDataDebugMessage.debugExitMessage(null, null);
154   }
155
156   /**
157    * Create unified substitution service template according to the input service template, based on
158    * the unified composition data.
159    *
160    * @param serviceTemplate            the service template
161    * @param unifiedCompositionDataList the unified composition data list. In case no consolidation,
162    *                                   one entry will be in this list, in case of having
163    *                                   consolidation, all entries in the list are the once which
164    *                                   need to be consolidated.
165    * @param context                    the translation context
166    * @return the substitution service template
167    */
168   public Optional<ServiceTemplate> createUnifiedSubstitutionServiceTemplate(
169       ServiceTemplate serviceTemplate,
170       List<UnifiedCompositionData> unifiedCompositionDataList,
171       TranslationContext context,
172       String substitutionNodeTypeId,
173       Integer index) {
174     if (CollectionUtils.isEmpty(unifiedCompositionDataList)) {
175       return Optional.empty();
176     }
177     UnifiedCompositionData unifiedCompositionData = unifiedCompositionDataList.get(0);
178     String templateName =
179         getTemplateName(serviceTemplate, unifiedCompositionData, substitutionNodeTypeId, index);
180     ServiceTemplate substitutionServiceTemplate =
181         HeatToToscaUtil.createInitSubstitutionServiceTemplate(templateName);
182
183     createIndexInputParameter(substitutionServiceTemplate);
184
185     String computeNodeType =
186         handleCompute(serviceTemplate, substitutionServiceTemplate, unifiedCompositionDataList,
187             context);
188     handlePorts(serviceTemplate, substitutionServiceTemplate, unifiedCompositionDataList,
189         computeNodeType, context);
190     createOutputParameters(serviceTemplate, substitutionServiceTemplate, unifiedCompositionDataList,
191         computeNodeType, context);
192     NodeType substitutionGlobalNodeType =
193         handleSubstitutionGlobalNodeType(serviceTemplate, substitutionServiceTemplate,
194             context, unifiedCompositionData, substitutionNodeTypeId, index);
195
196     HeatToToscaUtil.handleSubstitutionMapping(context,
197         substitutionNodeTypeId,
198         substitutionServiceTemplate, substitutionGlobalNodeType);
199
200     context.getTranslatedServiceTemplates().put(templateName, substitutionServiceTemplate);
201     return Optional.of(substitutionServiceTemplate);
202   }
203
204
205   /**
206    * Create abstract substitute node template that can be substituted by the input
207    * substitutionServiceTemplate.
208    *
209    * @param serviceTemplate             the service template
210    * @param substitutionServiceTemplate the subtitution service template
211    * @param unifiedCompositionDataList  the unified composition data list. In case no consolidation,
212    *                                    one entry will be in this list, in case of having
213    *                                    consolidation, all entries in the list are the once which
214    *                                    need to be consolidated.
215    * @param context                     the translation context
216    * @return the abstract substitute node template id
217    */
218   public String createAbstractSubstituteNodeTemplate(
219       ServiceTemplate serviceTemplate,
220       ServiceTemplate substitutionServiceTemplate,
221       List<UnifiedCompositionData> unifiedCompositionDataList,
222       String substituteNodeTypeId,
223       TranslationContext context,
224       Integer index) {
225
226     NodeTemplate substitutionNodeTemplate = new NodeTemplate();
227     List<String> directiveList = new ArrayList<>();
228     directiveList.add(ToscaConstants.NODE_TEMPLATE_DIRECTIVE_SUBSTITUTABLE);
229     substitutionNodeTemplate.setDirectives(directiveList);
230     substitutionNodeTemplate.setType(substituteNodeTypeId);
231     Optional<Map<String, Object>> abstractSubstitutionProperties =
232         createAbstractSubstitutionProperties(serviceTemplate,
233             substitutionServiceTemplate, unifiedCompositionDataList, context);
234     abstractSubstitutionProperties.ifPresent(substitutionNodeTemplate::setProperties);
235
236     //Add substitution filtering property
237     String substitutionServiceTemplateName = ToscaUtil.getServiceTemplateFileName(
238         substitutionServiceTemplate);
239     int count = unifiedCompositionDataList.size();
240     DataModelUtil.addSubstitutionFilteringProperty(substitutionServiceTemplateName,
241         substitutionNodeTemplate, count);
242     //Add index_value property
243     addIndexValueProperty(substitutionNodeTemplate);
244     String substituteNodeTemplateId =
245         getSubstituteNodeTemplateId(serviceTemplate, unifiedCompositionDataList.get(0),
246             substituteNodeTypeId, index);
247     //Add node template id and related abstract node template id in context
248     addUnifiedSubstitionData(context, serviceTemplate, unifiedCompositionDataList,
249         substituteNodeTemplateId);
250     DataModelUtil
251         .addNodeTemplate(serviceTemplate, substituteNodeTemplateId, substitutionNodeTemplate);
252     return substituteNodeTemplateId;
253
254   }
255
256   /**
257    * Update the connectivity from/to the "moved" nodes from the original service template to the new
258    * substitution service template.
259    *
260    * @param serviceTemplate            the service template
261    * @param unifiedCompositionDataList the unified composition data list. In case no consolidation,
262    *                                   one entry will be in this list, in case of having
263    *                                   consolidation, all entries in the list are the once which
264    *                                   need to be consolidated.
265    * @param context                    the translation context
266    */
267   public void updateCompositionConnectivity(ServiceTemplate serviceTemplate,
268                                             List<UnifiedCompositionData> unifiedCompositionDataList,
269                                             TranslationContext context) {
270     updOutputParamGetAttrInConnectivity(serviceTemplate, unifiedCompositionDataList, context);
271     updNodesGetAttrInConnectivity(serviceTemplate, unifiedCompositionDataList, context);
272     updNodesConnectedOutConnectivity(serviceTemplate, unifiedCompositionDataList, context);
273     updNodesConnectedInConnectivity(serviceTemplate, unifiedCompositionDataList, context);
274     updVolumeConnectivity(serviceTemplate, unifiedCompositionDataList, context);
275     updGroupsConnectivity(serviceTemplate, unifiedCompositionDataList, context);
276   }
277
278   /**
279    * Delete the "moved" nodes from the original service template to the new substitution service
280    * template.
281    *
282    * @param serviceTemplate            the service template
283    * @param unifiedCompositionDataList the unified composition data list. In case no consolidation,
284    *                                   one entry will be in this list, in case of having
285    *                                   consolidation, all entries in the list are the once which
286    *                                   need to be consolidated.
287    * @param context                    the translation context
288    */
289   public void cleanUnifiedCompositionEntities(
290       ServiceTemplate serviceTemplate,
291       List<UnifiedCompositionData> unifiedCompositionDataList,
292       TranslationContext context) {
293     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
294       ComputeTemplateConsolidationData computeTemplateConsolidationData =
295           unifiedCompositionData.getComputeTemplateConsolidationData();
296       cleanServiceTemplate(serviceTemplate, computeTemplateConsolidationData, context);
297
298       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
299           getPortTemplateConsolidationDataList(unifiedCompositionData);
300       for (PortTemplateConsolidationData portTemplateConsolidationData :
301           portTemplateConsolidationDataList) {
302         cleanServiceTemplate(serviceTemplate, portTemplateConsolidationData, context);
303       }
304     }
305
306   }
307
308   /**
309    * Clean node types.
310    *
311    * @param serviceTemplate            the service template
312    * @param unifiedCompositionDataList the unified composition data list
313    * @param context                    the context
314    */
315   public void cleanNodeTypes(ServiceTemplate serviceTemplate,
316                              List<UnifiedCompositionData> unifiedCompositionDataList,
317                              TranslationContext context) {
318     for (UnifiedCompositionData unifiedData : unifiedCompositionDataList) {
319       removeCleanedNodeType(
320           unifiedData.getComputeTemplateConsolidationData().getNodeTemplateId(), serviceTemplate,
321           context);
322     }
323     if (MapUtils.isEmpty(serviceTemplate.getNode_types())) {
324       serviceTemplate.setNode_types(null);
325     }
326   }
327
328   public void updateSubstitutionNodeTypePrefix(ServiceTemplate substitutionServiceTemplate) {
329     Map<String, NodeTemplate> node_templates =
330         substitutionServiceTemplate.getTopology_template().getNode_templates();
331
332     for (Map.Entry<String, NodeTemplate> nodeTemplateEntry : node_templates.entrySet()) {
333       String nodeTypeId = nodeTemplateEntry.getValue().getType();
334       NodeType origNodeType = substitutionServiceTemplate.getNode_types().get(nodeTypeId);
335       if (Objects.nonNull(origNodeType)
336           && nodeTypeId.startsWith(ToscaNodeType.VFC_TYPE_PREFIX)
337           && origNodeType.getDerived_from().equals(ToscaNodeType.NOVA_SERVER)) {
338         substitutionServiceTemplate.getNode_types().remove(nodeTypeId);
339
340         String newNodeTypeId =
341             nodeTypeId.replace(ToscaNodeType.VFC_TYPE_PREFIX, ToscaNodeType.COMPUTE_TYPE_PREFIX);
342         nodeTemplateEntry.getValue().setType(newNodeTypeId);
343         DataModelUtil
344             .addNodeTemplate(substitutionServiceTemplate, nodeTemplateEntry.getKey(),
345                 nodeTemplateEntry.getValue());
346         substitutionServiceTemplate.getNode_types().put(newNodeTypeId, origNodeType);
347       }
348     }
349   }
350
351   /**
352    * Update unified abstract nodes connectivity.
353    *
354    * @param serviceTemplate the service template
355    * @param context         the context
356    */
357   public void updateUnifiedAbstractNodesConnectivity(ServiceTemplate serviceTemplate,
358                                                      TranslationContext context) {
359
360
361     String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
362     UnifiedSubstitutionData unifiedSubstitutionData = context.getUnifiedSubstitutionData()
363         .get(serviceTemplateFileName);
364
365     if (Objects.nonNull(unifiedSubstitutionData)) {
366       //Handle get attribute in connectivity for abstarct node to abstract node templates
367       Set<String> abstractNodeIds =
368           new HashSet<>(unifiedSubstitutionData.getAllRelatedAbstractNodeIds());
369       handleGetAttrInConnectivity(serviceTemplate, abstractNodeIds, context);
370       //Handle get attribute in connectivity for abstract node templates to nested node template
371       Set<String> nestedNodeIds =
372           new HashSet<>(unifiedSubstitutionData.getAllUnifiedNestedNodeTemplateIds());
373       handleGetAttrInConnectivity(serviceTemplate, nestedNodeIds, context);
374     }
375   }
376
377   /**
378    * Handle unified nested definition.
379    *
380    * @param mainServiceTemplate    the main service template
381    * @param nestedServiceTemplate  the nested service template
382    * @param unifiedCompositionData the unified composition data
383    * @param context                the context
384    */
385   public void handleUnifiedNestedDefinition(ServiceTemplate mainServiceTemplate,
386                                             ServiceTemplate nestedServiceTemplate,
387                                             UnifiedCompositionData unifiedCompositionData,
388                                             TranslationContext context) {
389     handleUnifiedNestedNodeType(mainServiceTemplate, nestedServiceTemplate, context);
390     updateUnifiedNestedTemplates(mainServiceTemplate, nestedServiceTemplate,
391         unifiedCompositionData, context);
392   }
393
394   private void handleGetAttrInConnectivity(ServiceTemplate serviceTemplate,
395                                            Set<String> unifiedNodeIds,
396                                            TranslationContext context) {
397     Map<String, NodeTemplate> nodeTemplates =
398         serviceTemplate.getTopology_template().getNode_templates();
399     String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
400     for (String unifiedNodeId : unifiedNodeIds) {
401       NodeTemplate nodeTemplate = nodeTemplates.get(unifiedNodeId);
402       handleGetAttrInAbstractNodeTemplate(serviceTemplate, context, serviceTemplateFileName,
403           nodeTemplate);
404     }
405   }
406
407   private void handleUnifiedNestedNodeType(ServiceTemplate mainServiceTemplate,
408                                            ServiceTemplate nestedServiceTemplate,
409                                            TranslationContext context) {
410
411
412     SubstitutionMapping substitutionMappings =
413         nestedServiceTemplate.getTopology_template().getSubstitution_mappings();
414     String nodeTypeId = substitutionMappings.getNode_type();
415
416     Optional<String> newNestedNodeTypeId =
417         getNewNestedNodeTypeId(mainServiceTemplate, nestedServiceTemplate, context);
418
419     ServiceTemplate globalSubstitutionServiceTemplate =
420         context.getGlobalSubstitutionServiceTemplate();
421
422     if (isNestedServiceTemplateWasHandled(globalSubstitutionServiceTemplate, nestedServiceTemplate,
423         context,
424         newNestedNodeTypeId)) {
425       context
426           .updateHandledComputeType(ToscaUtil.getServiceTemplateFileName(mainServiceTemplate),
427               newNestedNodeTypeId.get(),
428               ToscaUtil.getServiceTemplateFileName(nestedServiceTemplate));
429       return;
430     }
431
432
433     newNestedNodeTypeId.ifPresent(
434         newNestedNodeTypeIdVal -> handleNestedNodeType(nodeTypeId, newNestedNodeTypeIdVal,
435             nestedServiceTemplate, mainServiceTemplate, globalSubstitutionServiceTemplate,
436             context));
437
438   }
439
440   private boolean isNestedServiceTemplateWasHandled(ServiceTemplate mainServiceTemplate,
441                                                     ServiceTemplate nestedServiceTemplate,
442                                                     TranslationContext context,
443                                                     Optional<String> newNestedNodeTypeId) {
444     return newNestedNodeTypeId.isPresent()
445         && context.isNestedServiceTemplateWasHandled(
446         ToscaUtil.getServiceTemplateFileName(mainServiceTemplate),
447         ToscaUtil.getServiceTemplateFileName(nestedServiceTemplate));
448   }
449
450   private void handleNestedNodeType(String nodeTypeId, String newNestedNodeTypeId,
451                                     ServiceTemplate nestedServiceTemplate,
452                                     ServiceTemplate mainServiceTemplate,
453                                     ServiceTemplate globalSubstitutionServiceTemplate,
454                                     TranslationContext context) {
455     updateNestedServiceTemplate(nestedServiceTemplate, context);
456     updateNestedNodeType(nodeTypeId, newNestedNodeTypeId, nestedServiceTemplate,
457         mainServiceTemplate,
458         globalSubstitutionServiceTemplate, context);
459
460
461   }
462
463   private void updateNestedServiceTemplate(ServiceTemplate nestedServiceTemplate,
464                                            TranslationContext context) {
465     enrichPortProperties(nestedServiceTemplate, context);
466   }
467
468   private void enrichPortProperties(ServiceTemplate nestedServiceTemplate,
469                                     TranslationContext context) {
470     String nestedServiceTemplateFileName =
471         ToscaUtil.getServiceTemplateFileName(nestedServiceTemplate);
472     FilePortConsolidationData filePortConsolidationData =
473         context.getConsolidationData().getPortConsolidationData().getFilePortConsolidationData
474             (nestedServiceTemplateFileName);
475
476     if (Objects.nonNull(filePortConsolidationData)) {
477       Set<String> portNodeTemplateIds = filePortConsolidationData.getAllPortNodeTemplateIds();
478       if (Objects.nonNull(portNodeTemplateIds)) {
479         for (String portNodeTemplateId : portNodeTemplateIds) {
480           NodeTemplate portNodeTemplate = DataModelUtil.getNodeTemplate(nestedServiceTemplate,
481               portNodeTemplateId);
482           List<EntityConsolidationData> portEntityConsolidationDataList = new ArrayList<>();
483           portEntityConsolidationDataList.add(filePortConsolidationData
484               .getPortTemplateConsolidationData(portNodeTemplateId));
485
486           handleNodeTypeProperties(nestedServiceTemplate,
487               portEntityConsolidationDataList, portNodeTemplate, UnifiedCompositionEntity.Port,
488               null, context);
489         }
490       }
491     }
492   }
493
494   private void updateNestedNodeType(String nodeTypeId, String newNestedNodeTypeId,
495                                     ServiceTemplate nestedServiceTemplate,
496                                     ServiceTemplate mainServiceTemplate,
497                                     ServiceTemplate globalSubstitutionServiceTemplate,
498                                     TranslationContext context) {
499     String indexedNewNestedNodeTypeId =
500         updateNodeTypeId(nodeTypeId, newNestedNodeTypeId, nestedServiceTemplate,
501             mainServiceTemplate,
502             globalSubstitutionServiceTemplate, context);
503
504     updateNodeTypeProperties(nestedServiceTemplate, globalSubstitutionServiceTemplate,
505         indexedNewNestedNodeTypeId);
506     //addComputeNodeTypeToGlobalST();
507
508   }
509
510   private void updateNodeTypeProperties(ServiceTemplate nestedServiceTemplate,
511                                         ServiceTemplate globalSubstitutionServiceTemplate,
512                                         String nodeTypeId) {
513     ToscaAnalyzerService toscaAnalyzerService = new ToscaAnalyzerServiceImpl();
514     Map<String, PropertyDefinition> nodeTypePropertiesDefinition =
515         toscaAnalyzerService.manageSubstitutionNodeTypeProperties(nestedServiceTemplate);
516     NodeType nestedNodeType =
517         DataModelUtil.getNodeType(globalSubstitutionServiceTemplate, nodeTypeId);
518     nestedNodeType.setProperties(nodeTypePropertiesDefinition);
519   }
520
521   private String updateNodeTypeId(String nodeTypeId, String newNestedNodeTypeId,
522                                   ServiceTemplate nestedServiceTemplate,
523                                   ServiceTemplate mainServiceTemplate,
524                                   ServiceTemplate globalSubstitutionServiceTemplate,
525                                   TranslationContext context) {
526     String indexedNewNestedNodeTypeId =
527         handleNestedNodeTypeInGlobalSubstitutionTemplate(nodeTypeId, newNestedNodeTypeId,
528             globalSubstitutionServiceTemplate, context);
529
530     handleSubstitutionMappingInNestedServiceTemplate(indexedNewNestedNodeTypeId,
531         nestedServiceTemplate, context);
532
533     context
534         .updateHandledComputeType(
535             ToscaUtil.getServiceTemplateFileName(mainServiceTemplate),
536             ToscaUtil.getServiceTemplateFileName(nestedServiceTemplate),
537             newNestedNodeTypeId);
538     return indexedNewNestedNodeTypeId;
539   }
540
541   private String handleNestedNodeTypeInGlobalSubstitutionTemplate(String nodeTypeId,
542                                                                   String newNestedNodeTypeId,
543                                                                   ServiceTemplate globalSubstitutionServiceTemplate,
544                                                                   TranslationContext context) {
545     String indexedNodeType =
546         getIndexedGlobalNodeTypeId(newNestedNodeTypeId, context);
547     context.updateUsedTimesForNestedComputeNodeType(
548         ToscaUtil.getServiceTemplateFileName(globalSubstitutionServiceTemplate),
549         newNestedNodeTypeId);
550     handleNestedNodeTypesInGlobalSubstituteServiceTemplate(nodeTypeId, indexedNodeType,
551         globalSubstitutionServiceTemplate, context);
552     return indexedNodeType;
553   }
554
555   private String getIndexedGlobalNodeTypeId(String newNestedNodeTypeId,
556                                             TranslationContext context) {
557     int globalNodeTypeIndex =
558         context.getGlobalNodeTypeIndex(
559             ToscaUtil.getServiceTemplateFileName(Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME),
560             newNestedNodeTypeId);
561     return globalNodeTypeIndex > 0 ? newNestedNodeTypeId + "_"
562         + String.valueOf(globalNodeTypeIndex) : newNestedNodeTypeId;
563   }
564
565   private void updateUnifiedNestedTemplates(ServiceTemplate mainServiceTemplate,
566                                             ServiceTemplate nestedServiceTemplate,
567                                             UnifiedCompositionData unifiedCompositionData,
568                                             TranslationContext context) {
569
570     NestedTemplateConsolidationData nestedTemplateConsolidationData =
571         unifiedCompositionData.getNestedTemplateConsolidationData();
572     if (Objects.isNull(nestedTemplateConsolidationData)) {
573       return;
574     }
575     handleNestedNodeTemplateInMainServiceTemplate(
576         nestedTemplateConsolidationData.getNodeTemplateId(), mainServiceTemplate,
577         nestedServiceTemplate, context);
578
579   }
580
581   /**
582    * Update connectivity for unified nested patterns.
583    *
584    * @param serviceTemplate        the service template
585    * @param nestedServiceTemplate  the nested service template
586    * @param unifiedCompositionData the unified composition data
587    * @param context                the context
588    */
589   public void updateUnifiedNestedConnectivity(ServiceTemplate serviceTemplate,
590                                               ServiceTemplate nestedServiceTemplate,
591                                               UnifiedCompositionData unifiedCompositionData,
592                                               TranslationContext context) {
593
594     updNestedCompositionNodesConnectedInConnectivity(serviceTemplate, unifiedCompositionData,
595         context);
596     updNestedCompositionNodesConnectedOutConnectivity(serviceTemplate, nestedServiceTemplate,
597         unifiedCompositionData, context);
598     updNestedCompositionNodesGetAttrInConnectivity(serviceTemplate, unifiedCompositionData,
599         context);
600     updNestedCompositionOutputParamGetAttrInConnectivity(serviceTemplate,
601         unifiedCompositionData, context);
602   }
603
604
605   /**
606    * Clean unified nested entities. Update the heat stack group with the new node template ids.
607    *
608    * @param serviceTemplate        the service template
609    * @param unifiedCompositionData the unified composition data
610    * @param context                the context
611    */
612   public void cleanUnifiedNestedEntities(ServiceTemplate serviceTemplate,
613                                          UnifiedCompositionData unifiedCompositionData,
614                                          TranslationContext context) {
615     EntityConsolidationData entityConsolidationData =
616         unifiedCompositionData.getNestedTemplateConsolidationData();
617     updateHeatStackGroupNestedComposition(serviceTemplate, entityConsolidationData, context);
618
619   }
620
621   public void handleComplexVfcType(ServiceTemplate serviceTemplate, TranslationContext context) {
622     SubstitutionMapping substitution_mappings =
623         serviceTemplate.getTopology_template().getSubstitution_mappings();
624
625     if (Objects.isNull(substitution_mappings)) {
626       return;
627     }
628
629     ServiceTemplate globalSubstitutionServiceTemplate =
630         context.getGlobalSubstitutionServiceTemplate();
631
632     String substitutionNT = substitution_mappings.getNode_type();
633     if (globalSubstitutionServiceTemplate.getNode_types().containsKey(substitutionNT)) {
634       //todo - remove comment after integration with AT&T
635 //      globalSubstitutionServiceTemplate.getNode_types().get(substitutionNT).setDerived_from
636 //          (ToscaNodeType.COMPLEX_VFC_NODE_TYPE);
637     }
638   }
639
640
641   protected void updNodesConnectedOutConnectivity(ServiceTemplate serviceTemplate,
642                                                   List<UnifiedCompositionData>
643                                                       unifiedCompositionDataList,
644                                                   TranslationContext context) {
645     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
646       ComputeTemplateConsolidationData computeTemplateConsolidationData = unifiedCompositionData
647           .getComputeTemplateConsolidationData();
648       //Add requirements in the abstract node template for nodes connected out for computes
649       String newComputeNodeTemplateId = getNewComputeNodeTemplateId(serviceTemplate,
650           computeTemplateConsolidationData.getNodeTemplateId());
651       Map<String, List<RequirementAssignmentData>> computeNodesConnectedOut =
652           computeTemplateConsolidationData.getNodesConnectedOut();
653       if (computeNodesConnectedOut != null) {
654         updateRequirementInAbstractNodeTemplate(serviceTemplate, computeTemplateConsolidationData,
655             newComputeNodeTemplateId, computeNodesConnectedOut, context);
656       }
657       String computeType = getComputeTypeSuffix(serviceTemplate, computeTemplateConsolidationData
658           .getNodeTemplateId());
659       //Add requirements in the abstract node template for nodes connected out for ports
660       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
661           getPortTemplateConsolidationDataList(unifiedCompositionData);
662       for (PortTemplateConsolidationData portTemplateConsolidationData :
663           portTemplateConsolidationDataList) {
664         String newPortNodeTemplateId = getNewPortNodeTemplateId(portTemplateConsolidationData
665             .getNodeTemplateId(), computeType, computeTemplateConsolidationData);
666         Map<String, List<RequirementAssignmentData>> portNodesConnectedOut =
667             portTemplateConsolidationData.getNodesConnectedOut();
668         if (portNodesConnectedOut != null) {
669           updateRequirementInAbstractNodeTemplate(serviceTemplate, portTemplateConsolidationData,
670               newPortNodeTemplateId, portNodesConnectedOut, context);
671         }
672       }
673     }
674   }
675
676   private void updNestedCompositionNodesConnectedOutConnectivity(ServiceTemplate serviceTemplate,
677                                                                  ServiceTemplate nestedServiceTemplate,
678                                                                  UnifiedCompositionData unifiedCompositionData,
679                                                                  TranslationContext context) {
680     NestedTemplateConsolidationData nestedTemplateConsolidationData =
681         unifiedCompositionData.getNestedTemplateConsolidationData();
682     Map<String, List<RequirementAssignmentData>> nodesConnectedOut =
683         Objects.isNull(nestedTemplateConsolidationData) ? new HashMap<>()
684             : nestedTemplateConsolidationData.getNodesConnectedOut();
685
686     FileComputeConsolidationData nestedFileComputeConsolidationData =
687         context.getConsolidationData().getComputeConsolidationData().getFileComputeConsolidationData
688             (ToscaUtil.getServiceTemplateFileName(nestedServiceTemplate));
689
690     if (Objects.isNull(nestedFileComputeConsolidationData)) {
691       return;
692     }
693
694     TypeComputeConsolidationData computeType =
695         nestedFileComputeConsolidationData.getAllTypeComputeConsolidationData().iterator().next();
696     if (Objects.isNull(computeType)) {
697       return;
698     }
699
700     String singleComputeId = computeType.getAllComputeNodeTemplateIds().iterator().next();
701     if (Objects.nonNull(singleComputeId)) {
702       updateRequirementInNestedNodeTemplate(serviceTemplate, nestedTemplateConsolidationData,
703           singleComputeId, nodesConnectedOut);
704     }
705   }
706
707   protected void updNodesConnectedInConnectivity(ServiceTemplate serviceTemplate,
708                                                  List<UnifiedCompositionData>
709                                                      unifiedCompositionDataList,
710                                                  TranslationContext context) {
711     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
712       ComputeTemplateConsolidationData computeTemplateConsolidationData = unifiedCompositionData
713           .getComputeTemplateConsolidationData();
714       //Update requirements in the node template which pointing to the computes
715       String newComputeNodeTemplateId = getNewComputeNodeTemplateId(serviceTemplate,
716           computeTemplateConsolidationData.getNodeTemplateId());
717       updNodesConnectedInConnectivity(serviceTemplate, computeTemplateConsolidationData,
718           newComputeNodeTemplateId, context, false);
719
720       String computeType = getComputeTypeSuffix(serviceTemplate, computeTemplateConsolidationData
721           .getNodeTemplateId());
722       //Update requirements in the node template which pointing to the ports
723       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
724           getPortTemplateConsolidationDataList(unifiedCompositionData);
725       for (PortTemplateConsolidationData portTemplateConsolidationData :
726           portTemplateConsolidationDataList) {
727         String newPortNodeTemplateId = getNewPortNodeTemplateId(portTemplateConsolidationData
728             .getNodeTemplateId(), computeType, computeTemplateConsolidationData);
729         updNodesConnectedInConnectivity(serviceTemplate, portTemplateConsolidationData,
730             newPortNodeTemplateId, context, false);
731       }
732     }
733   }
734
735   private void updNodesConnectedInConnectivity(ServiceTemplate serviceTemplate,
736                                                EntityConsolidationData entityConsolidationData,
737                                                String newNodeTemplateId,
738                                                TranslationContext context,
739                                                boolean isNested) {
740     Map<String, List<RequirementAssignmentData>> nodesConnectedIn =
741         entityConsolidationData.getNodesConnectedIn();
742     if (nodesConnectedIn == null) {
743       //No nodes connected in info
744       return;
745     }
746     for (Map.Entry<String, List<RequirementAssignmentData>> entry : nodesConnectedIn
747         .entrySet()) {
748       List<RequirementAssignmentData> requirementAssignmentDataList = entry.getValue();
749       for (RequirementAssignmentData requirementAssignmentData : requirementAssignmentDataList) {
750         RequirementAssignment requirementAssignment = requirementAssignmentData
751             .getRequirementAssignment();
752         if (!requirementAssignment.getNode().equals(entityConsolidationData
753             .getNodeTemplateId())) {
754           //The requirement assignment target node should be the one which we are handling in the
755           //consolidation object
756           continue;
757         }
758         //Update the requirement assignment object in the original node template
759         if (isNested) {
760           updateRequirementForNestedCompositionNodesConnectedIn(serviceTemplate,
761               requirementAssignmentData, entityConsolidationData, newNodeTemplateId, context);
762         } else {
763           updateRequirementForNodesConnectedIn(serviceTemplate, requirementAssignmentData,
764               entityConsolidationData, entry.getKey(), newNodeTemplateId, context);
765         }
766
767       }
768     }
769   }
770
771   protected void updNestedCompositionNodesConnectedInConnectivity(
772       ServiceTemplate serviceTemplate,
773       UnifiedCompositionData unifiedCompositionData,
774       TranslationContext context) {
775     NestedTemplateConsolidationData nestedTemplateConsolidationData = unifiedCompositionData
776         .getNestedTemplateConsolidationData();
777     //Update requirements in the node template which pointing to the nested nodes
778     String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
779     Optional<String> newNestedNodeTemplateId = context.getUnifiedNestedNodeTemplateId(
780         serviceTemplateFileName, nestedTemplateConsolidationData.getNodeTemplateId());
781     newNestedNodeTemplateId.ifPresent(
782         newNestedNodeTemplateIdVal -> updNodesConnectedInConnectivity(serviceTemplate,
783             nestedTemplateConsolidationData,
784             newNestedNodeTemplateIdVal, context, true));
785
786   }
787
788 //  protected void updNestedCompositionNodesConnectedOutConnectivity(
789 //      ServiceTemplate serviceTemplate,
790 //      UnifiedCompositionData unifiedCompositionData,
791 //      TranslationContext context) {
792 //    NestedTemplateConsolidationData nestedTemplateConsolidationData = unifiedCompositionData
793 //        .getNestedTemplateConsolidationData();
794 //    //Update requirements in the node template which pointing to the nested nodes
795 //    String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
796 //    Optional<String> newNestedNodeTemplateId = context.getUnifiedNestedNodeTemplateId(
797 //        serviceTemplateFileName, nestedTemplateConsolidationData.getNodeTemplateId());
798 //    newNestedNodeTemplateId.ifPresent(
799 //        newNestedNodeTemplateIdVal -> updNodesConnectedOutConnectivity(serviceTemplate,
800 //            nestedTemplateConsolidationData,
801 //            newNestedNodeTemplateIdVal, context, true));
802 //
803 //  }
804
805   protected void updVolumeConnectivity(ServiceTemplate serviceTemplate,
806                                        List<UnifiedCompositionData>
807                                            unifiedCompositionDataList,
808                                        TranslationContext context) {
809     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
810       ComputeTemplateConsolidationData computeTemplateConsolidationData = unifiedCompositionData
811           .getComputeTemplateConsolidationData();
812       //Add requirements in the abstract node template for compute volumes
813       String newComputeNodeTemplateId = getNewComputeNodeTemplateId(serviceTemplate,
814           computeTemplateConsolidationData.getNodeTemplateId());
815       Map<String, List<RequirementAssignmentData>> computeVolumes =
816           computeTemplateConsolidationData.getVolumes();
817       if (computeVolumes != null) {
818         updateRequirementInAbstractNodeTemplate(serviceTemplate, computeTemplateConsolidationData,
819             newComputeNodeTemplateId, computeVolumes, context);
820       }
821     }
822   }
823
824   protected void updGroupsConnectivity(ServiceTemplate serviceTemplate,
825                                        List<UnifiedCompositionData>
826                                            unifiedCompositionDataList,
827                                        TranslationContext context) {
828     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
829       ComputeTemplateConsolidationData computeTemplateConsolidationData = unifiedCompositionData
830           .getComputeTemplateConsolidationData();
831       //Add requirements in the abstract node template for nodes connected in for computes
832       String newComputeNodeTemplateId = getNewComputeNodeTemplateId(serviceTemplate,
833           computeTemplateConsolidationData.getNodeTemplateId());
834       updGroupsConnectivity(serviceTemplate, computeTemplateConsolidationData, context);
835
836       String computeType = getComputeTypeSuffix(serviceTemplate, computeTemplateConsolidationData
837           .getNodeTemplateId());
838       //Add requirements in the abstract node template for nodes connected in for ports
839       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
840           getPortTemplateConsolidationDataList(unifiedCompositionData);
841       for (PortTemplateConsolidationData portTemplateConsolidationData :
842           portTemplateConsolidationDataList) {
843         String newPortNodeTemplateId = getNewPortNodeTemplateId(portTemplateConsolidationData
844             .getNodeTemplateId(), computeType, computeTemplateConsolidationData);
845         updGroupsConnectivity(serviceTemplate, portTemplateConsolidationData, context);
846       }
847     }
848   }
849
850   private void updGroupsConnectivity(ServiceTemplate serviceTemplate, EntityConsolidationData
851       entityConsolidationData, TranslationContext context) {
852     List<String> groupIds = entityConsolidationData.getGroupIds();
853     if (groupIds == null) {
854       return;
855     }
856     String oldNodeTemplateId = entityConsolidationData.getNodeTemplateId();
857     String abstractNodeTemplateId = context.getUnifiedAbstractNodeTemplateId(
858         serviceTemplate, entityConsolidationData.getNodeTemplateId());
859     Map<String, GroupDefinition> groups = serviceTemplate.getTopology_template().getGroups();
860     if (groups != null) {
861       for (String groupId : groupIds) {
862         GroupDefinition groupDefinition = groups.get(groupId);
863         if (groupDefinition != null) {
864           List<String> groupMembers = groupDefinition.getMembers();
865           if (groupMembers.contains(oldNodeTemplateId)) {
866             //Replace the old node template id
867             groupMembers.remove(oldNodeTemplateId);
868             if (!groupMembers.contains(abstractNodeTemplateId)) {
869               //Add the abstract node template id if not already present
870               groupMembers.add(abstractNodeTemplateId);
871             }
872           }
873         }
874       }
875     }
876   }
877
878   protected void updOutputParamGetAttrInConnectivity(
879       ServiceTemplate serviceTemplate, List<UnifiedCompositionData> unifiedComposotionDataList,
880       TranslationContext context) {
881     for (UnifiedCompositionData unifiedCompositionData : unifiedComposotionDataList) {
882       ComputeTemplateConsolidationData computeTemplateConsolidationData =
883           unifiedCompositionData.getComputeTemplateConsolidationData();
884       String newComputeNodeTemplateId = getNewComputeNodeTemplateId(serviceTemplate,
885           computeTemplateConsolidationData.getNodeTemplateId());
886
887       updOutputParamGetAttrInConnectivity(serviceTemplate, computeTemplateConsolidationData,
888           computeTemplateConsolidationData.getNodeTemplateId(), newComputeNodeTemplateId,
889           context, false);
890
891       String computeType =
892           getComputeTypeSuffix(serviceTemplate,
893               computeTemplateConsolidationData.getNodeTemplateId());
894       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
895           getPortTemplateConsolidationDataList(unifiedCompositionData);
896       for (PortTemplateConsolidationData portTemplateConsolidationData :
897           portTemplateConsolidationDataList) {
898         String newPortNodeTemplateId =
899             getNewPortNodeTemplateId(portTemplateConsolidationData.getNodeTemplateId(), computeType,
900                 computeTemplateConsolidationData);
901
902         updOutputParamGetAttrInConnectivity(serviceTemplate, portTemplateConsolidationData,
903             portTemplateConsolidationData.getNodeTemplateId(), newPortNodeTemplateId, context,
904             false);
905       }
906     }
907   }
908
909   protected void updNodesGetAttrInConnectivity(
910       ServiceTemplate serviceTemplate,
911       List<UnifiedCompositionData> unifiedComposotionDataList,
912       TranslationContext context) {
913     Map<String, UnifiedCompositionEntity> consolidationNodeTemplateIdAndType =
914         getAllConsolidationNodeTemplateIdAndType(unifiedComposotionDataList);
915     for (UnifiedCompositionData unifiedCompositionData : unifiedComposotionDataList) {
916       ComputeTemplateConsolidationData computeTemplateConsolidationData =
917           unifiedCompositionData.getComputeTemplateConsolidationData();
918       String newComputeNodeTemplateId = getNewComputeNodeTemplateId(serviceTemplate,
919           computeTemplateConsolidationData.getNodeTemplateId());
920
921       updNodeGetAttrInConnectivity(serviceTemplate, computeTemplateConsolidationData,
922           computeTemplateConsolidationData.getNodeTemplateId(),
923           newComputeNodeTemplateId, context, consolidationNodeTemplateIdAndType, false);
924
925       String computeType =
926           getComputeTypeSuffix(serviceTemplate,
927               computeTemplateConsolidationData.getNodeTemplateId());
928
929       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
930           getPortTemplateConsolidationDataList(unifiedCompositionData);
931       for (PortTemplateConsolidationData portTemplateConsolidationData :
932           portTemplateConsolidationDataList) {
933         String newPotNodeTemplateId =
934             getNewPortNodeTemplateId(portTemplateConsolidationData.getNodeTemplateId(), computeType,
935                 computeTemplateConsolidationData);
936
937         updNodeGetAttrInConnectivity(serviceTemplate, portTemplateConsolidationData,
938             portTemplateConsolidationData.getNodeTemplateId(),
939             newPotNodeTemplateId, context, consolidationNodeTemplateIdAndType, false);
940       }
941     }
942   }
943
944   protected void updNestedCompositionOutputParamGetAttrInConnectivity(
945       ServiceTemplate serviceTemplate, UnifiedCompositionData unifiedCompositionData,
946       TranslationContext context) {
947     NestedTemplateConsolidationData nestedTemplateConsolidationData =
948         unifiedCompositionData.getNestedTemplateConsolidationData();
949     if (Objects.isNull(nestedTemplateConsolidationData)) {
950       return;
951     }
952     String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
953     Optional<String> newNestedNodeTemplateId = context.getUnifiedNestedNodeTemplateId(
954         serviceTemplateFileName, nestedTemplateConsolidationData.getNodeTemplateId());
955
956     newNestedNodeTemplateId.ifPresent(
957         newNestedNodeTemplateIdVal -> updOutputParamGetAttrInConnectivity(serviceTemplate,
958             nestedTemplateConsolidationData, nestedTemplateConsolidationData.getNodeTemplateId(),
959             newNestedNodeTemplateIdVal, context, true));
960   }
961
962   protected void updNestedCompositionNodesGetAttrInConnectivity(
963       ServiceTemplate serviceTemplate,
964       UnifiedCompositionData unifiedCompositionData,
965       TranslationContext context) {
966     NestedTemplateConsolidationData nestedTemplateConsolidationData =
967         unifiedCompositionData.getNestedTemplateConsolidationData();
968     if (Objects.isNull(nestedTemplateConsolidationData)) {
969       return;
970     }
971     String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
972     Optional<String> newNestedNodeTemplateId = context.getUnifiedNestedNodeTemplateId(
973         serviceTemplateFileName, nestedTemplateConsolidationData.getNodeTemplateId());
974
975     newNestedNodeTemplateId.ifPresent(
976         newNestedNodeTemplateIdVal -> updNodeGetAttrInConnectivity(serviceTemplate,
977             nestedTemplateConsolidationData, nestedTemplateConsolidationData.getNodeTemplateId(),
978             newNestedNodeTemplateIdVal, context, null, true));
979   }
980
981   private void updateRequirementForNodesConnectedIn(
982       ServiceTemplate serviceTemplate,
983       RequirementAssignmentData requirementAssignmentData,
984       EntityConsolidationData entityConsolidationData,
985       String originalNodeTemplateId,
986       String newNodeTemplateId,
987       TranslationContext context) {
988     ToscaAnalyzerService toscaAnalyzerService = new ToscaAnalyzerServiceImpl();
989     RequirementAssignment requirementAssignment = requirementAssignmentData
990         .getRequirementAssignment();
991     String newAbstractUnifiedNodeTemplateId = context.getUnifiedAbstractNodeTemplateId(
992         serviceTemplate, entityConsolidationData.getNodeTemplateId());
993     NodeTemplate abstractUnifiedNodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate,
994         newAbstractUnifiedNodeTemplateId);
995     Optional<String> newCapabilityId = getNewCapabilityForNodesConnectedIn(serviceTemplate,
996         abstractUnifiedNodeTemplate, requirementAssignment, newNodeTemplateId, context);
997     if (newCapabilityId.isPresent()) {
998       //Creating a copy of the requirement object and checking if it already exists in the
999       // original node template
1000       RequirementAssignment requirementAssignmentCopy = (RequirementAssignment) getClonedObject(
1001           requirementAssignmentData.getRequirementAssignment(), RequirementAssignment.class);
1002       NodeTemplate originalNodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate,
1003           originalNodeTemplateId);
1004       requirementAssignmentCopy.setCapability(newCapabilityId.get());
1005       requirementAssignmentCopy.setNode(newAbstractUnifiedNodeTemplateId);
1006       if (!toscaAnalyzerService.isRequirementExistInNodeTemplate(originalNodeTemplate,
1007           requirementAssignmentData.getRequirementId(), requirementAssignmentCopy)) {
1008         //Update the existing requirement
1009         requirementAssignmentData.getRequirementAssignment().setCapability(newCapabilityId
1010             .get());
1011         requirementAssignmentData.getRequirementAssignment()
1012             .setNode(newAbstractUnifiedNodeTemplateId);
1013       } else {
1014         //The updated requirement already exists in the node template so simply remove the
1015         // current one
1016         DataModelUtil.removeRequirementAssignment(originalNodeTemplate, requirementAssignmentData
1017             .getRequirementId(), requirementAssignmentData.getRequirementAssignment());
1018       }
1019     }
1020   }
1021
1022   private void updateRequirementForNestedCompositionNodesConnectedIn(
1023       ServiceTemplate serviceTemplate,
1024       RequirementAssignmentData requirementAssignmentData,
1025       EntityConsolidationData entityConsolidationData,
1026       String newNodeTemplateId,
1027       TranslationContext context) {
1028     ToscaAnalyzerService toscaAnalyzerService = new ToscaAnalyzerServiceImpl();
1029     String newAbstractUnifiedNodeTemplateId = newNodeTemplateId;
1030     RequirementAssignment requirementAssignment = requirementAssignmentData
1031         .getRequirementAssignment();
1032     //Creating a copy of the requirement object and checking if it already exists in the
1033     // original node template
1034     RequirementAssignment requirementAssignmentCopy = (RequirementAssignment) getClonedObject(
1035         requirementAssignmentData.getRequirementAssignment(), RequirementAssignment.class);
1036     NodeTemplate unifiedAbstractNestedNodeTemplate = DataModelUtil
1037         .getNodeTemplate(serviceTemplate, newAbstractUnifiedNodeTemplateId);
1038     requirementAssignmentCopy.setCapability(requirementAssignment.getCapability());
1039     requirementAssignmentCopy.setNode(newAbstractUnifiedNodeTemplateId);
1040     if (!toscaAnalyzerService.isRequirementExistInNodeTemplate(unifiedAbstractNestedNodeTemplate,
1041         requirementAssignmentData.getRequirementId(), requirementAssignmentCopy)) {
1042       //Update the existing requirement
1043       requirementAssignmentData.getRequirementAssignment()
1044           .setNode(newAbstractUnifiedNodeTemplateId);
1045     } else {
1046       //The updated requirement already exists in the node template so simply remove the
1047       // current one
1048       DataModelUtil.removeRequirementAssignment(unifiedAbstractNestedNodeTemplate,
1049           requirementAssignmentData.getRequirementId(), requirementAssignmentData
1050               .getRequirementAssignment());
1051     }
1052   }
1053
1054   private Optional<String> getNewCapabilityForNodesConnectedIn(ServiceTemplate serviceTemplate,
1055                                                                NodeTemplate unifiedNodeTemplate,
1056                                                                RequirementAssignment
1057                                                                    requirementAssignment,
1058                                                                String newNodeTemplateId,
1059                                                                TranslationContext context) {
1060     ServiceTemplate globalSubstitutionServiceTemplate =
1061         HeatToToscaUtil.fetchGlobalSubstitutionServiceTemplate(serviceTemplate, context);
1062     Map<String, NodeType> nodeTypes = globalSubstitutionServiceTemplate.getNode_types();
1063     String unifiedNodeTemplateType = unifiedNodeTemplate.getType();
1064     NodeType unifiedNodeType = nodeTypes.get(unifiedNodeTemplateType);
1065     Map<String, CapabilityDefinition> abstractNodeTypeCapabilities = unifiedNodeType
1066         .getCapabilities();
1067     for (Map.Entry<String, CapabilityDefinition> entry : abstractNodeTypeCapabilities.entrySet()) {
1068       String capabilityId = entry.getKey();
1069       CapabilityDefinition capabilityDefinition = entry.getValue();
1070       String capabilityType = capabilityDefinition.getType();
1071       if (capabilityType.equals(requirementAssignment.getCapability())) {
1072         //Matching capability type found..Check if the id ends with new node template id
1073         if (capabilityId.endsWith(newNodeTemplateId)) {
1074           return Optional.ofNullable(capabilityId);
1075         }
1076       }
1077     }
1078     return Optional.empty();
1079   }
1080
1081
1082   private void updateRequirementInAbstractNodeTemplate(ServiceTemplate serviceTemplate,
1083                                                        EntityConsolidationData
1084                                                            entityConsolidationData,
1085                                                        String newNodeTemplateId,
1086                                                        Map<String, List<RequirementAssignmentData>>
1087                                                            requirementAssignmentDataMap,
1088                                                        TranslationContext context) {
1089     ToscaAnalyzerService toscaAnalyzerService = new ToscaAnalyzerServiceImpl();
1090     for (Map.Entry<String, List<RequirementAssignmentData>> entry : requirementAssignmentDataMap
1091         .entrySet()) {
1092       String abstractNodeTemplateId = context.getUnifiedAbstractNodeTemplateId(
1093           serviceTemplate, entityConsolidationData.getNodeTemplateId());
1094       NodeTemplate abstractNodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate,
1095           abstractNodeTemplateId);
1096       if (abstractNodeTemplate == null) {
1097         //The abstract node template is not found from id in the context
1098         return;
1099       }
1100       List<RequirementAssignmentData> requirementAssignmentDataList = entry.getValue();
1101       for (RequirementAssignmentData requirementAssignmentData : requirementAssignmentDataList) {
1102         String oldRequirementId = requirementAssignmentData.getRequirementId();
1103         RequirementAssignment abstractRequirementAssignment = (RequirementAssignment)
1104             getClonedObject(requirementAssignmentData.getRequirementAssignment(),
1105                 RequirementAssignment.class);
1106         String newRequirementId = oldRequirementId + "_" + newNodeTemplateId;
1107         //Check if the requirement is not already present in the list of requirements of the
1108         // abstract node template
1109         if (!toscaAnalyzerService.isRequirementExistInNodeTemplate(abstractNodeTemplate,
1110             newRequirementId, abstractRequirementAssignment)) {
1111           DataModelUtil.addRequirementAssignment(abstractNodeTemplate, newRequirementId,
1112               abstractRequirementAssignment);
1113           //Update the volume relationship template if required
1114           updateVolumeRelationshipTemplate(serviceTemplate, abstractRequirementAssignment
1115               .getRelationship(), context);
1116         }
1117       }
1118     }
1119   }
1120
1121   private void updateRequirementInNestedNodeTemplate(ServiceTemplate serviceTemplate,
1122                                                      EntityConsolidationData
1123                                                          entityConsolidationData,
1124                                                      String newNodeTemplateId,
1125                                                      Map<String, List<RequirementAssignmentData>>
1126                                                          requirementAssignmentDataMap) {
1127     ToscaAnalyzerService toscaAnalyzerService = new ToscaAnalyzerServiceImpl();
1128
1129     if (MapUtils.isEmpty(requirementAssignmentDataMap)) {
1130       return;
1131     }
1132
1133     for (Map.Entry<String, List<RequirementAssignmentData>> entry : requirementAssignmentDataMap
1134         .entrySet()) {
1135       String nodeTemplateId = entityConsolidationData.getNodeTemplateId();
1136       NodeTemplate nodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate, nodeTemplateId);
1137       if (nodeTemplate == null) {
1138         //The node template is not found from id in the context
1139         return;
1140       }
1141       List<RequirementAssignmentData> requirementAssignmentDataList = entry.getValue();
1142       for (RequirementAssignmentData requirementAssignmentData : requirementAssignmentDataList) {
1143         String oldRequirementId = requirementAssignmentData.getRequirementId();
1144         RequirementAssignment clonedRequirementAssignment = (RequirementAssignment)
1145             getClonedObject(requirementAssignmentData.getRequirementAssignment(),
1146                 RequirementAssignment.class);
1147         String newRequirementId = oldRequirementId + "_" + newNodeTemplateId;
1148         //Check if the requirement is not already present in the list of requirements of the
1149         // node template
1150         if (!toscaAnalyzerService.isRequirementExistInNodeTemplate(nodeTemplate,
1151             newRequirementId, clonedRequirementAssignment)) {
1152           DataModelUtil.removeRequirementAssignment(nodeTemplate, oldRequirementId,
1153               requirementAssignmentData.getRequirementAssignment());
1154           DataModelUtil.addRequirementAssignment(nodeTemplate, newRequirementId,
1155               clonedRequirementAssignment);
1156         }
1157       }
1158     }
1159   }
1160
1161   private NodeTemplate getAbstractNodeTemplate(
1162       ServiceTemplate serviceTemplate,
1163       UnifiedCompositionEntity unifiedCompositionEntity,
1164       ComputeTemplateConsolidationData computeTemplateConsolidationData,
1165       PortTemplateConsolidationData portTemplateConsolidationData,
1166       TranslationContext context) {
1167     String abstractNodeTemplateId =
1168         getAbstractNodeTemplateId(serviceTemplate, unifiedCompositionEntity,
1169             computeTemplateConsolidationData, portTemplateConsolidationData, context);
1170
1171     return DataModelUtil.getNodeTemplate(serviceTemplate,
1172         abstractNodeTemplateId);
1173   }
1174
1175   private String getAbstractNodeTemplateId(
1176       ServiceTemplate serviceTemplate,
1177       UnifiedCompositionEntity unifiedCompositionEntity,
1178       ComputeTemplateConsolidationData computeTemplateConsolidationData,
1179       PortTemplateConsolidationData portTemplateConsolidationData,
1180       TranslationContext context) {
1181     switch (unifiedCompositionEntity) {
1182       case Compute:
1183         return context.getUnifiedAbstractNodeTemplateId(serviceTemplate,
1184             computeTemplateConsolidationData.getNodeTemplateId());
1185       case Port:
1186         return context.getUnifiedAbstractNodeTemplateId(serviceTemplate,
1187             portTemplateConsolidationData.getNodeTemplateId());
1188       default:
1189         return null;
1190     }
1191   }
1192
1193   private void updNodeGetAttrInConnectivity(
1194       ServiceTemplate serviceTemplate,
1195       EntityConsolidationData entityConsolidationData,
1196       String oldNodeTemplateId, String newNodeTemplateId,
1197       TranslationContext context,
1198       Map<String, UnifiedCompositionEntity> consolidationNodeTemplateIdAndType,
1199       boolean isNested) {
1200     Map<String, List<GetAttrFuncData>> nodesGetAttrIn = entityConsolidationData.getNodesGetAttrIn();
1201     if (MapUtils.isEmpty(nodesGetAttrIn)) {
1202       return;
1203     }
1204
1205     for (String sourceNodeTemplateId : nodesGetAttrIn.keySet()) {
1206       NodeTemplate sourceNodeTemplate =
1207           DataModelUtil.getNodeTemplate(serviceTemplate, sourceNodeTemplateId);
1208       if (!isNested && consolidationNodeTemplateIdAndType.keySet().contains(sourceNodeTemplateId)) {
1209         continue;
1210       }
1211       List<GetAttrFuncData> getAttrFuncDataList = nodesGetAttrIn.get(sourceNodeTemplateId);
1212       for (GetAttrFuncData getAttrFuncData : getAttrFuncDataList) {
1213         Object propertyValue =
1214             DataModelUtil.getPropertyValue(sourceNodeTemplate, getAttrFuncData.getFieldName());
1215         String newAttrName = null;
1216         String newGetAttrAbstractNodeTemplateId = newNodeTemplateId;
1217         if (!isNested) {
1218           newGetAttrAbstractNodeTemplateId =
1219               context.getUnifiedAbstractNodeTemplateId(serviceTemplate, oldNodeTemplateId);
1220           newAttrName = getNewSubstitutionOutputParameterId(newNodeTemplateId, getAttrFuncData
1221               .getAttributeName());
1222         }
1223         List<List<Object>> getAttrFuncValueList = extractGetAttrFunction(propertyValue);
1224         updateGetAttrValue(oldNodeTemplateId, getAttrFuncData, newGetAttrAbstractNodeTemplateId,
1225             newAttrName, getAttrFuncValueList, isNested);
1226       }
1227     }
1228   }
1229
1230   private void updateGetAttrValue(String oldNodeTemplateId, GetAttrFuncData getAttrFuncData,
1231                                   String newNodeTemplateId, String newAttrName,
1232                                   List<List<Object>> getAttrFuncValueList, boolean isNested) {
1233     for (List<Object> getAttrFuncValue : getAttrFuncValueList) {
1234       if (oldNodeTemplateId.equals(getAttrFuncValue.get(0))
1235           && getAttrFuncData.getAttributeName().equals(getAttrFuncValue.get(1))) {
1236         getAttrFuncValue.set(0, newNodeTemplateId);
1237         if (!isNested) {
1238           getAttrFuncValue.set(1, newAttrName);
1239         }
1240       }
1241     }
1242   }
1243
1244   private String getTemplateName(ServiceTemplate serviceTemplate,
1245                                  UnifiedCompositionData unifiedCompositionData,
1246                                  String nodeTypeId,
1247                                  Integer index) {
1248     ComputeTemplateConsolidationData computeTemplateConsolidationData =
1249         unifiedCompositionData.getComputeTemplateConsolidationData();
1250     String computeType = getComputeTypeSuffix(nodeTypeId);
1251     String templateName = "Nested_" + computeType;
1252     if (Objects.nonNull(index)) {
1253       templateName = templateName + "_" + index.toString();
1254     }
1255     return templateName;
1256   }
1257
1258   private String getComputeTypeSuffix(ServiceTemplate serviceTemplate,
1259                                       String computeNodeTemplateId) {
1260     NodeTemplate computeNodeTemplate =
1261         DataModelUtil.getNodeTemplate(serviceTemplate, computeNodeTemplateId);
1262     return getComputeTypeSuffix(computeNodeTemplate.getType());
1263   }
1264
1265   /**
1266    * Gets compute type.
1267    *
1268    * @param computeType the compute node type abc.def.vFSB
1269    * @return the compute type e.g.:vFSB
1270    */
1271   private String getComputeTypeSuffix(String computeType) {
1272     return DataModelUtil.getNamespaceSuffix(computeType);
1273   }
1274
1275   private void updOutputParamGetAttrInConnectivity(ServiceTemplate serviceTemplate,
1276                                                    EntityConsolidationData entityConsolidationData,
1277                                                    String oldNodeTemplateId,
1278                                                    String newNodeTemplateId,
1279                                                    TranslationContext context,
1280                                                    boolean isNested) {
1281     List<GetAttrFuncData> outputParametersGetAttrIn =
1282         entityConsolidationData.getOutputParametersGetAttrIn();
1283     if (CollectionUtils.isEmpty(outputParametersGetAttrIn)) {
1284       return;
1285     }
1286     for (GetAttrFuncData getAttrFuncData : outputParametersGetAttrIn) {
1287       Object outputParamValue =
1288           DataModelUtil.getOuputParameter(serviceTemplate, getAttrFuncData.getFieldName())
1289               .getValue();
1290       String newAttrName = null;
1291       String newGetAttrAbstractNodeTemplateId = newNodeTemplateId;
1292       if (!isNested) {
1293         newGetAttrAbstractNodeTemplateId =
1294             context.getUnifiedAbstractNodeTemplateId(serviceTemplate, oldNodeTemplateId);
1295         newAttrName = getNewSubstitutionOutputParameterId(newNodeTemplateId, getAttrFuncData
1296             .getAttributeName());
1297       }
1298       List<List<Object>> getAttrFuncValueList = extractGetAttrFunction(outputParamValue);
1299       updateGetAttrValue(oldNodeTemplateId, getAttrFuncData, newGetAttrAbstractNodeTemplateId,
1300           newAttrName,
1301           getAttrFuncValueList, isNested);
1302     }
1303
1304   }
1305
1306   private List<List<Object>> extractGetAttrFunction(Object valueObject) {
1307
1308     List<List<Object>> getAttrValueList = new ArrayList<>();
1309
1310     if (valueObject instanceof Map) {
1311       if (((Map) valueObject).containsKey(ToscaFunctions.GET_ATTRIBUTE.getDisplayName())) {
1312         getAttrValueList.add(
1313             (List<Object>) ((Map) valueObject).get(ToscaFunctions.GET_ATTRIBUTE.getDisplayName()));
1314       }
1315
1316       for (Object key : ((Map) valueObject).keySet()) {
1317         getAttrValueList.addAll(extractGetAttrFunction(((Map) valueObject).get(key)));
1318       }
1319
1320
1321     } else if (valueObject instanceof List) {
1322       for (Object valueEntity : (List) valueObject) {
1323         getAttrValueList.addAll(extractGetAttrFunction(valueEntity));
1324       }
1325     }
1326     return getAttrValueList;
1327   }
1328
1329   private boolean isIncludeToscaFunc(Object valueObject, ToscaFunctions toscaFunction) {
1330     if (valueObject instanceof Map) {
1331       if (((Map) valueObject).containsKey(toscaFunction.getDisplayName())) {
1332         return true;
1333       }
1334
1335       Set<Map.Entry<String, Object>> entries = ((Map<String, Object>) valueObject).entrySet();
1336       for (Map.Entry<String, Object> valueObjectEntry : entries) {
1337         if (isIncludeToscaFunc(valueObjectEntry.getValue(), toscaFunction)) {
1338           return true;
1339         }
1340       }
1341 //      Map.Entry<String, Object> functionMapEntry =
1342 //          (Map.Entry<String, Object>) ((Map) valueObject).entrySet().iterator().next();
1343 //      return isIncludeToscaFunc(functionMapEntry.getValue(), toscaFunction);
1344
1345     } else if (valueObject instanceof List) {
1346       for (Object valueEntity : (List) valueObject) {
1347         if (isIncludeToscaFunc(valueEntity, toscaFunction) == true) {
1348           return true;
1349         }
1350       }
1351     }
1352     return false;
1353   }
1354
1355   private void createOutputParameters(ServiceTemplate serviceTemplate,
1356                                       ServiceTemplate substitutionServiceTemplate,
1357                                       List<UnifiedCompositionData> unifiedCompositionDataList,
1358                                       String computeNodeType, TranslationContext context) {
1359
1360     createOutputParametersForCompute(serviceTemplate, substitutionServiceTemplate,
1361         unifiedCompositionDataList, context);
1362     createOutputParameterForPorts(serviceTemplate, substitutionServiceTemplate,
1363         unifiedCompositionDataList, computeNodeType, context);
1364   }
1365
1366   private void createOutputParameterForPorts(
1367       ServiceTemplate serviceTemplate,
1368       ServiceTemplate substitutionServiceTemplate,
1369       List<UnifiedCompositionData> unifiedCompositionDataList,
1370       String connectedComputeNodeType,
1371       TranslationContext context) {
1372     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
1373       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
1374           getPortTemplateConsolidationDataList(unifiedCompositionData);
1375       if (CollectionUtils.isEmpty(portTemplateConsolidationDataList)) {
1376         return;
1377       }
1378
1379       for (PortTemplateConsolidationData portTemplateConsolidationData :
1380           portTemplateConsolidationDataList) {
1381         String newPortNodeTemplateId =
1382             getNewPortNodeTemplateId(portTemplateConsolidationData.getNodeTemplateId(),
1383                 connectedComputeNodeType,
1384                 unifiedCompositionData.getComputeTemplateConsolidationData());
1385         addOutputParameters(portTemplateConsolidationData, newPortNodeTemplateId,
1386             serviceTemplate, substitutionServiceTemplate, unifiedCompositionDataList, context);
1387       }
1388     }
1389   }
1390
1391   //The ID should be <vm_type>_<port_type> or <vm_type>_<portNodeTemplateId>
1392   private String getNewPortNodeTemplateId(
1393       String portNodeTemplateId,
1394       String connectedComputeNodeType,
1395       ComputeTemplateConsolidationData computeTemplateConsolidationData) {
1396
1397     StringBuilder newPortNodeTemplateId = new StringBuilder();
1398     String portType = ConsolidationDataUtil.getPortType(portNodeTemplateId);
1399     newPortNodeTemplateId.append(DataModelUtil.getNamespaceSuffix(connectedComputeNodeType));
1400     if (computeTemplateConsolidationData.getPorts().get(portType).size() > 1) {
1401       //single port
1402       newPortNodeTemplateId.append("_").append(portNodeTemplateId);
1403     } else {
1404       //consolidation port
1405       newPortNodeTemplateId.append("_").append(portType);
1406     }
1407     return newPortNodeTemplateId.toString();
1408   }
1409
1410   private void createOutputParametersForCompute(
1411       ServiceTemplate serviceTemplate,
1412       ServiceTemplate substitutionServiceTemplate,
1413       List<UnifiedCompositionData>
1414           unifiedCompositionDataList,
1415       TranslationContext context) {
1416     List<EntityConsolidationData> computeConsolidationDataList =
1417         getComputeConsolidationDataList(unifiedCompositionDataList);
1418
1419     for (EntityConsolidationData computeTemplateConsolidationData : computeConsolidationDataList) {
1420       String newComputeNodeTemplateId =
1421           getNewComputeNodeTemplateId(serviceTemplate,
1422               computeTemplateConsolidationData.getNodeTemplateId());
1423       addOutputParameters(computeTemplateConsolidationData, newComputeNodeTemplateId,
1424           serviceTemplate, substitutionServiceTemplate, unifiedCompositionDataList, context);
1425     }
1426   }
1427
1428   private void addOutputParameters(EntityConsolidationData entityConsolidationData,
1429                                    String newNodeTemplateId,
1430                                    ServiceTemplate serviceTemplate,
1431                                    ServiceTemplate substitutionServiceTemplate,
1432                                    List<UnifiedCompositionData> unifiedCompositionDataList,
1433                                    TranslationContext context) {
1434     handleNodesGetAttrIn(entityConsolidationData, newNodeTemplateId, serviceTemplate,
1435         substitutionServiceTemplate, unifiedCompositionDataList, context);
1436
1437     handleOutputParamGetAttrIn(entityConsolidationData, newNodeTemplateId, serviceTemplate,
1438         substitutionServiceTemplate, context);
1439   }
1440
1441   private void handleOutputParamGetAttrIn(EntityConsolidationData entityConsolidationData,
1442                                           String newNodeTemplateId,
1443                                           ServiceTemplate serviceTemplate,
1444                                           ServiceTemplate substitutionServiceTemplate,
1445                                           TranslationContext context) {
1446     List<GetAttrFuncData> outputParametersGetAttrIn =
1447         entityConsolidationData.getOutputParametersGetAttrIn();
1448     if (!CollectionUtils.isEmpty(outputParametersGetAttrIn)) {
1449       for (GetAttrFuncData getAttrFuncData : outputParametersGetAttrIn) {
1450         createAndAddOutputParameter(entityConsolidationData, newNodeTemplateId,
1451             substitutionServiceTemplate, getAttrFuncData, context);
1452       }
1453     }
1454   }
1455
1456   private void handleNodesGetAttrIn(EntityConsolidationData entityConsolidationData,
1457                                     String newNodeTemplateId,
1458                                     ServiceTemplate serviceTemplate,
1459                                     ServiceTemplate substitutionServiceTemplate,
1460                                     List<UnifiedCompositionData> unifiedCompositionDataList,
1461                                     TranslationContext context) {
1462     Map<String, List<GetAttrFuncData>> getAttrIn = entityConsolidationData.getNodesGetAttrIn();
1463
1464     if (!MapUtils.isEmpty(getAttrIn)) {
1465       Map<String, UnifiedCompositionEntity> consolidationNodeTemplateIdAndType =
1466           getAllConsolidationNodeTemplateIdAndType(unifiedCompositionDataList);
1467       for (String sourceNodeTemplateId : getAttrIn.keySet()) {
1468         if (!consolidationNodeTemplateIdAndType.keySet().contains(sourceNodeTemplateId)) {
1469           List<GetAttrFuncData> getAttrFuncDataList = getAttrIn.get(sourceNodeTemplateId);
1470           for (GetAttrFuncData getAttrFuncData : getAttrFuncDataList) {
1471             createAndAddOutputParameter(entityConsolidationData, newNodeTemplateId,
1472                 substitutionServiceTemplate, getAttrFuncData, context);
1473           }
1474         }
1475       }
1476     }
1477   }
1478
1479   private void createAndAddOutputParameter(EntityConsolidationData entityConsolidationData,
1480                                            String newNodeTemplateId,
1481                                            ServiceTemplate substitutionServiceTemplate,
1482                                            GetAttrFuncData getAttrFuncData,
1483                                            TranslationContext context) {
1484     Map<String, List<Object>> parameterValue = new HashMap<>();
1485     List<Object> valueList = new ArrayList<>();
1486     valueList.add(newNodeTemplateId);
1487     valueList.add(getAttrFuncData.getAttributeName());
1488     parameterValue.put(ToscaFunctions.GET_ATTRIBUTE.getDisplayName(), valueList);
1489     ParameterDefinition outputParameter = new ParameterDefinition();
1490     outputParameter.setValue(parameterValue);
1491     setOutputParameterType(substitutionServiceTemplate, newNodeTemplateId, getAttrFuncData
1492         .getAttributeName(), outputParameter, context);
1493     DataModelUtil.addOutputParameterToTopologyTemplate(substitutionServiceTemplate,
1494         getNewSubstitutionOutputParameterId(newNodeTemplateId, getAttrFuncData.getAttributeName()),
1495         outputParameter);
1496   }
1497
1498   private void setOutputParameterType(ServiceTemplate substitutionServiceTemplate,
1499                                       String newNodeTemplateId,
1500                                       String outputParameterName,
1501                                       ParameterDefinition outputParameter,
1502                                       TranslationContext context) {
1503     NodeTemplate nodeTemplate = DataModelUtil.getNodeTemplate(substitutionServiceTemplate,
1504         newNodeTemplateId);
1505     //Get the type and entry schema of the output parameter from the node type flat hierarchy
1506     String outputParameterType = null;
1507     EntrySchema outputParameterEntrySchema = null;
1508     NodeType nodeTypeWithFlatHierarchy =
1509         HeatToToscaUtil.getNodeTypeWithFlatHierarchy(nodeTemplate.getType(),
1510             substitutionServiceTemplate, context);
1511     //Check if the parameter is present in the attributes
1512     AttributeDefinition outputParameterDefinitionFromAttributes =
1513         getOutputParameterDefinitionFromAttributes(nodeTypeWithFlatHierarchy, outputParameterName);
1514     if (Objects.nonNull(outputParameterDefinitionFromAttributes)) {
1515       outputParameterType = outputParameterDefinitionFromAttributes.getType();
1516       outputParameterEntrySchema = outputParameterDefinitionFromAttributes.getEntry_schema();
1517     } else {
1518       //If the below fails due to null pointer then we need to check if the heatToToscaMapping
1519       // properties and global types are in sync. Ideally the parameter should be found in either
1520       // properties or attributes collected from global types
1521       PropertyDefinition outputParameterDefinitionFromProperties =
1522           nodeTypeWithFlatHierarchy.getProperties().get(outputParameterName);
1523       outputParameterType = outputParameterDefinitionFromProperties.getType();
1524       outputParameterEntrySchema = outputParameterDefinitionFromProperties.getEntry_schema();
1525     }
1526     //Set the type and entry schema for the output param obtained from the node type hierarchy
1527     outputParameter.setType(outputParameterType);
1528     outputParameter.setEntry_schema(outputParameterEntrySchema);
1529   }
1530
1531   private String getNewInputParameterType(NodeTemplate nodeTemplate,
1532                                           ServiceTemplate serviceTemplate,
1533                                           String inputParameterName,
1534                                           TranslationContext context) {
1535     NodeType nodeTypeWithFlatHierarchy =
1536         HeatToToscaUtil.getNodeTypeWithFlatHierarchy(nodeTemplate.getType(),
1537             serviceTemplate, context);
1538     String parameterType = nodeTypeWithFlatHierarchy.getProperties()
1539         .get(inputParameterName).getType();
1540     return getUnifiedInputParameterType(parameterType);
1541   }
1542
1543   private AttributeDefinition getOutputParameterDefinitionFromAttributes(NodeType
1544                                                                              nodeTypeWithFlatHierarchy,
1545                                                                          String outputParameterName) {
1546     AttributeDefinition outputParameterDefinition = null;
1547     if ((Objects.nonNull(nodeTypeWithFlatHierarchy.getAttributes()))
1548         && (nodeTypeWithFlatHierarchy.getAttributes().containsKey(outputParameterName))) {
1549       outputParameterDefinition =
1550           nodeTypeWithFlatHierarchy.getAttributes().get(outputParameterName);
1551     }
1552     return outputParameterDefinition;
1553   }
1554
1555   private String getUnifiedInputParameterType(String parameterType) {
1556     String unifiedInputParameterType = null;
1557     if (Objects.nonNull(parameterType)) {
1558       if (parameterType.equalsIgnoreCase(PropertyType.STRING.getDisplayName())
1559           || parameterType.equalsIgnoreCase(PropertyType.INTEGER.getDisplayName())
1560           || parameterType.equalsIgnoreCase(PropertyType.FLOAT.getDisplayName())
1561           || parameterType.equalsIgnoreCase(PropertyType.BOOLEAN.getDisplayName())
1562           || parameterType.equalsIgnoreCase(PropertyType.TIMESTAMP.getDisplayName())
1563           || parameterType.equalsIgnoreCase(PropertyType.NULL.getDisplayName())
1564           || parameterType.equalsIgnoreCase(PropertyType.SCALAR_UNIT_SIZE.getDisplayName())
1565           || parameterType.equalsIgnoreCase(PropertyType.SCALAR_UNIT_FREQUENCY.getDisplayName())) {
1566         unifiedInputParameterType = parameterType.toLowerCase();
1567       } else if (parameterType.equalsIgnoreCase(PropertyType.MAP.getDisplayName())
1568           || parameterType.equalsIgnoreCase(PropertyType.LIST.getDisplayName())
1569           || parameterType.equalsIgnoreCase(PropertyTypeExt.JSON.getDisplayName())) {
1570         unifiedInputParameterType = PropertyTypeExt.JSON.getDisplayName();
1571       } else {
1572         unifiedInputParameterType = parameterType;
1573       }
1574     }
1575     return unifiedInputParameterType;
1576   }
1577
1578   private String getNewSubstitutionOutputParameterId(String newNodeTemplateId,
1579                                                      String attributeName) {
1580     return newNodeTemplateId + "_" + attributeName;
1581   }
1582
1583   private void addUnifiedSubstitionData(TranslationContext context, ServiceTemplate
1584       serviceTemplate, List<UnifiedCompositionData> unifiedCompositionDataList, String
1585                                             substituteNodeTemplateId) {
1586     String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
1587     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
1588       //Add compute node template mapping information
1589       ComputeTemplateConsolidationData computeTemplateConsolidationData =
1590           unifiedCompositionData.getComputeTemplateConsolidationData();
1591       String computeNodeTemplateId = computeTemplateConsolidationData.getNodeTemplateId();
1592       context.addUnifiedSubstitutionData(serviceTemplateFileName, computeNodeTemplateId,
1593           substituteNodeTemplateId);
1594       //Add Port template mapping information
1595       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
1596           getPortTemplateConsolidationDataList(unifiedCompositionData);
1597
1598       if (CollectionUtils.isNotEmpty(portTemplateConsolidationDataList)) {
1599         for (PortTemplateConsolidationData portTemplateConsolidationData :
1600             portTemplateConsolidationDataList) {
1601           String oldPortNodeTemplateId = portTemplateConsolidationData.getNodeTemplateId();
1602           context.addUnifiedSubstitutionData(serviceTemplateFileName, oldPortNodeTemplateId,
1603               substituteNodeTemplateId);
1604         }
1605       }
1606     }
1607   }
1608
1609   private void addIndexValueProperty(NodeTemplate nodeTemplate) {
1610     List<String> indexValueGetPropertyValue = new ArrayList<>();
1611     indexValueGetPropertyValue.add(ToscaConstants.MODELABLE_ENTITY_NAME_SELF);
1612     indexValueGetPropertyValue.add(ToscaConstants.SERVICE_TEMPLATE_FILTER_PROPERTY_NAME);
1613     indexValueGetPropertyValue.add(ToscaConstants.INDEX_VALUE_PROPERTY_NAME);
1614
1615     Map<String, Object> indexPropertyValue = new HashMap<>();
1616     Map<String, Object> properties = nodeTemplate.getProperties();
1617     indexPropertyValue.put(ToscaFunctions.GET_PROPERTY.getDisplayName(),
1618         indexValueGetPropertyValue);
1619     properties.put(ToscaConstants.INDEX_VALUE_PROPERTY_NAME,
1620         indexPropertyValue);
1621     nodeTemplate.setProperties(properties);
1622   }
1623
1624   private String getSubstituteNodeTemplateId(ServiceTemplate serviceTemplate,
1625                                              UnifiedCompositionData unifiedCompositionData,
1626                                              String nodeTypeId,
1627                                              Integer index) {
1628     String computeNodeTemplateId =
1629         unifiedCompositionData.getComputeTemplateConsolidationData().getNodeTemplateId();
1630     NodeTemplate computeNodeTemplate =
1631         DataModelUtil.getNodeTemplate(serviceTemplate, computeNodeTemplateId);
1632     String nodeTemplateId = ABSTRACT_NODE_TEMPLATE_ID_PREFIX + DataModelUtil
1633         .getNamespaceSuffix(nodeTypeId);
1634     if (Objects.nonNull(index)) {
1635       nodeTemplateId = nodeTemplateId + "_" + index.toString();
1636     }
1637     return nodeTemplateId;
1638   }
1639
1640   /**
1641    * Gets substitution node type id.
1642    *
1643    * @param serviceTemplate        the service template
1644    * @param unifiedCompositionData the unified composition data
1645    * @param index                  the index
1646    * @return the substitution node type id
1647    */
1648   public String getSubstitutionNodeTypeId(ServiceTemplate serviceTemplate,
1649                                           UnifiedCompositionData unifiedCompositionData,
1650                                           Integer index,
1651                                           TranslationContext context) {
1652     String computeNodeTemplateId =
1653         unifiedCompositionData.getComputeTemplateConsolidationData().getNodeTemplateId();
1654     NodeTemplate computeNodeTemplate =
1655         DataModelUtil.getNodeTemplate(serviceTemplate, computeNodeTemplateId);
1656     String computeType = computeNodeTemplate.getType();
1657     String globalSTName = ToscaUtil.getServiceTemplateFileName(Constants
1658         .GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME);
1659
1660     String nodeTypeId = ToscaNodeType.ABSTRACT_NODE_TYPE_PREFIX
1661         + DataModelUtil.getNamespaceSuffix(getIndexedGlobalNodeTypeId(computeType, context));
1662
1663     context.updateUsedTimesForNestedComputeNodeType(globalSTName, computeType);
1664
1665     if (Objects.nonNull(index)) {
1666       nodeTypeId = nodeTypeId + "_" + index.toString();
1667     }
1668     return nodeTypeId;
1669   }
1670
1671   private String getNewComputeNodeTemplateId(
1672       ServiceTemplate serviceTemplate,
1673       String computeNodeTemplateId) {
1674     return getComputeTypeSuffix(serviceTemplate, computeNodeTemplateId);
1675   }
1676
1677   private NodeType handleSubstitutionGlobalNodeType(ServiceTemplate serviceTemplate,
1678                                                     ServiceTemplate substitutionServiceTemplate,
1679                                                     TranslationContext context,
1680                                                     UnifiedCompositionData unifiedCompositionData,
1681                                                     String substitutionNodeTypeId,
1682                                                     Integer index) {
1683     NodeType substitutionNodeType = new ToscaAnalyzerServiceImpl()
1684         .createInitSubstitutionNodeType(substitutionServiceTemplate,
1685             ToscaNodeType.VFC_ABSTRACT_SUBSTITUTE);
1686     ServiceTemplate globalSubstitutionServiceTemplate =
1687         HeatToToscaUtil.fetchGlobalSubstitutionServiceTemplate(serviceTemplate, context);
1688     DataModelUtil.addNodeType(globalSubstitutionServiceTemplate, substitutionNodeTypeId,
1689         substitutionNodeType);
1690
1691     return substitutionNodeType;
1692   }
1693
1694   private void handlePorts(ServiceTemplate serviceTemplate,
1695                            ServiceTemplate substitutionServiceTemplate,
1696                            List<UnifiedCompositionData> unifiedCompositionDataList,
1697                            String connectedComputeNodeType,
1698                            TranslationContext context) {
1699
1700     if (unifiedCompositionDataList.size() > 1) {
1701       handleConsolidationPorts(serviceTemplate, substitutionServiceTemplate,
1702           unifiedCompositionDataList, connectedComputeNodeType, context);
1703     } else {
1704       handleSinglePorts(serviceTemplate, substitutionServiceTemplate, connectedComputeNodeType,
1705           unifiedCompositionDataList, context);
1706     }
1707   }
1708
1709   private void handleSinglePorts(ServiceTemplate serviceTemplate,
1710                                  ServiceTemplate substitutionServiceTemplate,
1711                                  String connectedComputeNodeType,
1712                                  List<UnifiedCompositionData> unifiedCompositionDataList,
1713                                  TranslationContext context) {
1714     UnifiedCompositionData unifiedCompositionData = unifiedCompositionDataList.get(0);
1715     List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
1716         getPortTemplateConsolidationDataList(unifiedCompositionData);
1717     if (CollectionUtils.isEmpty(portTemplateConsolidationDataList)) {
1718       return;
1719     }
1720     for (PortTemplateConsolidationData portTemplateConsolidationData :
1721         portTemplateConsolidationDataList) {
1722       List<EntityConsolidationData> portConsolidationDataList = new ArrayList<>();
1723       portConsolidationDataList.add(portTemplateConsolidationData);
1724       handlePortNodeTemplate(serviceTemplate, substitutionServiceTemplate,
1725           portConsolidationDataList, connectedComputeNodeType,
1726           unifiedCompositionData.getComputeTemplateConsolidationData(),
1727           unifiedCompositionDataList, context);
1728     }
1729   }
1730
1731   private void handleConsolidationPorts(ServiceTemplate serviceTemplate,
1732                                         ServiceTemplate substitutionServiceTemplate,
1733                                         List<UnifiedCompositionData> unifiedCompositionDataList,
1734                                         String connectedComputeNodeType,
1735                                         TranslationContext context) {
1736     Collection<ComputeTemplateConsolidationData> computeConsolidationDataList =
1737         (Collection) getComputeConsolidationDataList(unifiedCompositionDataList);
1738
1739     Map<String, List<String>> portIdsPerPortType = UnifiedCompositionUtil
1740         .collectAllPortsFromEachTypesFromComputes(computeConsolidationDataList);
1741
1742     for (String portType : portIdsPerPortType.keySet()) {
1743       List<EntityConsolidationData> portTemplateConsolidationDataList =
1744           getPortConsolidationDataList(portIdsPerPortType.get(portType),
1745               unifiedCompositionDataList);
1746       if (CollectionUtils.isEmpty(portTemplateConsolidationDataList)) {
1747         continue;
1748       }
1749
1750       handlePortNodeTemplate(serviceTemplate, substitutionServiceTemplate,
1751           portTemplateConsolidationDataList, connectedComputeNodeType,
1752           unifiedCompositionDataList.get(0).getComputeTemplateConsolidationData(),
1753           unifiedCompositionDataList, context);
1754     }
1755   }
1756
1757   private void handlePortNodeTemplate(
1758       ServiceTemplate serviceTemplate,
1759       ServiceTemplate substitutionServiceTemplate,
1760       List<EntityConsolidationData> portTemplateConsolidationDataList,
1761       String connectedComputeNodeType,
1762       ComputeTemplateConsolidationData computeTemplateConsolidationData,
1763       List<UnifiedCompositionData> unifiedCompositionDataList,
1764       TranslationContext context) {
1765     EntityConsolidationData portTemplateConsolidationData =
1766         portTemplateConsolidationDataList.get(0);
1767     NodeTemplate newPortNodeTemplate = getNodeTemplate(
1768         portTemplateConsolidationData.getNodeTemplateId(), serviceTemplate, context).clone();
1769
1770     removeConnectivityOut(portTemplateConsolidationData, newPortNodeTemplate);
1771     handleProperties(serviceTemplate, newPortNodeTemplate,
1772         substitutionServiceTemplate, UnifiedCompositionEntity.Port,
1773         portTemplateConsolidationDataList, computeTemplateConsolidationData,
1774         unifiedCompositionDataList, context);
1775
1776     String newPortNodeTemplateId =
1777         getNewPortNodeTemplateId(portTemplateConsolidationData
1778                 .getNodeTemplateId(), connectedComputeNodeType,
1779             computeTemplateConsolidationData);
1780     //Update requirements for relationships between the consolidation entities
1781     handleConsolidationEntitiesRequirementConnectivity(newPortNodeTemplate,
1782         serviceTemplate, context);
1783     DataModelUtil.addNodeTemplate(substitutionServiceTemplate, newPortNodeTemplateId,
1784         newPortNodeTemplate);
1785
1786     //Add the node template mapping in the context for handling requirement updation
1787     for (EntityConsolidationData data : portTemplateConsolidationDataList) {
1788       String newPortTemplateId = getNewPortNodeTemplateId(data.getNodeTemplateId(),
1789           connectedComputeNodeType, computeTemplateConsolidationData);
1790       context.addSubstitutionServiceTemplateUnifiedSubstitutionData(ToscaUtil
1791               .getServiceTemplateFileName(serviceTemplate), data.getNodeTemplateId(),
1792           newPortTemplateId);
1793     }
1794
1795   }
1796
1797   private NodeTemplate getNodeTemplate(String nodeTemplateId, ServiceTemplate serviceTemplate,
1798                                        TranslationContext context) {
1799
1800     NodeTemplate nodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate, nodeTemplateId);
1801
1802     if (Objects.isNull(nodeTemplate)) {
1803       nodeTemplate = context
1804           .getCleanedNodeTemplate(ToscaUtil.getServiceTemplateFileName(serviceTemplate),
1805               nodeTemplateId);
1806
1807     }
1808     return nodeTemplate;
1809   }
1810
1811
1812   private String handleCompute(ServiceTemplate serviceTemplate,
1813                                ServiceTemplate substitutionServiceTemplate,
1814                                List<UnifiedCompositionData> unifiedCompositionDataList,
1815                                TranslationContext context) {
1816     ComputeTemplateConsolidationData computeTemplateConsolidationData =
1817         unifiedCompositionDataList.get(0).getComputeTemplateConsolidationData();
1818     handleComputeNodeTemplate(serviceTemplate, substitutionServiceTemplate,
1819         unifiedCompositionDataList, context);
1820     ServiceTemplate globalSubstitutionServiceTemplate =
1821         HeatToToscaUtil.fetchGlobalSubstitutionServiceTemplate(serviceTemplate, context);
1822     return handleComputeNodeType(serviceTemplate, substitutionServiceTemplate,
1823         computeTemplateConsolidationData);
1824   }
1825
1826   private String handleComputeNodeType(
1827       ServiceTemplate serviceTemplate,
1828       ServiceTemplate substitutionServiceTemplate,
1829       ComputeTemplateConsolidationData computeTemplateConsolidationData) {
1830     NodeTemplate computeNodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate,
1831         computeTemplateConsolidationData.getNodeTemplateId());
1832     String computeNodeTypeId = computeNodeTemplate.getType();
1833     NodeType computeNodeType =
1834         DataModelUtil.getNodeType(serviceTemplate, computeNodeTypeId);
1835     DataModelUtil
1836         .addNodeType(substitutionServiceTemplate, computeNodeTypeId, computeNodeType);
1837
1838     return computeNodeTypeId;
1839   }
1840
1841   private String getComputeNodeType(String nodeType) {
1842     String computeTypeSuffix = getComputeTypeSuffix(nodeType);
1843     return ToscaNodeType.COMPUTE_TYPE_PREFIX + "." + computeTypeSuffix;
1844   }
1845
1846   private void handleComputeNodeTemplate(ServiceTemplate serviceTemplate,
1847                                          ServiceTemplate substitutionServiceTemplate,
1848                                          List<UnifiedCompositionData> unifiedCompositionDataList,
1849                                          TranslationContext context) {
1850     ComputeTemplateConsolidationData computeTemplateConsolidationData =
1851         unifiedCompositionDataList.get(0).getComputeTemplateConsolidationData();
1852     NodeTemplate newComputeNodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate,
1853         computeTemplateConsolidationData.getNodeTemplateId()).clone();
1854
1855     removeConnectivityOut(computeTemplateConsolidationData, newComputeNodeTemplate);
1856     removeVolumeConnectivity(computeTemplateConsolidationData, newComputeNodeTemplate);
1857
1858     List<EntityConsolidationData> computeConsoliadtionDataList =
1859         getComputeConsolidationDataList(unifiedCompositionDataList);
1860
1861     handleProperties(serviceTemplate, newComputeNodeTemplate,
1862         substitutionServiceTemplate, UnifiedCompositionEntity.Compute,
1863         computeConsoliadtionDataList, computeTemplateConsolidationData, unifiedCompositionDataList,
1864         context);
1865
1866     String newComputeNodeTemplateId = getNewComputeNodeTemplateId(serviceTemplate,
1867         computeTemplateConsolidationData.getNodeTemplateId());
1868     //Update requirements for relationships between the consolidation entities
1869     handleConsolidationEntitiesRequirementConnectivity(
1870         newComputeNodeTemplate,
1871         serviceTemplate, context);
1872     DataModelUtil
1873         .addNodeTemplate(substitutionServiceTemplate,
1874             newComputeNodeTemplateId, newComputeNodeTemplate);
1875     //Add the node template mapping in the context for handling requirement updation
1876     for (EntityConsolidationData data : computeConsoliadtionDataList) {
1877       String newComputeTemplateId = getNewComputeNodeTemplateId(serviceTemplate,
1878           computeTemplateConsolidationData.getNodeTemplateId());
1879       context.addSubstitutionServiceTemplateUnifiedSubstitutionData(ToscaUtil
1880               .getServiceTemplateFileName(serviceTemplate), data.getNodeTemplateId(),
1881           newComputeTemplateId);
1882     }
1883   }
1884
1885   private void updateComputeNodeType(ServiceTemplate serviceTemplate,
1886                                      String nodeTemplateId,
1887                                      NodeTemplate newComputeNodeTemplate) {
1888     String computeNodeType = getComputeNodeType(newComputeNodeTemplate.getType());
1889     NodeType origNodeType = serviceTemplate.getNode_types().get(newComputeNodeTemplate.getType());
1890     DataModelUtil.removeNodeType(serviceTemplate, newComputeNodeTemplate.getType());
1891     DataModelUtil.addNodeType(serviceTemplate, computeNodeType, origNodeType);
1892     newComputeNodeTemplate.setType(computeNodeType);
1893     DataModelUtil.addNodeTemplate(serviceTemplate, nodeTemplateId, newComputeNodeTemplate);
1894   }
1895
1896   private List<EntityConsolidationData> getComputeConsolidationDataList(
1897       List<UnifiedCompositionData> unifiedCompositionDataList) {
1898     List<EntityConsolidationData> computeConsolidationDataList = new ArrayList<>();
1899     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
1900       computeConsolidationDataList
1901           .add(unifiedCompositionData.getComputeTemplateConsolidationData());
1902     }
1903     return computeConsolidationDataList;
1904   }
1905
1906
1907   private void handleProperties(ServiceTemplate serviceTemplate,
1908                                 NodeTemplate nodeTemplate,
1909                                 ServiceTemplate substitutionServiceTemplate,
1910                                 UnifiedCompositionEntity unifiedCompositionEntity,
1911                                 List<EntityConsolidationData> entityConsolidationDataList,
1912                                 ComputeTemplateConsolidationData computeTemplateConsolidationData,
1913                                 List<UnifiedCompositionData> unifiedCompositionDataList,
1914                                 TranslationContext context) {
1915     List<String> propertiesWithIdenticalVal =
1916         consolidationService.getPropertiesWithIdenticalVal(unifiedCompositionEntity);
1917     nodeTemplate.setProperties(new HashedMap());
1918     handleNodeTemplateProperties(serviceTemplate, nodeTemplate, substitutionServiceTemplate,
1919         unifiedCompositionEntity, entityConsolidationDataList, computeTemplateConsolidationData,
1920         unifiedCompositionDataList, context);
1921     //Add enrich properties from openecomp node type as input to global and substitution ST
1922     handleNodeTypeProperties(substitutionServiceTemplate,
1923         entityConsolidationDataList, nodeTemplate, unifiedCompositionEntity,
1924         computeTemplateConsolidationData, context);
1925
1926   }
1927
1928   private void handleNodeTemplateProperties(ServiceTemplate serviceTemplate,
1929                                             NodeTemplate nodeTemplate,
1930                                             ServiceTemplate substitutionServiceTemplate,
1931                                             UnifiedCompositionEntity unifiedCompositionEntity,
1932                                             List<EntityConsolidationData>
1933                                                 entityConsolidationDataList,
1934                                             ComputeTemplateConsolidationData
1935                                                 computeTemplateConsolidationData,
1936                                             List<UnifiedCompositionData> unifiedCompositionDataList,
1937                                             TranslationContext context) {
1938     List<String> propertiesWithIdenticalVal =
1939         consolidationService.getPropertiesWithIdenticalVal(unifiedCompositionEntity);
1940
1941     for (EntityConsolidationData entityConsolidationData : entityConsolidationDataList) {
1942       String nodeTemplateId = entityConsolidationData.getNodeTemplateId();
1943       Map<String, Object> properties =
1944           DataModelUtil.getNodeTemplateProperties(serviceTemplate, nodeTemplateId);
1945       if (MapUtils.isEmpty(properties)) {
1946         continue;
1947       }
1948
1949       for (Map.Entry<String, Object> propertyEntry : properties.entrySet()) {
1950         NodeType nodeTypeWithFlatHierarchy =
1951             HeatToToscaUtil.getNodeTypeWithFlatHierarchy(nodeTemplate.getType(), serviceTemplate,
1952                 context);
1953         PropertyDefinition propertyDefinition =
1954             nodeTypeWithFlatHierarchy.getProperties().get(propertyEntry.getKey());
1955         String propertyType = propertyDefinition.getType();
1956
1957         if (propertiesWithIdenticalVal.contains(propertyEntry.getKey())) {
1958           String parameterId =
1959               updateIdenticalProperty(nodeTemplateId, propertyEntry.getKey(), nodeTemplate,
1960                   unifiedCompositionEntity, unifiedCompositionDataList);
1961
1962           addInputParameter(
1963               parameterId, propertyType,
1964               propertyType.equals(PropertyType.LIST.getDisplayName()) ? propertyDefinition
1965                   .getEntry_schema() : null,
1966               substitutionServiceTemplate);
1967         } else {
1968           Optional<String> parameterId =
1969               updateProperty(serviceTemplate, nodeTemplateId, nodeTemplate, propertyEntry,
1970                   unifiedCompositionEntity, computeTemplateConsolidationData,
1971                   unifiedCompositionDataList,
1972                   context);
1973           //todo - define list of type which will match the node property type (instead of string)
1974           parameterId.ifPresent(
1975               parameterIdValue -> addPropertyInputParameter(propertyType,
1976                   substitutionServiceTemplate,
1977                   propertyDefinition.getEntry_schema(), parameterIdValue, context));
1978         }
1979       }
1980     }
1981   }
1982
1983   private void handleNodeTypeProperties(ServiceTemplate substitutionServiceTemplate,
1984                                         List<EntityConsolidationData> entityConsolidationDataList,
1985                                         NodeTemplate nodeTemplate,
1986                                         UnifiedCompositionEntity compositionEntity,
1987                                         ComputeTemplateConsolidationData
1988                                             computeTemplateConsolidationData,
1989                                         TranslationContext context) {
1990     ToscaAnalyzerService toscaAnalyzerService = new ToscaAnalyzerServiceImpl();
1991     Optional<NodeType> enrichNodeType;
1992     List<String> enrichProperties;
1993
1994     if (compositionEntity.equals(UnifiedCompositionEntity.Port)) {
1995       enrichNodeType =
1996           toscaAnalyzerService.fetchNodeType(ToscaNodeType.NETWORK_PORT,
1997               context.getGlobalServiceTemplates().values());
1998       enrichProperties = context.getEnrichPortResourceProperties();
1999       if (!enrichNodeType.isPresent() || Objects.isNull(enrichProperties)) {
2000         return;
2001       }
2002     } else {
2003       return;
2004     }
2005
2006     Map<String, Object> nodeTemplateProperties = nodeTemplate.getProperties();
2007     Map<String, PropertyDefinition> enrichNodeTypeProperties = enrichNodeType.get().getProperties();
2008     if (Objects.nonNull(enrichNodeTypeProperties)) {
2009       for (String enrichPropertyName : enrichProperties) {
2010         handleEntityConsolidationDataNodeTypeProperties(
2011             enrichPropertyName, substitutionServiceTemplate,
2012             enrichNodeType.get(), nodeTemplate, compositionEntity, computeTemplateConsolidationData,
2013             entityConsolidationDataList, nodeTemplateProperties, context);
2014       }
2015     }
2016   }
2017
2018   private void handleEntityConsolidationDataNodeTypeProperties(String enrichPropertyName,
2019                                                                ServiceTemplate substitutionServiceTemplate,
2020                                                                NodeType enrichNodeType,
2021                                                                NodeTemplate nodeTemplate,
2022                                                                UnifiedCompositionEntity compositionEntity,
2023                                                                ComputeTemplateConsolidationData computeTemplateConsolidationData,
2024                                                                List<EntityConsolidationData> entityConsolidationDataList,
2025                                                                Map<String, Object> nodeTemplateProperties,
2026                                                                TranslationContext context) {
2027
2028     String propertyType;
2029
2030     for (EntityConsolidationData entityConsolidationData : entityConsolidationDataList) {
2031       String nodeTemplateId = entityConsolidationData.getNodeTemplateId();
2032
2033       String inputParamId =
2034           getParameterId(nodeTemplateId, nodeTemplate, enrichPropertyName,
2035               compositionEntity, computeTemplateConsolidationData);
2036       Map<String, String> propertyValMap = new HashMap<>();
2037
2038       context
2039           .addNewPropertyIdToNodeTemplate(
2040               ToscaUtil.getServiceTemplateFileName(substitutionServiceTemplate),
2041               inputParamId, nodeTemplateProperties.get(enrichPropertyName));
2042
2043       if (nodeTemplateProperties.containsKey(enrichPropertyName)) {
2044         handleExistingEnrichedProperty(enrichPropertyName, nodeTemplateProperties, inputParamId);
2045       } else {
2046         propertyValMap.put(ToscaFunctions.GET_INPUT.getDisplayName(), inputParamId);
2047         nodeTemplate.getProperties().put(enrichPropertyName, propertyValMap);
2048       }
2049       propertyType =
2050           enrichNodeType.getProperties().get(enrichPropertyName).getType();
2051
2052       addPropertyInputParameter(propertyType, substitutionServiceTemplate, enrichNodeType
2053               .getProperties().get(enrichPropertyName).getEntry_schema(),
2054           inputParamId, context);
2055
2056     }
2057   }
2058
2059   private void handleExistingEnrichedProperty(String enrichPropertyName,
2060                                               Map<String, Object> nodeTemplateProperties,
2061                                               String inputParamId) {
2062     Object enrichedProperty = nodeTemplateProperties.get(enrichPropertyName);
2063     if (!isPropertyContainsToscaFunction(enrichedProperty)) {
2064       Map<String, Object> propertyWithGetInput = new HashMap<>();
2065       propertyWithGetInput.put(ToscaFunctions.GET_INPUT.getDisplayName(), inputParamId);
2066       nodeTemplateProperties.put(enrichPropertyName, propertyWithGetInput);
2067     }
2068   }
2069
2070
2071   private boolean isPropertyContainsToscaFunction(Object propertyValue) {
2072     ToscaFunctions[] values = ToscaFunctions.values();
2073     for (ToscaFunctions toscaFunction : values) {
2074       if (isIncludeToscaFunc(propertyValue, toscaFunction)) {
2075         return true;
2076       }
2077     }
2078
2079     return false;
2080   }
2081
2082
2083   private void addPropertyInputParameter(String propertyType,
2084                                          ServiceTemplate substitutionServiceTemplate,
2085                                          EntrySchema entrySchema, String parameterId,
2086                                          TranslationContext context) {
2087     if (isParameterBelongsToEnrichedPortProperties(parameterId, context)) {
2088       addInputParameter(parameterId,
2089           propertyType,
2090           propertyType.equals(PropertyType.LIST.getDisplayName()) ? entrySchema : null,
2091           substitutionServiceTemplate);
2092     } else if (isPropertySimpleType(propertyType)) {
2093       addInputParameter(parameterId, PropertyType.LIST.getDisplayName(),
2094           DataModelUtil.createEntrySchema(propertyType.toLowerCase(), null, null),
2095           substitutionServiceTemplate);
2096
2097     } else if (propertyType.equals(PropertyTypeExt.JSON.getDisplayName()) ||
2098         (Objects.nonNull(entrySchema) && isPropertySimpleType(entrySchema.getType()))) {
2099       addInputParameter(parameterId, PropertyType.LIST.getDisplayName(),
2100           DataModelUtil.createEntrySchema(PropertyTypeExt.JSON.getDisplayName(), null, null),
2101           substitutionServiceTemplate);
2102     } else {
2103       addInputParameter(parameterId, analyzeParameterType(propertyType), DataModelUtil
2104               .createEntrySchema(analyzeEntrySchemaType(propertyType, entrySchema), null, null),
2105           substitutionServiceTemplate);
2106     }
2107   }
2108
2109   private boolean isParameterBelongsToEnrichedPortProperties(String parameterId,
2110                                                              TranslationContext context) {
2111     List enrichPortResourceProperties = context.getEnrichPortResourceProperties();
2112
2113     for (int i = 0; i < enrichPortResourceProperties.size(); i++) {
2114       if (parameterId.contains((CharSequence) enrichPortResourceProperties.get(i))) {
2115         return true;
2116       }
2117     }
2118
2119     return false;
2120   }
2121
2122   private boolean isPropertySimpleType(String propertyType) {
2123     return !Objects.isNull(propertyType) &&
2124         (propertyType.equalsIgnoreCase(PropertyType.STRING.getDisplayName())
2125             || propertyType.equalsIgnoreCase(PropertyType.INTEGER.getDisplayName())
2126             || propertyType.equalsIgnoreCase(PropertyType.FLOAT.getDisplayName())
2127             || propertyType.equalsIgnoreCase(PropertyType.BOOLEAN.getDisplayName()));
2128   }
2129
2130   private String analyzeParameterType(String propertyType) {
2131     return propertyType.equalsIgnoreCase(PropertyType.LIST.getDisplayName()) ? PropertyType.LIST
2132         .getDisplayName() : propertyType;
2133   }
2134
2135   private String analyzeEntrySchemaType(String propertyType, EntrySchema entrySchema) {
2136     return propertyType.equalsIgnoreCase(PropertyType.LIST.getDisplayName()) ?
2137         entrySchema.getType() : null;
2138   }
2139
2140   private void handleConsolidationEntitiesRequirementConnectivity(NodeTemplate nodeTemplate,
2141                                                                   ServiceTemplate serviceTemplate,
2142                                                                   TranslationContext context) {
2143     List<Map<String, RequirementAssignment>> nodeTemplateRequirements = DataModelUtil
2144         .getNodeTemplateRequirementList(nodeTemplate);
2145     if (CollectionUtils.isEmpty(nodeTemplateRequirements)) {
2146       return;
2147     }
2148
2149     for (Map<String, RequirementAssignment> requirement : nodeTemplateRequirements) {
2150       for (Map.Entry<String, RequirementAssignment> entry : requirement.entrySet()) {
2151         RequirementAssignment requirementAssignment = entry.getValue();
2152         String requirementNode = requirementAssignment.getNode();
2153         String unifiedNodeTemplateId =
2154             context.getUnifiedSubstitutionNodeTemplateId(serviceTemplate,
2155                 requirementNode);
2156         if (unifiedNodeTemplateId != null) {
2157           //Update the node id in the requirement
2158           requirementAssignment.setNode(unifiedNodeTemplateId);
2159         }
2160       }
2161     }
2162     nodeTemplate.setRequirements(nodeTemplateRequirements);
2163   }
2164
2165   /**
2166    * Update the node references in the volume relationship templates.
2167    *
2168    * @param serviceTemplate the service template
2169    * @param context         the context
2170    */
2171   private void updateVolumeRelationshipTemplate(ServiceTemplate serviceTemplate,
2172                                                 String relationshipId,
2173                                                 TranslationContext context) {
2174     Map<String, RelationshipTemplate> relationshipTemplates = DataModelUtil
2175         .getRelationshipTemplates(serviceTemplate);
2176     if (relationshipTemplates != null) {
2177       RelationshipTemplate relationshipTemplate = relationshipTemplates.get(relationshipId);
2178       if (relationshipTemplate != null) {
2179         String relationshipTemplateType = relationshipTemplate.getType();
2180         if (relationshipTemplateType.equals(ToscaRelationshipType.CINDER_VOLUME_ATTACHES_TO)) {
2181           handleCinderVolumeAttachmentRelationshipTemplate(serviceTemplate,
2182               relationshipTemplate, context);
2183         }
2184       }
2185     }
2186   }
2187
2188
2189   private void handleCinderVolumeAttachmentRelationshipTemplate(ServiceTemplate
2190                                                                     substitutionServiceTemplate,
2191                                                                 RelationshipTemplate
2192                                                                     relationshipTemplate,
2193                                                                 TranslationContext context) {
2194     Map<String, Object> properties = relationshipTemplate.getProperties();
2195     properties.computeIfPresent(HeatConstants.INSTANCE_UUID_PROPERTY_NAME, (key, value) ->
2196         context.getUnifiedAbstractNodeTemplateId(substitutionServiceTemplate,
2197             (String) value));
2198   }
2199
2200   private String updateIdenticalProperty(String nodeTemplateId, String propertyId,
2201                                          NodeTemplate nodeTemplate,
2202                                          UnifiedCompositionEntity unifiedCompositionEntity,
2203                                          List<UnifiedCompositionData> unifiedCompositionDataList) {
2204
2205     String inputParamId;
2206     Map<String, Object> propertyVal = new HashMap<>();
2207
2208     switch (unifiedCompositionEntity) {
2209       case Compute:
2210         inputParamId = COMPUTE_IDENTICAL_VALUE_PROPERTY_PREFIX + propertyId
2211             + COMPUTE_IDENTICAL_VALUE_PROPERTY_SUFFIX;
2212
2213         propertyVal.put(ToscaFunctions.GET_INPUT.getDisplayName(), inputParamId);
2214         nodeTemplate.getProperties().put(propertyId, propertyVal);
2215
2216         return inputParamId;
2217
2218       case Port:
2219         String portType = ConsolidationDataUtil.getPortType(nodeTemplateId);
2220         ComputeTemplateConsolidationData computeTemplateConsolidationData =
2221             getConnectedComputeConsolidationData(unifiedCompositionDataList, nodeTemplateId);
2222         inputParamId = getInputParamIdForPort(nodeTemplateId, propertyId, portType,
2223             computeTemplateConsolidationData);
2224
2225         propertyVal.put(ToscaFunctions.GET_INPUT.getDisplayName(), inputParamId);
2226         nodeTemplate.getProperties().put(propertyId, propertyVal);
2227
2228         return inputParamId;
2229
2230       default:
2231         return null;
2232     }
2233   }
2234
2235   private String getInputParamIdForPort(String nodeTemplateId, String propertyId, String portType,
2236                                         ComputeTemplateConsolidationData computeTemplateConsolidationData) {
2237     String inputParamId;
2238     if (Objects.isNull(computeTemplateConsolidationData)
2239         || computeTemplateConsolidationData.getPorts().get(portType).size() > 1) {
2240       inputParamId =
2241           UnifiedCompositionEntity.Port.name().toLowerCase() + "_" + nodeTemplateId + "_" +
2242               propertyId;
2243
2244     } else {
2245       inputParamId =
2246           UnifiedCompositionEntity.Port.name().toLowerCase() + "_" + portType + "_"
2247               + propertyId;
2248     }
2249     return inputParamId;
2250   }
2251
2252   private void addInputParameter(String parameterId,
2253                                  String parameterType,
2254                                  EntrySchema entrySchema,
2255                                  ServiceTemplate serviceTemplate) {
2256
2257     ParameterDefinition parameterDefinition = DataModelUtil.createParameterDefinition
2258         (parameterType, null, null,
2259             true, null, null,
2260             entrySchema, null);
2261
2262
2263     DataModelUtil
2264         .addInputParameterToTopologyTemplate(serviceTemplate, parameterId, parameterDefinition);
2265   }
2266
2267   // Return the input parameter Id which is used in the new property value if there is one
2268   private Optional<String> updateProperty(
2269       ServiceTemplate serviceTemplate,
2270       String nodeTemplateId, NodeTemplate nodeTemplate,
2271       Map.Entry<String, Object> propertyEntry,
2272       UnifiedCompositionEntity compositionEntity,
2273       ComputeTemplateConsolidationData computeTemplateConsolidationData,
2274       List<UnifiedCompositionData> unifiedCompositionDataList,
2275       TranslationContext context) {
2276
2277     if (handleGetAttrFromConsolidationNodes(serviceTemplate, nodeTemplateId, nodeTemplate,
2278         propertyEntry, unifiedCompositionDataList, context)) {
2279       return Optional.empty();
2280     }
2281
2282
2283     String inputParamId =
2284         getParameterId(nodeTemplateId, nodeTemplate, propertyEntry.getKey(), compositionEntity,
2285             computeTemplateConsolidationData);
2286     Map<String, List<String>> propertyVal = getPropertyValueInputParam(nodeTemplateId,
2287         nodeTemplate, inputParamId);
2288     nodeTemplate.getProperties().put(propertyEntry.getKey(), propertyVal);
2289     return Optional.of(inputParamId);
2290   }
2291
2292   private Map<String, List<String>> getPropertyValueInputParam(String nodeTemplateId,
2293                                                                NodeTemplate nodeTemplate,
2294                                                                String inputParamId) {
2295     Map<String, List<String>> propertyVal = new HashMap<>();
2296     List<String> getInputFuncParams = new ArrayList<>();
2297     getInputFuncParams.add(inputParamId);
2298     getInputFuncParams.add(ToscaConstants.INDEX_VALUE_PROPERTY_NAME);
2299     propertyVal.put(ToscaFunctions.GET_INPUT.getDisplayName(), getInputFuncParams);
2300     return propertyVal;
2301   }
2302
2303   private boolean handleGetAttrFromConsolidationNodes(
2304       ServiceTemplate serviceTemplate,
2305       String nodeTemplateId, NodeTemplate nodeTemplate,
2306       Map.Entry<String, Object> propertyEntry,
2307       List<UnifiedCompositionData> unifiedCompositionDataList,
2308       TranslationContext context) {
2309     Map<String, UnifiedCompositionEntity> consolidationNodeTemplateIdAndType =
2310         getAllConsolidationNodeTemplateIdAndType(unifiedCompositionDataList);
2311
2312     Set<String> consolidationNodeTemplateIds = consolidationNodeTemplateIdAndType.keySet();
2313     Map<String, String> entityIdToType = ConsolidationService.getConsolidationEntityIdToType(
2314         serviceTemplate, context.getConsolidationData());
2315     boolean includeGetAttrFromConsolidationNodes = false;
2316     boolean includeGetAttrFromOutsideNodes = false;
2317     boolean isGetAttrFromConsolidationIsFromSameType = false;
2318     List<List<Object>> getAttrFunctionList = extractGetAttrFunction(propertyEntry.getValue());
2319     for (List<Object> getAttrFunc : getAttrFunctionList) {
2320       String getAttrNodeId = (String) getAttrFunc.get(0);
2321       if (consolidationNodeTemplateIds.contains(getAttrNodeId)) {
2322         includeGetAttrFromConsolidationNodes = true;
2323         if (isGetAttrNodeTemplateFromSameType(nodeTemplateId, getAttrNodeId, entityIdToType)) {
2324           isGetAttrFromConsolidationIsFromSameType = true;
2325         }
2326       } else {
2327         includeGetAttrFromOutsideNodes = true;
2328       }
2329     }
2330     if ((includeGetAttrFromConsolidationNodes && includeGetAttrFromOutsideNodes)
2331         ||
2332         (includeGetAttrFromConsolidationNodes && isIncludeToscaFunc(propertyEntry.getValue(),
2333             ToscaFunctions.GET_INPUT))) {
2334       //This case is currently not supported - this property will be ignored
2335       return true;
2336     } else if (includeGetAttrFromConsolidationNodes && !isGetAttrFromConsolidationIsFromSameType) {
2337       Object clonedPropertyValue = getClonedPropertyValue(propertyEntry);
2338       List<List<Object>> clonedGetAttrFuncList = extractGetAttrFunction(clonedPropertyValue);
2339       for (List<Object> getAttrFunc : clonedGetAttrFuncList) {
2340         String targetNodeTemplateId = (String) getAttrFunc.get(0);
2341         if (consolidationNodeTemplateIds.contains(targetNodeTemplateId)) {
2342           updatePropertyGetAttrFunc(serviceTemplate, unifiedCompositionDataList, context,
2343               consolidationNodeTemplateIdAndType, targetNodeTemplateId, getAttrFunc);
2344         }
2345       }
2346       nodeTemplate.getProperties().put(propertyEntry.getKey(), clonedPropertyValue);
2347       return true;
2348     }
2349     return false;
2350   }
2351
2352   private boolean isGetAttrFromConsolidationNodesIsFromSameType(String sourceNodeTemplateId,
2353                                                                 Set<String> nodeTemplateIdsFromConsolidation,
2354                                                                 Map<String, String>
2355                                                                     nodeTemplateIdToType) {
2356     for (String idFromConsolidation : nodeTemplateIdsFromConsolidation) {
2357       if (isGetAttrNodeTemplateFromSameType(sourceNodeTemplateId, idFromConsolidation,
2358           nodeTemplateIdToType)) {
2359         return true;
2360       }
2361     }
2362     return false;
2363   }
2364
2365   private boolean isGetAttrNodeTemplateFromSameType(String sourceNodeTemplateId,
2366                                                     String targetNodeTemplateId,
2367                                                     Map<String, String> nodeTemplateIdToType) {
2368
2369     if (Objects.isNull(nodeTemplateIdToType.get(sourceNodeTemplateId))
2370         || Objects.isNull(nodeTemplateIdToType.get(targetNodeTemplateId))) {
2371       return false;
2372     }
2373
2374     return nodeTemplateIdToType.get(sourceNodeTemplateId).equals(nodeTemplateIdToType
2375         .get(targetNodeTemplateId));
2376   }
2377
2378   private void updatePropertyGetAttrFunc(
2379       ServiceTemplate serviceTemplate,
2380       List<UnifiedCompositionData> unifiedCompositionDataList,
2381       TranslationContext context,
2382       Map<String, UnifiedCompositionEntity> consolidationNodeTemplateIdAndType,
2383       String targetNodeTemplateId,
2384       List<Object> getAttrFunc) {
2385     UnifiedCompositionEntity targetCompositionEntity =
2386         consolidationNodeTemplateIdAndType.get(targetNodeTemplateId);
2387     String targetNewNodeTemplateId =
2388         getNewNodeTemplateId(serviceTemplate, unifiedCompositionDataList, targetNodeTemplateId,
2389             targetCompositionEntity);
2390     getAttrFunc.set(0, targetNewNodeTemplateId);
2391   }
2392
2393   private String getNewNodeTemplateId(ServiceTemplate serviceTemplate,
2394                                       List<UnifiedCompositionData> unifiedCompositionDataList,
2395                                       String nodeTemplateId,
2396                                       UnifiedCompositionEntity compositionEntity) {
2397     switch (compositionEntity) {
2398       case Compute:
2399         return getNewComputeNodeTemplateId(serviceTemplate, nodeTemplateId);
2400       case Port:
2401         ComputeTemplateConsolidationData connectedComputeConsolidationData =
2402             getConnectedComputeConsolidationData(
2403                 unifiedCompositionDataList, nodeTemplateId);
2404         NodeTemplate connectedComputeNodeTemplate =
2405             DataModelUtil.getNodeTemplate(serviceTemplate,
2406                 connectedComputeConsolidationData.getNodeTemplateId());
2407         return getNewPortNodeTemplateId(nodeTemplateId, connectedComputeNodeTemplate.getType(),
2408             connectedComputeConsolidationData);
2409       default:
2410         return null;
2411     }
2412   }
2413
2414   private String getNewNodeTemplateId(String origNodeTemplateId,
2415                                       String serviceTemplateFileName,
2416                                       ServiceTemplate serviceTemplate,
2417                                       TranslationContext context) {
2418     ConsolidationData consolidationData = context.getConsolidationData();
2419
2420     if (isIdIsOfExpectedType(origNodeTemplateId, UnifiedCompositionEntity.Port,
2421         serviceTemplateFileName,
2422         context)) {
2423       return handleIdOfPort(origNodeTemplateId, serviceTemplateFileName, consolidationData);
2424     } else if (isIdIsOfExpectedType(origNodeTemplateId, UnifiedCompositionEntity.Compute,
2425         serviceTemplateFileName, context)) {
2426       NodeTemplate nodeTemplate =
2427           getComputeNodeTemplate(origNodeTemplateId, serviceTemplate, context);
2428       return getComputeTypeSuffix(nodeTemplate.getType());
2429     }
2430
2431     return null;
2432   }
2433
2434   private ComputeTemplateConsolidationData getConnectedComputeConsolidationData(
2435       List<UnifiedCompositionData> unifiedCompositionDataList,
2436       String portNodeTemplateId) {
2437     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
2438       Collection<List<String>> portsCollection =
2439           unifiedCompositionData.getComputeTemplateConsolidationData().getPorts().values();
2440       for (List<String> portIdList : portsCollection) {
2441         if (portIdList.contains(portNodeTemplateId)) {
2442           return unifiedCompositionData.getComputeTemplateConsolidationData();
2443         }
2444       }
2445     }
2446     return null;
2447   }
2448
2449   private Object getClonedPropertyValue(Map.Entry<String, Object> propertyEntry) {
2450     if (propertyEntry.getValue() instanceof Map) {
2451       return getClonedObject(propertyEntry.getValue(), Map.class);
2452     } else if (propertyEntry.getValue() instanceof List) {
2453       return getClonedObject(propertyEntry.getValue(), List.class);
2454     }
2455     return propertyEntry.getValue();
2456   }
2457
2458
2459   private String getParameterId(String nodeTemplateId, NodeTemplate nodeTemplate, String propertyId,
2460                                 UnifiedCompositionEntity unifiedCompositionEntity,
2461                                 ComputeTemplateConsolidationData computeTemplateConsolidationData) {
2462     switch (unifiedCompositionEntity) {
2463       case Compute:
2464         return UnifiedCompositionEntity.Compute.name().toLowerCase() + "_"
2465             + getComputeTypeSuffix(nodeTemplate.getType()) + "_" + propertyId;
2466       case Port:
2467         String portType = ConsolidationDataUtil.getPortType(nodeTemplateId);
2468         if (Objects.isNull(computeTemplateConsolidationData)
2469             || computeTemplateConsolidationData.getPorts().get(portType).size() > 1) {
2470           return UnifiedCompositionEntity.Port.name().toLowerCase() + "_" + nodeTemplateId + "_"
2471               + propertyId;
2472         }
2473         return UnifiedCompositionEntity.Port.name().toLowerCase() + "_" + portType + "_"
2474             + propertyId;
2475       default:
2476         return propertyId;
2477     }
2478   }
2479
2480   private void removeConnectivityOut(EntityConsolidationData entityConsolidationData,
2481                                      NodeTemplate nodeTemplate) {
2482     if (MapUtils.isEmpty(entityConsolidationData.getNodesConnectedOut())) {
2483       return;
2484     }
2485
2486     for (List<RequirementAssignmentData> requirementAssignmentDataList : entityConsolidationData
2487         .getNodesConnectedOut().values()) {
2488       for (RequirementAssignmentData requirementAssignmentData : requirementAssignmentDataList) {
2489         DataModelUtil.removeRequirementsAssignment(nodeTemplate.getRequirements(),
2490             requirementAssignmentData.getRequirementId());
2491       }
2492       if (nodeTemplate.getRequirements().isEmpty()) {
2493         nodeTemplate.setRequirements(null);
2494       }
2495     }
2496   }
2497
2498   private void removeVolumeConnectivity(
2499       ComputeTemplateConsolidationData computeTemplateConsolidationData,
2500       NodeTemplate computeNodeTemplate) {
2501     if (MapUtils.isEmpty(computeTemplateConsolidationData.getVolumes())) {
2502       return;
2503     }
2504     Collection<List<RequirementAssignmentData>> volumeCollection =
2505         computeTemplateConsolidationData.getVolumes().values();
2506     for (List<RequirementAssignmentData> requirementAssignmentDataList : volumeCollection) {
2507       for (RequirementAssignmentData requirementAssignmentData : requirementAssignmentDataList) {
2508         DataModelUtil.removeRequirementsAssignment(computeNodeTemplate.getRequirements(),
2509             requirementAssignmentData.getRequirementId());
2510       }
2511     }
2512     if (computeNodeTemplate.getRequirements().isEmpty()) {
2513       computeNodeTemplate.setRequirements(null);
2514     }
2515   }
2516
2517   private void createIndexInputParameter(ServiceTemplate substitutionServiceTemplate) {
2518     ParameterDefinition indexParameterDefinition =
2519         DataModelUtil.createParameterDefinition(PropertyType.INTEGER.getDisplayName(),
2520             "Index value of this substitution service template runtime instance", null,
2521             false, createIndexValueConstraint(), null, null, 0);
2522     DataModelUtil.addInputParameterToTopologyTemplate(substitutionServiceTemplate,
2523         ToscaConstants.INDEX_VALUE_PROPERTY_NAME, indexParameterDefinition);
2524   }
2525
2526
2527   private List<Constraint> createIndexValueConstraint() {
2528     List<Constraint> constraints;
2529     constraints = new ArrayList<>();
2530     Constraint constraint = new Constraint();
2531     constraint.setGreater_or_equal(0);
2532     constraints.add(constraint);
2533     return constraints;
2534   }
2535
2536   private Optional<UnifiedComposition> getUnifiedCompositionInstance(UnifiedCompositionMode mode) {
2537     String unifiedCompositionImplClassName =
2538         unifiedCompositionImplMap.get(mode.name()).getImplementationClass();
2539     if (StringUtils.isEmpty(unifiedCompositionImplClassName)) {
2540       return Optional.empty();
2541     }
2542     return Optional
2543         .of(CommonMethods.newInstance(unifiedCompositionImplClassName, UnifiedComposition.class));
2544   }
2545
2546   private Optional<Map<String, Object>> createAbstractSubstitutionProperties(
2547       ServiceTemplate serviceTemplate,
2548       ServiceTemplate substitutionServiceTemplate,
2549       List<UnifiedCompositionData> unifiedCompositionDataList,
2550       TranslationContext context) {
2551     Map<String, Object> abstractSubstituteProperties = new LinkedHashMap<>();
2552     Map<String, ParameterDefinition> substitutionTemplateInputs = DataModelUtil
2553         .getInputParameters(substitutionServiceTemplate);
2554     if (substitutionTemplateInputs == null) {
2555       return Optional.empty();
2556     }
2557     //Since all the computes have the same type fetching the type from the first entry
2558     NodeTemplate firstComputeNodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate,
2559         unifiedCompositionDataList.get(0)
2560             .getComputeTemplateConsolidationData().getNodeTemplateId());
2561     String computeType = getComputeTypeSuffix(firstComputeNodeTemplate.getType());
2562     for (Map.Entry<String, ParameterDefinition> input : substitutionTemplateInputs.entrySet()) {
2563       String substitutionTemplateInputName = input.getKey();
2564       ParameterDefinition inputParameterDefinition = input.getValue();
2565       String inputType = inputParameterDefinition.getType();
2566       UnifiedCompositionEntity inputUnifiedCompositionEntity =
2567           getInputCompositionEntity(substitutionTemplateInputName);
2568
2569       if (!inputType.equalsIgnoreCase(PropertyType.LIST.getDisplayName())) {
2570         if (isIdenticalValueProperty(
2571             substitutionTemplateInputName, inputUnifiedCompositionEntity, context)) {
2572           //Handle identical value properties
2573           Optional<String> identicalValuePropertyName =
2574               getIdenticalValuePropertyName(substitutionTemplateInputName,
2575                   inputUnifiedCompositionEntity, context);
2576
2577           identicalValuePropertyName.ifPresent(propertyName -> updateIdenticalPropertyValue(propertyName,
2578               substitutionTemplateInputName, computeType, inputUnifiedCompositionEntity,
2579               unifiedCompositionDataList.get(0), serviceTemplate, abstractSubstituteProperties,
2580               context));
2581         }
2582         continue;
2583       }
2584
2585       //Check if the input is of type compute or port
2586       List<Object> abstractPropertyValue = new ArrayList<>();
2587       Object propertyValue = null;
2588       switch (inputUnifiedCompositionEntity) {
2589         case Compute:
2590           for (UnifiedCompositionData compositionData : unifiedCompositionDataList) {
2591             ComputeTemplateConsolidationData computeTemplateConsolidationData =
2592                 compositionData.getComputeTemplateConsolidationData();
2593             propertyValue = getComputePropertyValue(substitutionTemplateInputName,
2594                 serviceTemplate, computeTemplateConsolidationData);
2595             if (!(propertyValue instanceof Optional)) {
2596               abstractPropertyValue.add(propertyValue);
2597             }
2598           }
2599           break;
2600         case Port:
2601           for (UnifiedCompositionData compositionData : unifiedCompositionDataList) {
2602             List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
2603                 getPortTemplateConsolidationDataList(compositionData);
2604             //Get the input type for this input whether it is of type
2605             // port_<port_node_template_id>_<property_name> or port_<port_type>_<property_name>
2606             PortInputType portInputType = getPortInputType(substitutionTemplateInputName,
2607                 compositionData);
2608             for (PortTemplateConsolidationData portTemplateConsolidationData :
2609                 portTemplateConsolidationDataList) {
2610               //Get the port property value
2611               String portNodeTemplateId = portTemplateConsolidationData.getNodeTemplateId();
2612               propertyValue = getPortPropertyValue(substitutionTemplateInputName,
2613                   computeType, portInputType, serviceTemplate,
2614                   portNodeTemplateId);
2615               //If the value object is Optional.empty it implies that the property name was not
2616               // found in the input name
2617               if (!(propertyValue instanceof Optional)) {
2618                 if (!abstractPropertyValue.contains(propertyValue)) {
2619                   abstractPropertyValue.add(propertyValue);
2620                 }
2621               }
2622             }
2623           }
2624           break;
2625         default:
2626           break;
2627       }
2628       //Add the property only if it has at least one non-null value
2629       for (Object val : abstractPropertyValue) {
2630         if (Objects.nonNull(val)) {
2631           updateAbstractPropertyValue(substitutionTemplateInputName, inputParameterDefinition,
2632               abstractPropertyValue, abstractSubstituteProperties);
2633           break;
2634         }
2635       }
2636     }
2637     return Optional.ofNullable(abstractSubstituteProperties);
2638   }
2639
2640   private void updateAbstractPropertyValue(String substitutionTemplateInputName,
2641                                            ParameterDefinition parameterDefinition,
2642                                            List<Object> abstractPropertyValue,
2643                                            Map<String, Object> abstractSubstituteProperties) {
2644     if (abstractPropertyValue.size() > 1) {
2645       abstractSubstituteProperties.put(substitutionTemplateInputName, abstractPropertyValue);
2646     } else {
2647       Object propertyValue = abstractPropertyValue.get(0);
2648       String entrySchemaType = parameterDefinition.getEntry_schema().getType();
2649       if (entrySchemaType.equalsIgnoreCase(PropertyType.STRING.getDisplayName())
2650           || entrySchemaType.equalsIgnoreCase(PropertyType.INTEGER.getDisplayName())
2651           || entrySchemaType.equalsIgnoreCase(PropertyType.FLOAT.getDisplayName())
2652           || entrySchemaType.equalsIgnoreCase(PropertyType.BOOLEAN.getDisplayName())
2653           || entrySchemaType.equals(PropertyTypeExt.JSON.getDisplayName())) {
2654         abstractSubstituteProperties.put(substitutionTemplateInputName, abstractPropertyValue);
2655       } else {
2656         abstractSubstituteProperties.put(substitutionTemplateInputName, propertyValue);
2657       }
2658     }
2659   }
2660
2661   private void updateIdenticalPropertyValue(String identicalValuePropertyName,
2662                                             String substitutionTemplateInputName,
2663                                             String computeType,
2664                                             UnifiedCompositionEntity entity,
2665                                             UnifiedCompositionData unifiedCompositionData,
2666                                             ServiceTemplate serviceTemplate,
2667                                             Map<String, Object> abstractSubstituteProperties,
2668                                             TranslationContext context) {
2669     Optional<Object> identicalPropertyValueByType =
2670         getIdenticalPropertyValueByType(identicalValuePropertyName, substitutionTemplateInputName,
2671             entity, unifiedCompositionData, serviceTemplate, context);
2672
2673     if (identicalPropertyValueByType.isPresent()) {
2674       abstractSubstituteProperties
2675           .put(substitutionTemplateInputName, identicalPropertyValueByType.get());
2676
2677     }
2678
2679
2680   }
2681
2682   private Optional<Object> getIdenticalPropertyValueByType(String identicalValuePropertyName,
2683                                                            String substitutionTemplateInputName,
2684                                                            UnifiedCompositionEntity entity,
2685                                                            UnifiedCompositionData unifiedCompositionData,
2686                                                            ServiceTemplate serviceTemplate,
2687                                                            TranslationContext context) {
2688
2689     ComputeTemplateConsolidationData computeTemplateConsolidationData =
2690         unifiedCompositionData.getComputeTemplateConsolidationData();
2691
2692     Optional<Object> computeIdenticalPropertyValue;
2693     switch (entity) {
2694       case Compute:
2695         computeIdenticalPropertyValue =
2696             getIdenticalPropertyValue(identicalValuePropertyName, serviceTemplate,
2697                 entity, computeTemplateConsolidationData, context);
2698         return computeIdenticalPropertyValue.isPresent() ? Optional.of(
2699             computeIdenticalPropertyValue.get()) : Optional.empty();
2700
2701       case Other:
2702         computeIdenticalPropertyValue =
2703             getIdenticalPropertyValue(identicalValuePropertyName, serviceTemplate,
2704                 entity, computeTemplateConsolidationData, context);
2705         return computeIdenticalPropertyValue.isPresent() ? Optional.of(
2706             computeIdenticalPropertyValue.get()) : Optional.empty();
2707
2708       case Port:
2709         List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
2710             unifiedCompositionData.getPortTemplateConsolidationDataList();
2711         for (PortTemplateConsolidationData portTemplateConsolidationData : portTemplateConsolidationDataList) {
2712           String portType =
2713               ConsolidationDataUtil.getPortType(portTemplateConsolidationData.getNodeTemplateId());
2714           if (substitutionTemplateInputName.contains(portType)) {
2715             return getIdenticalPropertyValue(identicalValuePropertyName, serviceTemplate,
2716                 entity, portTemplateConsolidationData, context);
2717           }
2718         }
2719     }
2720
2721     return Optional.empty();
2722
2723   }
2724
2725
2726   private PortInputType getPortInputType(String inputName,
2727                                          UnifiedCompositionData unifiedCompositionData) {
2728     String portInputPrefix = UnifiedCompositionEntity.Port.name().toLowerCase() + "_";
2729     ComputeTemplateConsolidationData computeTemplateConsolidationData = unifiedCompositionData
2730         .getComputeTemplateConsolidationData();
2731     List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
2732         getPortTemplateConsolidationDataList(unifiedCompositionData);
2733     //Scan the available port node template ids to check if the input is of the form
2734     // "port_<port_node_template_id>_<property_name>"
2735     for (PortTemplateConsolidationData portTemplateConsolidationData :
2736         portTemplateConsolidationDataList) {
2737       String portNodeTemplateId = portTemplateConsolidationData.getNodeTemplateId();
2738       String portNodeTemplateIdPrefix = portInputPrefix + portNodeTemplateId;
2739       if (inputName.startsWith(portNodeTemplateIdPrefix)) {
2740         return PortInputType.NodeTemplateId;
2741       }
2742     }
2743     //Check whether the input is of the form "port_<port_type>_<property_name>"
2744     Set<String> portTypes = computeTemplateConsolidationData.getPorts().keySet();
2745     for (String portType : portTypes) {
2746       String expectedPortTypeSusbtring = portInputPrefix + portType + "_";
2747       if (inputName.startsWith(expectedPortTypeSusbtring)) {
2748         return PortInputType.PortType;
2749       }
2750     }
2751     return PortInputType.Other;
2752   }
2753
2754   private void cleanServiceTemplate(ServiceTemplate serviceTemplate,
2755                                     EntityConsolidationData entity,
2756                                     TranslationContext context) {
2757     removeNodeTemplateFromServiceTemplate(serviceTemplate, entity, context);
2758     updateHeatStackGroup(serviceTemplate, entity, context);
2759     updateSubstitutionMapping(serviceTemplate, context);
2760   }
2761
2762   private void removeNodeTemplateFromServiceTemplate(ServiceTemplate serviceTemplate,
2763                                                      EntityConsolidationData entity,
2764                                                      TranslationContext context) {
2765     String nodeTemplateIdToRemove = entity.getNodeTemplateId();
2766     Map<String, NodeTemplate> nodeTemplates =
2767         serviceTemplate.getTopology_template().getNode_templates();
2768     NodeTemplate nodeTemplateToRemove =
2769         nodeTemplates.get(nodeTemplateIdToRemove);
2770     nodeTemplates.remove(nodeTemplateIdToRemove);
2771
2772     context.addCleanedNodeTemplate(ToscaUtil.getServiceTemplateFileName(serviceTemplate),
2773         nodeTemplateIdToRemove,
2774         entity.getClass() == ComputeTemplateConsolidationData.class
2775             ? UnifiedCompositionEntity.Compute
2776             : UnifiedCompositionEntity.Port,
2777         nodeTemplateToRemove);
2778
2779   }
2780
2781   private void removeCleanedNodeType(String cleanedNodeTemplateId,
2782                                      ServiceTemplate serviceTemplate,
2783                                      TranslationContext context) {
2784     NodeTemplate cleanedNodeTemplate =
2785         context
2786             .getCleanedNodeTemplate(ToscaUtil.getServiceTemplateFileName(serviceTemplate),
2787                 cleanedNodeTemplateId);
2788     String typeToRemove = cleanedNodeTemplate.getType();
2789
2790     if (Objects.nonNull(typeToRemove)
2791         && serviceTemplate.getNode_types().containsKey(typeToRemove)) {
2792       serviceTemplate.getNode_types().remove(typeToRemove);
2793     }
2794   }
2795
2796   private void updateHeatStackGroup(ServiceTemplate serviceTemplate,
2797                                     EntityConsolidationData entity,
2798                                     TranslationContext context) {
2799     Map<String, GroupDefinition> groups = serviceTemplate.getTopology_template()
2800         .getGroups() == null ? new HashMap<>()
2801         : serviceTemplate.getTopology_template().getGroups();
2802     String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
2803     String nodeRelatedAbstractNodeId =
2804         context.getUnifiedAbstractNodeTemplateId(serviceTemplate, entity.getNodeTemplateId());
2805
2806     for (Map.Entry<String, GroupDefinition> groupEntry : groups.entrySet()) {
2807       GroupDefinition groupDefinition = groupEntry.getValue();
2808       if (isHeatStackGroup(groupDefinition.getType())) {
2809         updateGroupMembersWithNewUnifiedNodeTemplateId(entity, nodeRelatedAbstractNodeId,
2810             groupEntry);
2811       }
2812     }
2813   }
2814
2815   private void updateGroupMembersWithNewUnifiedNodeTemplateId(
2816       EntityConsolidationData entity,
2817       String newNodetemplateId,
2818       Map.Entry<String, GroupDefinition> groupEntry) {
2819     List<String> members = groupEntry.getValue().getMembers();
2820     if (members.contains(entity.getNodeTemplateId())) {
2821       members.remove(entity.getNodeTemplateId());
2822       if (!members.contains(newNodetemplateId)) {
2823         members.add(newNodetemplateId);
2824       }
2825     }
2826     groupEntry.getValue().setMembers(members);
2827   }
2828
2829   private void updateSubstitutableNodeTemplateRequirements(ServiceTemplate serviceTemplate,
2830                                                            ServiceTemplate substitutionServiceTemplate) {
2831     if (Objects.isNull(substitutionServiceTemplate.getTopology_template())) {
2832       return;
2833     }
2834
2835     SubstitutionMapping substitution_mappings =
2836         substitutionServiceTemplate.getTopology_template().getSubstitution_mappings();
2837
2838     if (Objects.isNull(substitution_mappings)) {
2839       return;
2840     }
2841
2842     String node_type = substitution_mappings.getNode_type();
2843     Map<String, List<String>> requirements = substitution_mappings.getRequirements();
2844
2845
2846   }
2847
2848   private void updateSubstitutionMapping(ServiceTemplate serviceTemplate,
2849                                          TranslationContext context) {
2850     SubstitutionMapping substitutionMappings =
2851         DataModelUtil.getSubstitutionMappings(serviceTemplate);
2852     if (Objects.nonNull(substitutionMappings)) {
2853
2854       if (Objects.nonNull(substitutionMappings.getRequirements())) {
2855         updateSubstitutionMappingRequirements(substitutionMappings.getRequirements(),
2856             serviceTemplate, context);
2857       }
2858
2859       if (Objects.nonNull(substitutionMappings.getCapabilities())) {
2860         updateSubstitutionMappingCapabilities(substitutionMappings.getCapabilities(),
2861             serviceTemplate, context);
2862       }
2863     }
2864   }
2865
2866   private void updateSubstitutionMappingRequirements(Map<String, List<String>>
2867                                                          substitutionMappingRequirements,
2868                                                      ServiceTemplate serviceTemplate,
2869                                                      TranslationContext context) {
2870     for (Map.Entry<String, List<String>> entry : substitutionMappingRequirements.entrySet()) {
2871       List<String> requirement = entry.getValue();
2872       String oldNodeTemplateId = requirement.get(0);
2873       String newAbstractNodeTemplateId = context.getUnifiedAbstractNodeTemplateId(serviceTemplate,
2874           requirement.get(0));
2875       String newSubstitutionNodeTemplateId = context.getUnifiedSubstitutionNodeTemplateId(
2876           serviceTemplate, oldNodeTemplateId);
2877       if (Objects.nonNull(newAbstractNodeTemplateId)
2878           && Objects.nonNull(newSubstitutionNodeTemplateId)) {
2879         requirement.set(0, newAbstractNodeTemplateId);
2880         String newRequirementValue = requirement.get(1) + "_" + newSubstitutionNodeTemplateId;
2881         requirement.set(1, newRequirementValue);
2882       }
2883     }
2884   }
2885
2886   private void updateSubstitutionMappingCapabilities(Map<String, List<String>>
2887                                                          substitutionMappingCapabilities,
2888                                                      ServiceTemplate serviceTemplate,
2889                                                      TranslationContext context) {
2890     for (Map.Entry<String, List<String>> entry : substitutionMappingCapabilities.entrySet()) {
2891       List<String> capability = entry.getValue();
2892       String oldNodeTemplateId = capability.get(0);
2893       String newAbstractNodeTemplateId = context.getUnifiedAbstractNodeTemplateId(serviceTemplate,
2894           capability.get(0));
2895       String newSubstitutionNodeTemplateId = context.getUnifiedSubstitutionNodeTemplateId(
2896           serviceTemplate, oldNodeTemplateId);
2897       if (Objects.nonNull(newAbstractNodeTemplateId)
2898           && Objects.nonNull(newSubstitutionNodeTemplateId)) {
2899         capability.set(0, newAbstractNodeTemplateId);
2900         String newRequirementValue = capability.get(1) + "_" + newSubstitutionNodeTemplateId;
2901         capability.set(1, newRequirementValue);
2902       }
2903     }
2904   }
2905
2906   private void updateHeatStackGroupNestedComposition(ServiceTemplate serviceTemplate,
2907                                                      EntityConsolidationData entity,
2908                                                      TranslationContext context) {
2909     Map<String, GroupDefinition> groups = serviceTemplate.getTopology_template()
2910         .getGroups() == null ? new HashMap<>() : serviceTemplate.getTopology_template().getGroups();
2911     String serviceTemplateFileName = ToscaUtil.getServiceTemplateFileName(serviceTemplate);
2912     Optional<String> nestedNodeTemplateId =
2913         context.getUnifiedNestedNodeTemplateId(serviceTemplateFileName, entity.getNodeTemplateId());
2914     if (nestedNodeTemplateId.isPresent()) {
2915       for (Map.Entry<String, GroupDefinition> groupEntry : groups.entrySet()) {
2916         GroupDefinition groupDefinition = groupEntry.getValue();
2917         if (isHeatStackGroup(groupDefinition.getType())) {
2918           updateGroupMembersWithNewUnifiedNodeTemplateId(entity, nestedNodeTemplateId.get(),
2919               groupEntry);
2920         }
2921       }
2922     }
2923   }
2924
2925   private void handleNestedNodeTemplateInMainServiceTemplate(String nestedNodeTemplateId,
2926                                                              ServiceTemplate mainServiceTemplate,
2927                                                              ServiceTemplate nestedServiceTemplate,
2928                                                              TranslationContext context) {
2929     NodeTemplate nestedNodeTemplate = DataModelUtil.getNodeTemplate(mainServiceTemplate,
2930         nestedNodeTemplateId);
2931     if (Objects.isNull(nestedNodeTemplate)) {
2932       return;
2933     }
2934
2935     updateNestedNodeTemplateProperties(nestedServiceTemplate, nestedNodeTemplate, context);
2936
2937     Optional<String> unifiedNestedNodeTypeId = context
2938         .getUnifiedNestedNodeTypeId(
2939             ToscaUtil.getServiceTemplateFileName(Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME),
2940             nestedNodeTemplate.getType());
2941     unifiedNestedNodeTypeId
2942         .ifPresent(unifiedNestedNodeTypeIdVal -> updateNestedNodeTemplate(
2943             unifiedNestedNodeTypeIdVal, nestedNodeTemplateId, nestedNodeTemplate,
2944             mainServiceTemplate, context));
2945
2946     //updateNestedNodeTemplateRequirement(nestedNodeTemplateId, mainServiceTemplate,
2947     //nestedServiceTemplate, context);
2948
2949     //updateNodeTemplateRequirements(nestedNodeTemplateId, mainServiceTemplate,
2950     //nestedServiceTemplate, context);
2951
2952     //updateNodeDependencyRequirement(mainServiceTemplate, context, nestedNodeTemplate);
2953   }
2954
2955   private void updateNestedNodeTemplateRequirement(String nestedNodeTemplateId,
2956                                                    ServiceTemplate mainServiceTemplate,
2957                                                    ServiceTemplate nestedServiceTemplate,
2958                                                    TranslationContext context) {
2959     NestedTemplateConsolidationData nestedTemplateConsolidationData =
2960         ConsolidationDataUtil
2961             .getNestedTemplateConsolidationData(context, mainServiceTemplate, null,
2962                 nestedNodeTemplateId);
2963
2964     FileComputeConsolidationData fileComputeConsolidationData =
2965         context.getConsolidationData().getComputeConsolidationData().getFileComputeConsolidationData
2966             (ToscaUtil.getServiceTemplateFileName(nestedServiceTemplate));
2967
2968
2969     TypeComputeConsolidationData compute =
2970         fileComputeConsolidationData.getAllTypeComputeConsolidationData().iterator().next();
2971
2972     if (Objects.isNull(nestedTemplateConsolidationData)) {
2973       return;
2974     }
2975
2976     Map<String, List<RequirementAssignmentData>> nodesConnectedOut =
2977         nestedTemplateConsolidationData.getNodesConnectedOut();
2978
2979     if (MapUtils.isEmpty(nodesConnectedOut)) {
2980       return;
2981     }
2982
2983     updateRequirements(nestedNodeTemplateId, mainServiceTemplate, nestedServiceTemplate, compute,
2984         nodesConnectedOut);
2985   }
2986
2987   private void updateRequirements(String nestedNodeTemplateId, ServiceTemplate mainServiceTemplate,
2988                                   ServiceTemplate nestedServiceTemplate,
2989                                   TypeComputeConsolidationData compute,
2990                                   Map<String, List<RequirementAssignmentData>> nodesConnectedOut) {
2991     NodeTemplate nodeTemplate =
2992         DataModelUtil.getNodeTemplate(mainServiceTemplate, nestedNodeTemplateId);
2993
2994     for (List<RequirementAssignmentData> requirementAssignmentDataList : nodesConnectedOut
2995         .values()) {
2996       for (RequirementAssignmentData data : requirementAssignmentDataList) {
2997         if (!data.getRequirementId().equals("dependency")) {
2998           DataModelUtil.addRequirementAssignment(nodeTemplate, data.getRequirementId(),
2999               cloneRequirementAssignment(data.getRequirementAssignment()));
3000           updateRequirementInSubMapping(nestedServiceTemplate, compute, data);
3001
3002         }
3003       }
3004     }
3005
3006     removeUneccessaryRequirements(nodeTemplate);
3007   }
3008
3009   private void updateRequirementInSubMapping(ServiceTemplate nestedServiceTemplate,
3010                                              TypeComputeConsolidationData compute,
3011                                              RequirementAssignmentData data) {
3012     List<String> subMappingRequirement =
3013         Arrays.asList(compute.getAllComputeNodeTemplateIds().iterator().next(), "dependency");
3014     DataModelUtil.addSubstitutionMappingReq(nestedServiceTemplate, data.getRequirementId(),
3015         subMappingRequirement);
3016   }
3017
3018
3019   private RequirementAssignment cloneRequirementAssignment(RequirementAssignment reqToClone) {
3020     RequirementAssignment requirementAssignment = new RequirementAssignment();
3021
3022     requirementAssignment.setRelationship(reqToClone.getRelationship());
3023     requirementAssignment.setNode(reqToClone.getNode());
3024     requirementAssignment.setCapability(reqToClone.getCapability());
3025
3026     return requirementAssignment;
3027   }
3028
3029   private void removeUneccessaryRequirements(NodeTemplate nodeTemplate) {
3030     List<Map<String, RequirementAssignment>> reqsToRemove = new ArrayList<>();
3031     for (Map<String, RequirementAssignment> requirementDefinitionMap : nodeTemplate
3032         .getRequirements()) {
3033       if (requirementDefinitionMap.containsKey("dependency")) {
3034         reqsToRemove.add(requirementDefinitionMap);
3035       }
3036     }
3037
3038     nodeTemplate.getRequirements().removeAll(reqsToRemove);
3039   }
3040
3041   private RequirementAssignment getRequirementAssignmentFromDefinition(
3042       Map.Entry<String, RequirementDefinition> requirementDefinitionEntry) {
3043
3044     RequirementAssignment requirementAssignment = new RequirementAssignment();
3045     if (requirementDefinitionEntry.getValue() instanceof RequirementDefinition) {
3046       requirementAssignment.setCapability(requirementDefinitionEntry.getValue().getCapability());
3047       requirementAssignment.setNode(requirementDefinitionEntry.getValue().getNode());
3048       requirementAssignment
3049           .setRelationship(requirementDefinitionEntry.getValue().getRelationship());
3050     } else if (requirementDefinitionEntry.getValue() instanceof Map) {
3051       Map<String, Object> reqAsMap = (Map<String, Object>) requirementDefinitionEntry.getValue();
3052       requirementAssignment.setCapability((String) reqAsMap.get("capability"));
3053       requirementAssignment.setNode((String) reqAsMap.get("node"));
3054       requirementAssignment.setRelationship((String) reqAsMap.get("relationship"));
3055     }
3056     return requirementAssignment;
3057   }
3058
3059   private void updateNestedNodeTemplateProperties(ServiceTemplate nestedServiceTemplate,
3060                                                   NodeTemplate nestedNodeTemplate,
3061                                                   TranslationContext context) {
3062
3063     Map<String, Object> newPropertyInputParamIds =
3064         context.getAllNewPropertyInputParamIdsPerNodeTenplateId(ToscaUtil
3065             .getServiceTemplateFileName(nestedServiceTemplate));
3066
3067     for (Map.Entry<String, Object> entry : newPropertyInputParamIds.entrySet()) {
3068       if (Objects.nonNull(entry.getValue())) {
3069         Object value = getClonedObject(entry.getValue());
3070         nestedNodeTemplate.getProperties().put(entry.getKey(), value);
3071       }
3072     }
3073
3074     String subNodeType =
3075         nestedServiceTemplate.getTopology_template().getSubstitution_mappings().getNode_type();
3076     nestedNodeTemplate.setType(subNodeType);
3077
3078   }
3079
3080   private void handleSubstitutionMappingInNestedServiceTemplate(
3081       String newNestedNodeType,
3082       ServiceTemplate nestedServiceTemplate,
3083       TranslationContext context) {
3084     if (Objects.isNull(newNestedNodeType)) {
3085       return;
3086     }
3087
3088     Set<String> relatedNestedNodeTypeIds =
3089         context.getAllRelatedNestedNodeTypeIds();
3090
3091     SubstitutionMapping substitutionMappings =
3092         nestedServiceTemplate.getTopology_template().getSubstitution_mappings();
3093     if (!relatedNestedNodeTypeIds.contains(substitutionMappings.getNode_type())) {
3094       substitutionMappings.setNode_type(newNestedNodeType);
3095     }
3096   }
3097
3098   private void updateNestedNodeTemplate(String newNestedNodeTypeId,
3099                                         String nestedNodeTemplateId,
3100                                         NodeTemplate nestedNodeTemplate,
3101                                         ServiceTemplate mainServiceTemplate,
3102                                         TranslationContext context) {
3103     String mainSTName = ToscaUtil.getServiceTemplateFileName(mainServiceTemplate);
3104     String globalSTName =
3105         ToscaUtil.getServiceTemplateFileName(Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME);
3106     int index =
3107         context.getHandledNestedComputeNodeTemplateIndex(globalSTName, newNestedNodeTypeId);
3108     String newNodeTemplateId =
3109         Constants.ABSTRACT_NODE_TEMPLATE_ID_PREFIX + getComputeTypeSuffix(newNestedNodeTypeId)
3110             + "_" + index;
3111
3112     nestedNodeTemplate.setType(newNestedNodeTypeId);
3113     mainServiceTemplate.getTopology_template().getNode_templates().remove(nestedNodeTemplateId);
3114     mainServiceTemplate.getTopology_template().getNode_templates()
3115         .put(newNodeTemplateId, nestedNodeTemplate);
3116
3117     context.addUnifiedNestedNodeTemplateId(mainSTName, nestedNodeTemplateId, newNodeTemplateId);
3118   }
3119
3120   private void handleNestedNodeTypesInGlobalSubstituteServiceTemplate(
3121       String origNestedNodeTypeId,
3122       String newNestedNodeTypeId,
3123       ServiceTemplate globalSubstitutionServiceTemplate,
3124       TranslationContext context) {
3125     Set<String> relatedNestedNodeTypeIds =
3126         context.getAllRelatedNestedNodeTypeIds();
3127
3128     Map<String, NodeType> nodeTypes = globalSubstitutionServiceTemplate.getNode_types();
3129     if (!relatedNestedNodeTypeIds.contains(origNestedNodeTypeId)) {
3130       NodeType nested = DataModelUtil.getNodeType(globalSubstitutionServiceTemplate,
3131           origNestedNodeTypeId);
3132       setNewValuesForNestedNodeType(origNestedNodeTypeId, newNestedNodeTypeId, nested, nodeTypes);
3133     } else {
3134       NodeType nested =
3135           (NodeType) DataModelUtil.getClonedObject(
3136               DataModelUtil.getNodeType(globalSubstitutionServiceTemplate, origNestedNodeTypeId));
3137       nested.setDerived_from(ToscaNodeType.VFC_ABSTRACT_SUBSTITUTE);
3138       nodeTypes.put(newNestedNodeTypeId, nested);
3139     }
3140     context.addUnifiedNestedNodeTypeId(Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME,
3141         origNestedNodeTypeId, newNestedNodeTypeId);
3142   }
3143
3144   private void setNewValuesForNestedNodeType(String origNestedNodeType,
3145                                              String newNestedNodeTypeId,
3146                                              NodeType nested,
3147                                              Map<String, NodeType> nodeTypes) {
3148     if (Objects.nonNull(nested)) {
3149       nested.setDerived_from(ToscaNodeType.VFC_ABSTRACT_SUBSTITUTE);
3150       nodeTypes.remove(origNestedNodeType);
3151       nodeTypes.put(newNestedNodeTypeId, nested);
3152     }
3153   }
3154
3155   private Optional<String> getNewNestedNodeTypeId(ServiceTemplate mainServiceTemplate,
3156                                                   ServiceTemplate nestedServiceTemplate,
3157                                                   TranslationContext context) {
3158     FileComputeConsolidationData fileComputeConsolidationData =
3159         context.getConsolidationData().getComputeConsolidationData()
3160             .getFileComputeConsolidationData(
3161                 ToscaUtil.getServiceTemplateFileName(nestedServiceTemplate));
3162
3163     if (Objects.nonNull(fileComputeConsolidationData)) {
3164       String nestedNodeTypePrefix = ToscaNodeType.ABSTRACT_NODE_TYPE_PREFIX + "heat.";
3165       return Optional
3166           .of(nestedNodeTypePrefix + getComputeTypeInNestedFile(fileComputeConsolidationData));
3167     }
3168     return Optional.empty();
3169   }
3170
3171   private String getComputeTypeInNestedFile(
3172       FileComputeConsolidationData fileComputeConsolidationData) {
3173     List<TypeComputeConsolidationData> typeComputeConsolidationDatas =
3174         new ArrayList<>(fileComputeConsolidationData.getAllTypeComputeConsolidationData());
3175     if (typeComputeConsolidationDatas.size() == 0) {
3176       return null;
3177     } else {
3178       String computeNodeType = fileComputeConsolidationData.getAllComputeTypes().iterator().next();
3179       return getComputeTypeSuffix(computeNodeType);
3180     }
3181   }
3182
3183   private void handleGetAttrInAbstractNodeTemplate(ServiceTemplate serviceTemplate,
3184                                                    TranslationContext context,
3185                                                    String serviceTemplateFileName,
3186                                                    NodeTemplate abstractNodeTemplate) {
3187     Map<String, Object> properties =
3188         abstractNodeTemplate == null || abstractNodeTemplate.getProperties() == null
3189             ? new HashMap<>()
3190             : abstractNodeTemplate.getProperties();
3191     for (Object propertyValue : properties.values()) {
3192       List<List<Object>> getAttrList = extractGetAttrFunction(propertyValue);
3193       for (List<Object> getAttrFuncValue : getAttrList) {
3194         String origNodeTemplateId = (String) getAttrFuncValue.get(0);
3195         Optional<String> nestedNodeTemplateId = context.getUnifiedNestedNodeTemplateId(ToscaUtil
3196             .getServiceTemplateFileName(serviceTemplate), origNodeTemplateId);
3197         if (nestedNodeTemplateId.isPresent()) {
3198           getAttrFuncValue.set(0, nestedNodeTemplateId.get());
3199         } else {
3200           replaceGetAttrNodeIdAndAttrName(serviceTemplate, context, serviceTemplateFileName,
3201               getAttrFuncValue);
3202         }
3203       }
3204     }
3205   }
3206
3207   private void replaceGetAttrNodeIdAndAttrName(ServiceTemplate serviceTemplate,
3208                                                TranslationContext context,
3209                                                String serviceTemplateFileName,
3210                                                List<Object> getAttrFuncValue) {
3211     String origNodeTemplateId = (String) getAttrFuncValue.get(0);
3212     String attributeName = (String) getAttrFuncValue.get(1);
3213
3214     String unifiedAbstractNodeTemplateId =
3215         context.getUnifiedAbstractNodeTemplateId(serviceTemplate, origNodeTemplateId);
3216
3217     if (Objects.isNull(unifiedAbstractNodeTemplateId)) {
3218       return;
3219     }
3220
3221     String newNodeTemplateId =
3222         getNewNodeTemplateId(origNodeTemplateId, serviceTemplateFileName, serviceTemplate, context);
3223
3224     String newSubstitutionOutputParameterId =
3225         getNewSubstitutionOutputParameterId(newNodeTemplateId, attributeName);
3226
3227     getAttrFuncValue.set(0, unifiedAbstractNodeTemplateId);
3228     getAttrFuncValue.set(1, newSubstitutionOutputParameterId);
3229   }
3230
3231   private NodeTemplate getComputeNodeTemplate(String origNodeTemplateId,
3232                                               ServiceTemplate serviceTemplate,
3233                                               TranslationContext context) {
3234     NodeTemplate computeNodeTemplate =
3235         DataModelUtil.getNodeTemplate(serviceTemplate, origNodeTemplateId);
3236     if (computeNodeTemplate == null) {
3237       computeNodeTemplate =
3238           context.getCleanedNodeTemplate(ToscaUtil.getServiceTemplateFileName(serviceTemplate),
3239               origNodeTemplateId);
3240     }
3241     return computeNodeTemplate;
3242   }
3243
3244   private String handleIdOfPort(String origNodeTemplateId, String serviceTemplateFileName,
3245                                 ConsolidationData consolidationData) {
3246     Optional<Pair<String, ComputeTemplateConsolidationData>>
3247         computeTypeAndComputeTemplateByPortId =
3248         getComputeTypeAndComputeTemplateByPortId(origNodeTemplateId, serviceTemplateFileName,
3249             consolidationData);
3250     if (computeTypeAndComputeTemplateByPortId.isPresent()) {
3251       Pair<String, ComputeTemplateConsolidationData> computeIdToComputeData =
3252           computeTypeAndComputeTemplateByPortId.get();
3253       return getNewPortNodeTemplateId(origNodeTemplateId, computeIdToComputeData.getKey(),
3254           computeIdToComputeData.getValue());
3255     }
3256
3257     return null;
3258   }
3259
3260   private Optional<Pair<String, ComputeTemplateConsolidationData>>
3261   getComputeTypeAndComputeTemplateByPortId(String portId, String serviceTemplateFileName,
3262                                            ConsolidationData consolidationData) {
3263     FileComputeConsolidationData fileComputeConsolidationData =
3264         consolidationData.getComputeConsolidationData()
3265             .getFileComputeConsolidationData(serviceTemplateFileName);
3266     Set<String> computeTypes =
3267         fileComputeConsolidationData.getAllComputeTypes();
3268
3269     for (String computeType : computeTypes) {
3270       Collection<ComputeTemplateConsolidationData> computeTemplateConsolidationDatas =
3271           fileComputeConsolidationData.getTypeComputeConsolidationData(computeType)
3272               .getAllComputeTemplateConsolidationData();
3273
3274       for (ComputeTemplateConsolidationData compute : computeTemplateConsolidationDatas) {
3275         if (ConsolidationDataUtil.isComputeReferenceToPortId(compute, portId)) {
3276           return Optional.of(new ImmutablePair<>(computeType, compute));
3277         }
3278       }
3279     }
3280
3281     return Optional.empty();
3282   }
3283
3284   private boolean isIdIsOfExpectedType(String id,
3285                                        UnifiedCompositionEntity expectedUnifiedCompositionEntity,
3286                                        String serviceTemplateFileName,
3287                                        TranslationContext context) {
3288     UnifiedSubstitutionData unifiedSubstitutionData =
3289         context.getUnifiedSubstitutionData().get(serviceTemplateFileName);
3290     if (Objects.isNull(unifiedSubstitutionData)) {
3291       return false;
3292     }
3293
3294     UnifiedCompositionEntity actualUnifiedCompositionEntity =
3295         unifiedSubstitutionData.getCleanedNodeTemplateCompositionEntity(id);
3296
3297     return actualUnifiedCompositionEntity == null ? false
3298         : actualUnifiedCompositionEntity.equals(expectedUnifiedCompositionEntity);
3299   }
3300
3301   private boolean isHeatStackGroup(String groupType) {
3302     return groupType.equals(ToscaGroupType.HEAT_STACK);
3303   }
3304
3305   private Object getPortPropertyValue(String inputName,
3306                                       String computeType,
3307                                       PortInputType portInputType,
3308                                       ServiceTemplate serviceTemplate,
3309                                       String portNodeTemplateId) {
3310     //Get the input prefix to extract the property name from the input name
3311     String portInputPrefix = getPortInputPrefix(
3312         portNodeTemplateId, portInputType);
3313     //Get the property name from the input
3314     Optional<String> propertyName = getPropertyNameFromInput(inputName,
3315         UnifiedCompositionEntity.Port, computeType, portInputPrefix);
3316     //Get the property value from the node template
3317     if (propertyName.isPresent()) {
3318       NodeTemplate portNodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate,
3319           portNodeTemplateId);
3320       if (Objects.nonNull(portNodeTemplate)) {
3321         return getPropertyValueFromNodeTemplate(propertyName.get(), portNodeTemplate);
3322       }
3323     }
3324     return Optional.empty();
3325   }
3326
3327   private Optional<String> getPortTypeFromInput(
3328       String inputName,
3329       String portNodeTemplateId,
3330       ComputeTemplateConsolidationData computeTemplateConsolidationData) {
3331     String portTypeFromInput = null;
3332     String portInputPrefix = UnifiedCompositionEntity.Port.name().toLowerCase() + "_";
3333     String portNodeTemplateIdPrefix = portInputPrefix + portNodeTemplateId;
3334     if (inputName.startsWith(portNodeTemplateIdPrefix)) {
3335       return Optional.empty();
3336     }
3337     Set<String> portTypes = computeTemplateConsolidationData.getPorts().keySet();
3338     for (String portType : portTypes) {
3339       String expectedPortTypeSusbtring = "_" + portType + "_";
3340       if (inputName.contains(expectedPortTypeSusbtring)) {
3341         portTypeFromInput = portType;
3342         break;
3343       }
3344     }
3345     return Optional.ofNullable(portTypeFromInput);
3346   }
3347
3348   private Object getComputePropertyValue(
3349       String inputName,
3350       ServiceTemplate serviceTemplate,
3351       ComputeTemplateConsolidationData computeTemplateConsolidationData) {
3352     NodeTemplate nodeTemplate = DataModelUtil.getNodeTemplate(serviceTemplate,
3353         computeTemplateConsolidationData.getNodeTemplateId());
3354     String nodeType = getComputeTypeSuffix(nodeTemplate.getType());
3355     Optional<String> propertyName =
3356         getPropertyNameFromInput(inputName, UnifiedCompositionEntity.Compute, nodeType, null);
3357     if (propertyName.isPresent()) {
3358       return getPropertyValueFromNodeTemplate(propertyName.get(), nodeTemplate);
3359     }
3360     return Optional.empty();
3361   }
3362
3363   private Optional<Object> getIdenticalPropertyValue(String identicalValuePropertyName,
3364                                                      ServiceTemplate serviceTemplate,
3365                                                      UnifiedCompositionEntity unifiedCompositionEntity,
3366                                                      EntityConsolidationData entity,
3367                                                      TranslationContext context) {
3368     NodeTemplate nodeTemplate =
3369         getNodeTemplate(entity.getNodeTemplateId(), serviceTemplate, context);
3370
3371     Object propertyValueFromNodeTemplate =
3372         getPropertyValueFromNodeTemplate(identicalValuePropertyName, nodeTemplate);
3373
3374     return Objects.isNull(propertyValueFromNodeTemplate) ? Optional.empty()
3375         : Optional.of(propertyValueFromNodeTemplate);
3376   }
3377
3378   private UnifiedCompositionEntity getInputCompositionEntity(String inputName) {
3379     UnifiedCompositionEntity inputCompositionEntity = UnifiedCompositionEntity.Other;
3380     String inputType = inputName.substring(0, inputName.indexOf('_'));
3381     if (inputType.equals(UnifiedCompositionEntity.Compute.name().toLowerCase())) {
3382       inputCompositionEntity = UnifiedCompositionEntity.Compute;
3383     } else if (inputType.equals(UnifiedCompositionEntity.Port.name().toLowerCase())) {
3384       inputCompositionEntity = UnifiedCompositionEntity.Port;
3385     }
3386     return inputCompositionEntity;
3387   }
3388
3389   private Optional<String> getPropertyNameFromInput(
3390       String inputName,
3391       UnifiedCompositionEntity compositionEntity,
3392       String computeType, String portInputPrefix) {
3393     String propertyName = null;
3394     switch (compositionEntity) {
3395       case Compute:
3396         propertyName = inputName.substring(inputName.lastIndexOf(computeType)
3397             + computeType.length() + 1);
3398         break;
3399       case Port:
3400         if (inputName.startsWith(portInputPrefix)) {
3401           propertyName = inputName.split(portInputPrefix)[1];
3402         }
3403         break;
3404       default:
3405         break;
3406     }
3407     return Optional.ofNullable(propertyName);
3408   }
3409
3410   private String getPortInputPrefix(
3411       String portNodeTemplateId,
3412       PortInputType portInputType) {
3413     String portInputPrefix = UnifiedCompositionEntity.Port.name().toLowerCase() + "_";
3414     String portType = ConsolidationDataUtil.getPortType(portNodeTemplateId);
3415     if (portInputType == PortInputType.NodeTemplateId) {
3416       portInputPrefix += portNodeTemplateId + "_";
3417     } else if (portInputType == PortInputType.PortType) {
3418       portInputPrefix += portType + "_";
3419     }
3420     return portInputPrefix;
3421   }
3422
3423   private boolean isIdenticalValueProperty(String inputName,
3424                                            UnifiedCompositionEntity unifiedCompositionEntity,
3425                                            TranslationContext context) {
3426
3427     List<String> identicalValuePropertyList =
3428         consolidationService.getPropertiesWithIdenticalVal(unifiedCompositionEntity);
3429
3430     StringBuilder builder = getPropertyValueStringBuilder(unifiedCompositionEntity);
3431
3432     boolean isMatchingProperty = Pattern.matches(builder.toString(), inputName);
3433     return (isMatchingProperty
3434         && isPropertyFromIdenticalValuesList(inputName, unifiedCompositionEntity,
3435         identicalValuePropertyList));
3436   }
3437
3438   private boolean isPropertyFromIdenticalValuesList(String inputName,
3439                                                     UnifiedCompositionEntity unifiedCompositionEntity,
3440                                                     List<String> identicalValuePropertyList) {
3441     switch (unifiedCompositionEntity) {
3442       case Compute:
3443         return identicalValuePropertyList.contains(getIdenticalValuePropertyName(inputName,
3444             unifiedCompositionEntity, null).get());
3445
3446       case Other:
3447         return identicalValuePropertyList.contains(getIdenticalValuePropertyName(inputName,
3448             unifiedCompositionEntity, null).get());
3449
3450       case Port:
3451         return getPortPropertyNameFromInput(inputName, identicalValuePropertyList).isPresent();
3452
3453       default:
3454         return false;
3455     }
3456   }
3457
3458   private Optional<String> getPortPropertyNameFromInput(String inputName,
3459                                                         List<String> identicalValuePropertyList) {
3460     for (String identicalProperty : identicalValuePropertyList) {
3461       if (inputName.contains(identicalProperty)) {
3462         return Optional.of(identicalProperty);
3463       }
3464     }
3465     return Optional.empty();
3466   }
3467
3468   private StringBuilder getPropertyValueStringBuilder(
3469       UnifiedCompositionEntity unifiedCompositionEntity) {
3470
3471     switch (unifiedCompositionEntity) {
3472       case Compute:
3473         return getComputePropertyValueStringBuilder();
3474
3475       case Other:
3476         return getComputePropertyValueStringBuilder();
3477
3478       case Port:
3479         return getPortPropertyValueStringBuilder();
3480
3481       default:
3482         return null;
3483     }
3484   }
3485
3486   private StringBuilder getPortPropertyValueStringBuilder() {
3487     StringBuilder builder;
3488     builder = new StringBuilder(PORT_IDENTICAL_VALUE_PROPERTY_PREFIX);
3489     builder.append(".+");
3490     return builder;
3491   }
3492
3493   private StringBuilder getComputePropertyValueStringBuilder() {
3494     StringBuilder builder;
3495     builder = new StringBuilder(COMPUTE_IDENTICAL_VALUE_PROPERTY_PREFIX);
3496     builder.append("[a-z]+");
3497     builder.append(COMPUTE_IDENTICAL_VALUE_PROPERTY_SUFFIX);
3498     return builder;
3499   }
3500
3501   private Optional<String> getIdenticalValuePropertyName(String input,
3502                                                          UnifiedCompositionEntity unifiedCompositionEntity,
3503                                                          TranslationContext context) {
3504     switch (unifiedCompositionEntity) {
3505       case Compute:
3506         return Optional.of(input.split("_")[1]);
3507
3508       case Other:
3509         return Optional.of(input.split("_")[1]);
3510
3511       case Port:
3512         return getPortPropertyNameFromInput(input, consolidationService
3513             .getPropertiesWithIdenticalVal(unifiedCompositionEntity));
3514
3515       default:
3516         return Optional.empty();
3517     }
3518   }
3519
3520   private Object getPropertyValueFromNodeTemplate(String propertyName, NodeTemplate nodeTemplate) {
3521     Map<String, Object> nodeTemplateProperties = nodeTemplate.getProperties();
3522     if (nodeTemplateProperties != null) {
3523       Object propertyValue = nodeTemplateProperties.get(propertyName);
3524       propertyValue = getClonedObject(propertyValue);
3525       return propertyValue;
3526     }
3527     return null;
3528   }
3529
3530   private Map<String, UnifiedCompositionEntity> getAllConsolidationNodeTemplateIdAndType(
3531       List<UnifiedCompositionData> unifiedCompositionDataList) {
3532
3533     Map<String, UnifiedCompositionEntity> consolidationNodeTemplateIdAndType = new HashMap<>();
3534     for (UnifiedCompositionData unifiedCompositionData : unifiedCompositionDataList) {
3535       ComputeTemplateConsolidationData computeTemplateConsolidationData =
3536           unifiedCompositionData.getComputeTemplateConsolidationData();
3537       if (Objects.nonNull(computeTemplateConsolidationData)) {
3538         consolidationNodeTemplateIdAndType
3539             .put(computeTemplateConsolidationData.getNodeTemplateId(),
3540                 UnifiedCompositionEntity.Compute);
3541       }
3542       List<PortTemplateConsolidationData> portTemplateConsolidationDataList =
3543           getPortTemplateConsolidationDataList(unifiedCompositionData);
3544       for (PortTemplateConsolidationData portTemplateConsolidationData :
3545           portTemplateConsolidationDataList) {
3546         consolidationNodeTemplateIdAndType.put(portTemplateConsolidationData.getNodeTemplateId(),
3547             UnifiedCompositionEntity.Port);
3548       }
3549       NestedTemplateConsolidationData nestedTemplateConsolidationData =
3550           unifiedCompositionData.getNestedTemplateConsolidationData();
3551       if (Objects.nonNull(nestedTemplateConsolidationData)) {
3552         consolidationNodeTemplateIdAndType
3553             .put(nestedTemplateConsolidationData.getNodeTemplateId(),
3554                 UnifiedCompositionEntity.Nested);
3555       }
3556     }
3557     return consolidationNodeTemplateIdAndType;
3558   }
3559
3560   private List<PortTemplateConsolidationData> getPortTemplateConsolidationDataList(
3561       UnifiedCompositionData unifiedCompositionData) {
3562     return unifiedCompositionData.getPortTemplateConsolidationDataList() == null ? new
3563         ArrayList<>() : unifiedCompositionData.getPortTemplateConsolidationDataList();
3564   }
3565
3566   private enum PortInputType {
3567     NodeTemplateId,
3568     PortType,
3569     Other;
3570   }
3571 }