0902af3eb05429380d4078bde56b7f608e22dbdb
[sdc.git] /
1 /*
2  * Copyright © 2016-2017 European Support Limited
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 package org.openecomp.sdc.translator.services.heattotosca;
18
19 import org.apache.commons.collections4.CollectionUtils;
20 import org.apache.commons.collections4.MapUtils;
21 import org.apache.commons.io.FilenameUtils;
22 import org.openecomp.core.translator.api.HeatToToscaTranslator;
23 import org.openecomp.core.translator.datatypes.TranslatorOutput;
24 import org.openecomp.core.translator.factory.HeatToToscaTranslatorFactory;
25 import org.openecomp.core.utilities.file.FileContentHandler;
26 import org.openecomp.core.utilities.file.FileUtils;
27 import org.openecomp.core.utilities.orchestration.OnboardingTypesEnum;
28 import org.openecomp.core.validation.util.MessageContainerUtil;
29 import org.openecomp.sdc.common.errors.CoreException;
30 import org.openecomp.sdc.common.togglz.ToggleableFeature;
31 import org.openecomp.sdc.common.utils.SdcCommon;
32 import org.openecomp.sdc.datatypes.error.ErrorLevel;
33 import org.openecomp.sdc.datatypes.error.ErrorMessage;
34 import org.openecomp.sdc.heat.datatypes.HeatBoolean;
35 import org.openecomp.sdc.heat.datatypes.manifest.FileData;
36 import org.openecomp.sdc.heat.datatypes.model.HeatOrchestrationTemplate;
37 import org.openecomp.sdc.heat.datatypes.model.HeatResourcesTypes;
38 import org.openecomp.sdc.heat.datatypes.model.Resource;
39 import org.openecomp.sdc.heat.datatypes.structure.HeatStructureTree;
40 import org.openecomp.sdc.heat.datatypes.structure.ValidationStructureList;
41 import org.openecomp.sdc.heat.services.HeatConstants;
42 import org.openecomp.sdc.heat.services.tree.HeatTreeManager;
43 import org.openecomp.sdc.heat.services.tree.HeatTreeManagerUtil;
44 import org.openecomp.sdc.logging.api.Logger;
45 import org.openecomp.sdc.logging.api.LoggerFactory;
46 import org.openecomp.sdc.logging.context.impl.MdcDataDebugMessage;
47 import org.openecomp.sdc.logging.context.impl.MdcDataErrorMessage;
48 import org.openecomp.sdc.logging.types.LoggerConstants;
49 import org.openecomp.sdc.logging.types.LoggerErrorCode;
50 import org.openecomp.sdc.logging.types.LoggerErrorDescription;
51 import org.openecomp.sdc.logging.types.LoggerTragetServiceName;
52 import org.openecomp.sdc.tosca.datatypes.ToscaCapabilityType;
53 import org.openecomp.sdc.tosca.datatypes.ToscaElementTypes;
54 import org.openecomp.sdc.tosca.datatypes.ToscaNodeType;
55 import org.openecomp.sdc.tosca.datatypes.ToscaRelationshipType;
56 import org.openecomp.sdc.tosca.datatypes.ToscaServiceModel;
57 import org.openecomp.sdc.tosca.datatypes.model.AttributeDefinition;
58 import org.openecomp.sdc.tosca.datatypes.model.CapabilityDefinition;
59 import org.openecomp.sdc.tosca.datatypes.model.Import;
60 import org.openecomp.sdc.tosca.datatypes.model.NodeTemplate;
61 import org.openecomp.sdc.tosca.datatypes.model.NodeType;
62 import org.openecomp.sdc.tosca.datatypes.model.ParameterDefinition;
63 import org.openecomp.sdc.tosca.datatypes.model.PropertyDefinition;
64 import org.openecomp.sdc.tosca.datatypes.model.PropertyType;
65 import org.openecomp.sdc.tosca.datatypes.model.RequirementAssignment;
66 import org.openecomp.sdc.tosca.datatypes.model.RequirementDefinition;
67 import org.openecomp.sdc.tosca.datatypes.model.ServiceTemplate;
68 import org.openecomp.sdc.tosca.datatypes.model.Template;
69 import org.openecomp.sdc.tosca.datatypes.model.TopologyTemplate;
70 import org.openecomp.sdc.tosca.services.DataModelUtil;
71 import org.openecomp.sdc.tosca.services.ToscaAnalyzerService;
72 import org.openecomp.sdc.tosca.services.ToscaConstants;
73 import org.openecomp.sdc.tosca.services.ToscaExtensionYamlUtil;
74 import org.openecomp.sdc.tosca.services.ToscaUtil;
75 import org.openecomp.sdc.tosca.services.YamlUtil;
76 import org.openecomp.sdc.tosca.services.impl.ToscaAnalyzerServiceImpl;
77 import org.openecomp.sdc.translator.datatypes.heattotosca.AttachedPropertyVal;
78 import org.openecomp.sdc.translator.datatypes.heattotosca.AttachedResourceId;
79 import org.openecomp.sdc.translator.datatypes.heattotosca.ReferenceType;
80 import org.openecomp.sdc.translator.datatypes.heattotosca.TranslationContext;
81 import org.openecomp.sdc.translator.datatypes.heattotosca.to.FileDataCollection;
82 import org.openecomp.sdc.translator.datatypes.heattotosca.to.TranslateTo;
83 import org.openecomp.sdc.translator.services.heattotosca.errors.ResourceNotFoundInHeatFileErrorBuilder;
84 import org.openecomp.sdc.translator.services.heattotosca.globaltypes.GlobalTypesGenerator;
85 import org.openecomp.sdc.translator.services.heattotosca.helper.FunctionTranslationHelper;
86 import org.openecomp.sdc.translator.services.heattotosca.mapping.TranslatorHeatToToscaPropertyConverter;
87
88 import java.io.IOException;
89 import java.io.InputStream;
90 import java.util.ArrayList;
91 import java.util.Collection;
92 import java.util.HashMap;
93 import java.util.HashSet;
94 import java.util.List;
95 import java.util.Map;
96 import java.util.Objects;
97 import java.util.Optional;
98 import java.util.Set;
99 import java.util.stream.Collectors;
100
101 /**
102  * The type Heat to tosca util.
103  */
104 public class HeatToToscaUtil {
105
106   private static final Logger LOGGER = LoggerFactory.getLogger(HeatToToscaUtil.class);
107   public static final String FQ_NAME = "fq_name";
108   public static final String GET_PARAM = "get_param";
109   protected static MdcDataDebugMessage mdcDataDebugMessage = new MdcDataDebugMessage();
110   private static final String FORWARDER = "forwarder";
111   private static final String GET_ATTR = "get_attr";
112   private static final String GET_RESOURCE = "get_resource";
113
114   /**
115    * Load and translate template data translator output.
116    *
117    * @param fileNameContentMap the file name content map
118    * @return the translator output
119    */
120   public static TranslatorOutput loadAndTranslateTemplateData(
121       FileContentHandler fileNameContentMap) {
122     mdcDataDebugMessage.debugEntryMessage(null, null);
123     HeatToToscaTranslator heatToToscaTranslator =
124         HeatToToscaTranslatorFactory.getInstance().createInterface();
125
126     try (InputStream fileContent = fileNameContentMap.getFileContent(SdcCommon.MANIFEST_NAME)) {
127       heatToToscaTranslator.addManifest(SdcCommon.MANIFEST_NAME, FileUtils.toByteArray(fileContent));
128     } catch (IOException e) {
129       throw new RuntimeException("Failed to read manifest", e);
130     }
131
132     fileNameContentMap.getFileList().stream()
133         .filter(fileName -> !(fileName.equals(SdcCommon.MANIFEST_NAME))).forEach(
134             fileName -> heatToToscaTranslator
135                 .addFile(fileName, FileUtils.toByteArray
136                     (fileNameContentMap.getFileContent(fileName))));
137
138     Map<String, List<ErrorMessage>> errors = heatToToscaTranslator.validate();
139     if (MapUtils.isNotEmpty(MessageContainerUtil.getMessageByLevel(ErrorLevel.ERROR, errors))) {
140       TranslatorOutput translatorOutput = new TranslatorOutput();
141       translatorOutput.setErrorMessages(errors);
142       return translatorOutput;
143     }
144
145     try (InputStream structureFile = getHeatStructureTreeFile(fileNameContentMap)) {
146       heatToToscaTranslator.addExternalArtifacts(SdcCommon.HEAT_META, structureFile);
147
148       mdcDataDebugMessage.debugExitMessage(null, null);
149       return heatToToscaTranslator.translate();
150     } catch (IOException e) {
151       // rethrow as a RuntimeException to keep the signature backward compatible
152       throw new RuntimeException("Failed to read Heat template tree", e);
153     }
154   }
155
156
157   private static InputStream getHeatStructureTreeFile(FileContentHandler fileNameContentMap) {
158     HeatTreeManager heatTreeManager = HeatTreeManagerUtil.initHeatTreeManager(fileNameContentMap);
159     heatTreeManager.createTree();
160     HeatStructureTree tree = heatTreeManager.getTree();
161     ValidationStructureList validationStructureList = new ValidationStructureList(tree);
162     return FileUtils.convertToInputStream(validationStructureList, FileUtils.FileExtension.JSON);
163   }
164
165   /**
166    * Build list of files to search optional.
167    *
168    * @param heatFileName  the heat file name
169    * @param filesDataList the files data list
170    * @param types         the types
171    * @return the optional
172    */
173   public static Optional<List<FileData>> buildListOfFilesToSearch(String heatFileName,
174                                                                   List<FileData> filesDataList,
175                                                                   FileData.Type... types) {
176     List<FileData> list = new ArrayList<>(filesDataList);
177     Optional<FileData> resourceFileData = HeatToToscaUtil.getFileData(heatFileName, filesDataList);
178     if (resourceFileData.isPresent() && Objects.nonNull(resourceFileData.get().getData())) {
179       list.addAll(resourceFileData.get().getData());
180     }
181     return Optional.ofNullable(HeatToToscaUtil.getFilteredListOfFileDataByTypes(list, types));
182   }
183
184   /**
185    * Gets filtered list of file data by types.
186    *
187    * @param filesToSearch the files to search
188    * @param types         the types
189    * @return the filtered list of file data by types
190    */
191   public static List<FileData> getFilteredListOfFileDataByTypes(List<FileData> filesToSearch,
192                                                                 FileData.Type... types) {
193     return filesToSearch.stream().filter(FileData.buildFileDataPredicateByType(types))
194         .collect(Collectors.toList());
195   }
196
197   /**
198    * Gets file data from the list according to the input heat file name.
199    *
200    * @param heatFileName the heat file name
201    * @param fileDataList the file data list
202    * @return the file data
203    */
204   public static Optional<FileData> getFileData(String heatFileName,
205                                                Collection<FileData> fileDataList) {
206     for (FileData file : fileDataList) {
207       if (file.getFile().equals(heatFileName)) {
208         return Optional.of(file);
209       }
210     }
211     return Optional.empty();
212   }
213
214   /**
215    * Gets file data which is supported by the translator, from the context according the input heat
216    * file name.
217    *
218    * @param heatFileName the heat file name
219    * @param context      the translation context
220    * @return the file data
221    */
222   public static FileData getFileData(String heatFileName, TranslationContext context) {
223
224     List<FileData> fileDataList = context.getManifest().getContent().getData();
225     for (FileData fileData : fileDataList) {
226       if (TranslationService.getTypesToProcessByTranslator().contains(fileData.getType())
227           && fileData.getFile().equals(heatFileName)) {
228         return fileData;
229       }
230     }
231     return null;
232   }
233
234   static FileDataCollection getFileCollectionsByFilter(List<FileData> fileDataList,
235                                                        Set<FileData.Type> typeFilter,
236                                                        TranslationContext translationContext) {
237     FileDataCollection fileDataCollection = new FileDataCollection();
238     Map<String, FileData> filteredFiles = filterFileDataListByType(fileDataList, typeFilter);
239     Set<String> referenced = new HashSet<>();
240
241     for (FileData fileData : filteredFiles.values()) {
242       String fileName = fileData.getFile();
243
244       if (FileData.isHeatFile(fileData.getType())) {
245         if (fileData.getBase() != null && fileData.getBase()) {
246           fileDataCollection.addBaseFiles(fileData);
247         }
248         HeatOrchestrationTemplate heatOrchestrationTemplate = new YamlUtil()
249             .yamlToObject(translationContext.getFileContent(fileName),
250                 HeatOrchestrationTemplate.class);
251         if (MapUtils.isNotEmpty(heatOrchestrationTemplate.getResources())) {
252           applyFilterOnFileCollection(heatOrchestrationTemplate, translationContext,
253               fileDataCollection, filteredFiles, referenced);
254         }
255
256       } else {
257         fileDataCollection.addArtifactFiles(fileData);
258         filteredFiles.remove(fileData.getFile());
259       }
260     }
261
262     referenced.forEach(filteredFiles::remove);
263     if (!CollectionUtils.isEmpty(fileDataCollection.getBaseFile())) {
264       for (FileData fileData : fileDataCollection.getBaseFile()) {
265         filteredFiles.remove(fileData.getFile());
266       }
267     }
268     fileDataCollection.setAddOnFiles(filteredFiles.values());
269     return fileDataCollection;
270   }
271
272   private static void applyFilterOnFileCollection(
273       HeatOrchestrationTemplate heatOrchestrationTemplate,
274       TranslationContext translationContext,
275       FileDataCollection fileDataCollection, Map<String, FileData> filteredFiles,
276       Set<String> referenced) {
277     List<String> filenames = extractFilenamesFromFileDataList(filteredFiles.values());
278
279     for (Resource resource : heatOrchestrationTemplate.getResources().values()) {
280       if (filenames.contains(resource.getType())) {
281         handleNestedFile(translationContext, fileDataCollection, filteredFiles, referenced,
282             resource.getType());
283       } else if (resource.getType()
284           .equals(HeatResourcesTypes.RESOURCE_GROUP_RESOURCE_TYPE.getHeatResource())) {
285         handleResourceGrpNestedFile(resource, translationContext, fileDataCollection,
286             filteredFiles, filenames, referenced);
287       }
288     }
289   }
290
291   private static void handleResourceGrpNestedFile(Resource resource,
292                                                   TranslationContext translationContext,
293                                                   FileDataCollection fileDataCollection,
294                                                   Map<String, FileData> filteredFiles,
295                                                   List<String> filenames,
296                                                   Set<String> referenced) {
297     Object resourceDef = resource.getProperties().get(HeatConstants.RESOURCE_DEF_PROPERTY_NAME);
298     Object innerTypeDef = ((Map) resourceDef).get("type");
299     if (innerTypeDef instanceof String) {
300       String internalResourceType = (String) innerTypeDef;
301       if (filenames.contains(internalResourceType)) {
302         handleNestedFile(translationContext, fileDataCollection, filteredFiles,
303             referenced, internalResourceType);
304       }
305     }
306   }
307
308   private static void handleNestedFile(TranslationContext translationContext,
309                                        FileDataCollection fileDataCollection,
310                                        Map<String, FileData> filteredFiles, Set<String> referenced,
311                                        String nestedFileName) {
312
313
314     mdcDataDebugMessage.debugEntryMessage(null, null);
315
316     referenced.add(nestedFileName);
317     fileDataCollection.addNestedFiles(filteredFiles.get(nestedFileName));
318     translationContext.getNestedHeatsFiles().add(nestedFileName);
319
320     mdcDataDebugMessage.debugExitMessage(null, null);
321   }
322
323   private static Map<String, FileData> filterFileDataListByType(List<FileData> fileDataList,
324                                                                 Set<FileData.Type> typesToGet) {
325     Map<String, FileData> filtered = new HashMap<>();
326     fileDataList.stream().filter(file -> typesToGet.contains(file.getType()))
327         .forEach(file -> filtered.put(file.getFile(), file));
328     return filtered;
329   }
330
331   private static List<String> extractFilenamesFromFileDataList(Collection<FileData> fileDataList) {
332     return fileDataList.stream().map(FileData::getFile).collect(Collectors.toList());
333   }
334
335   /**
336    * Extract attached resource id optional.
337    *
338    * @param translateTo  the translate to
339    * @param propertyName the property name
340    * @return the optional
341    */
342   public static Optional<AttachedResourceId> extractAttachedResourceId(TranslateTo translateTo,
343                                                                        String propertyName) {
344
345
346     mdcDataDebugMessage.debugEntryMessage(null, null);
347
348     Object propertyValue = translateTo.getResource().getProperties().get(propertyName);
349     if (propertyValue == null) {
350       return Optional.empty();
351     }
352
353     mdcDataDebugMessage.debugExitMessage(null, null);
354     return extractAttachedResourceId(translateTo.getHeatFileName(),
355         translateTo.getHeatOrchestrationTemplate(), translateTo.getContext(), propertyValue);
356   }
357
358   /**
359    * Extract attached resource id optional.
360    *
361    * @param heatFileName              the heat file name
362    * @param heatOrchestrationTemplate the heat orchestration template
363    * @param context                   the context
364    * @param propertyValue             the property value
365    * @return the optional
366    */
367   public static Optional<AttachedResourceId> extractAttachedResourceId(
368       String heatFileName,
369       HeatOrchestrationTemplate heatOrchestrationTemplate,
370       TranslationContext context,
371       Object propertyValue) {
372
373     Object entity;
374     Object translatedId;
375
376     if (Objects.isNull(propertyValue)) {
377       return Optional.empty();
378     }
379
380     ReferenceType referenceType = ReferenceType.OTHER;
381     if (propertyValue instanceof Map && !((Map) propertyValue).isEmpty()) {
382       Map<String, Object> propMap = (Map) propertyValue;
383       Map.Entry<String, Object> entry = propMap.entrySet().iterator().next();
384       entity = entry.getValue();
385       String key = entry.getKey();
386       referenceType = getReferenceTypeFromAttachedResouce(key);
387
388       if (!FunctionTranslationFactory.getInstance(entry.getKey()).isPresent()) {
389         translatedId = null;
390       } else {
391         translatedId = FunctionTranslationFactory.getInstance(entry.getKey()).get()
392             .translateFunction(null, null, null, entry.getKey(), entry.getValue(), heatFileName,
393                 heatOrchestrationTemplate, null, context);
394       }
395       if (translatedId instanceof String
396           && !FunctionTranslationHelper.isResourceSupported((String) translatedId)) {
397         translatedId = null;
398       }
399
400     } else {
401       translatedId = propertyValue;
402       entity = propertyValue;
403     }
404
405     return Optional.of(new AttachedResourceId(translatedId, entity, referenceType));
406   }
407
408   private static ReferenceType getReferenceTypeFromAttachedResouce(String key) {
409     ReferenceType referenceType;
410     switch (key) {
411       case GET_RESOURCE:
412         referenceType = ReferenceType.GET_RESOURCE;
413         break;
414       case GET_PARAM:
415         referenceType = ReferenceType.GET_PARAM;
416         break;
417       case GET_ATTR:
418         referenceType = ReferenceType.GET_ATTR;
419         break;
420       default:
421         referenceType = ReferenceType.OTHER;
422         break;
423     }
424
425     return referenceType;
426   }
427
428   /**
429    * Gets contrail attached heat resource id.
430    *
431    * @param attachedResource the attached resource
432    * @return the contrail attached heat resource id
433    */
434   public static Optional<String> getContrailAttachedHeatResourceId(
435       AttachedResourceId attachedResource) {
436
437
438     mdcDataDebugMessage.debugEntryMessage(null, null);
439
440     if (attachedResource == null) {
441       return Optional.empty();
442     }
443
444     if (attachedResource.isGetResource()) {
445       return Optional.of((String) attachedResource.getEntityId());
446     }
447
448     if (attachedResource.isGetAttr()) {
449       return getResourceId(attachedResource.getEntityId());
450     }
451
452     mdcDataDebugMessage.debugExitMessage(null, null);
453     return Optional.empty();
454   }
455
456   /**
457    * Extract property optional.
458    *
459    * @param propertyValue the property value
460    * @return the optional
461    */
462   public static Optional<AttachedPropertyVal> extractProperty(Object propertyValue) {
463
464     mdcDataDebugMessage.debugEntryMessage(null, null);
465     Object attachedPropertyVal;
466     if (Objects.isNull(propertyValue)) {
467       return Optional.empty();
468     }
469
470     ReferenceType referenceType = ReferenceType.OTHER;
471     if (propertyValue instanceof Map && !((Map) propertyValue).isEmpty()) {
472       Map<String, Object> propMap = (Map) propertyValue;
473       Map.Entry<String, Object> entry = propMap.entrySet().iterator().next();
474       attachedPropertyVal = entry.getValue();
475       String key = entry.getKey();
476       switch (key) {
477         case GET_RESOURCE:
478           referenceType = ReferenceType.GET_RESOURCE;
479           break;
480         case GET_PARAM:
481           referenceType = ReferenceType.GET_PARAM;
482           break;
483         case GET_ATTR:
484           referenceType = ReferenceType.GET_ATTR;
485           break;
486         default:
487           break;
488       }
489
490     } else {
491       attachedPropertyVal = propertyValue;
492     }
493
494     mdcDataDebugMessage.debugExitMessage(null, null);
495     return Optional.of(new AttachedPropertyVal(attachedPropertyVal, referenceType));
496   }
497
498   /**
499    * Map boolean.
500    *
501    * @param nodeTemplate the node template
502    * @param propertyKey  the property key
503    */
504   public static void mapBoolean(NodeTemplate nodeTemplate, String propertyKey) {
505     mdcDataDebugMessage.debugEntryMessage(null, null);
506
507     Object value = nodeTemplate.getProperties().get(propertyKey);
508     if (value != null && !(value instanceof Map)) {
509       nodeTemplate.getProperties().put(propertyKey, HeatBoolean.eval(value));
510     }
511
512     mdcDataDebugMessage.debugExitMessage(null, null);
513   }
514
515   /**
516    * Map boolean list.
517    *
518    * @param nodeTemplate    the node template
519    * @param propertyListKey the property list key
520    */
521   public static void mapBooleanList(NodeTemplate nodeTemplate, String propertyListKey) {
522     Object listValue = nodeTemplate.getProperties().get(propertyListKey);
523     if (listValue instanceof List) {
524       List booleanList = (List) listValue;
525       for (int i = 0; i < booleanList.size(); i++) {
526         Object value = booleanList.get(i);
527         if (value != null && !(value instanceof Map)) {
528           booleanList.set(i, HeatBoolean.eval(value));
529         }
530       }
531     }
532   }
533
534
535   /**
536    * Is yml file type boolean.
537    *
538    * @param filename the filename
539    * @return the boolean
540    */
541   public static boolean isYmlFileType(String filename) {
542     String extension = FilenameUtils.getExtension(filename);
543     return "yaml".equalsIgnoreCase(extension)
544         || "yml".equalsIgnoreCase(extension);
545   }
546
547   /**
548    * Is nested resource boolean.
549    *
550    * @param resource the resource
551    * @return the boolean
552    */
553   public static boolean isNestedResource(Resource resource) {
554     mdcDataDebugMessage.debugEntryMessage(null, null);
555
556     String resourceType = resource.getType();
557
558     if (resourceType.equals(HeatResourcesTypes.RESOURCE_GROUP_RESOURCE_TYPE.getHeatResource())) {
559       Object resourceDef = resource.getProperties().get(HeatConstants.RESOURCE_DEF_PROPERTY_NAME);
560       if (!(((Map) resourceDef).get("type") instanceof String)) {
561         //currently only resource group which is poinitng to nested heat file is supported
562         //dynamic type is currently not supported
563         return false;
564       }
565       String internalResourceType = (String) ((Map) resourceDef).get("type");
566       if (isYamlFile(internalResourceType)) {
567         return true;
568       }
569     } else if (isYamlFile(resourceType)) {
570       return true;
571     }
572
573     mdcDataDebugMessage.debugExitMessage(null, null);
574     return false;
575   }
576
577   /**
578    * Checks if the nested resource represents a VFC or a complex VFC (Heat file should contain at
579    * least one or more compute nodes).
580    *
581    * @param resource the resource
582    * @param context the context
583    * @return true if the resource represents a VFC and false otherwise.
584    */
585   public static boolean isNestedVfcResource(Resource resource, TranslationContext context) {
586     mdcDataDebugMessage.debugEntryMessage(null, null);
587     Optional<String> nestedHeatFileName = HeatToToscaUtil.getNestedHeatFileName(resource);
588     HeatOrchestrationTemplate nestedHeatOrchestrationTemplate = new YamlUtil()
589         .yamlToObject(context.getFileContent(nestedHeatFileName.get()),
590             HeatOrchestrationTemplate.class);
591     if (Objects.nonNull(nestedHeatOrchestrationTemplate.getResources())) {
592       for (String innerResourceId : nestedHeatOrchestrationTemplate.getResources().keySet()) {
593         if (ConsolidationDataUtil
594             .isComputeResource(nestedHeatOrchestrationTemplate, innerResourceId)) {
595           return true;
596         }
597       }
598     }
599     mdcDataDebugMessage.debugExitMessage(null, null);
600     return false;
601   }
602
603   /**
604    * Get nested heat file name in case of nested resource.
605    *
606    * @param resource the resource
607    * @return the nested heat file name
608    */
609   public static Optional<String> getNestedHeatFileName(Resource resource) {
610     mdcDataDebugMessage.debugEntryMessage(null, null);
611
612     if (!isNestedResource(resource)) {
613       return Optional.empty();
614     }
615
616     String resourceType = resource.getType();
617
618     if (resourceType.equals(HeatResourcesTypes.RESOURCE_GROUP_RESOURCE_TYPE.getHeatResource())) {
619       Object resourceDef = resource.getProperties().get(HeatConstants.RESOURCE_DEF_PROPERTY_NAME);
620       String internalResourceType = (String) ((Map) resourceDef).get("type");
621       return Optional.of(internalResourceType);
622     }
623
624     mdcDataDebugMessage.debugExitMessage(null, null);
625     return Optional.of(resourceType);
626   }
627
628   /**
629    * Gets nested file.
630    *
631    * @param resource the resource
632    * @return the nested file
633    */
634   public static Optional<String> getNestedFile(Resource resource) {
635
636
637     mdcDataDebugMessage.debugEntryMessage(null, null);
638
639     if (!isNestedResource(resource)) {
640       return Optional.empty();
641     }
642     String resourceType = resource.getType();
643     if (resourceType.equals(HeatResourcesTypes.RESOURCE_GROUP_RESOURCE_TYPE.getHeatResource())) {
644       Object resourceDef = resource.getProperties().get(HeatConstants.RESOURCE_DEF_PROPERTY_NAME);
645       String internalResourceType = (String) ((Map) resourceDef).get("type");
646
647       mdcDataDebugMessage.debugExitMessage(null, null);
648       return Optional.of(internalResourceType);
649     } else {
650       mdcDataDebugMessage.debugExitMessage(null, null);
651       return Optional.of(resourceType);
652     }
653   }
654
655   private static boolean isYamlFile(String fileName) {
656     return fileName.endsWith(".yaml") || fileName.endsWith(".yml");
657   }
658
659   /**
660    * Gets resource.
661    *
662    * @param heatOrchestrationTemplate the heat orchestration template
663    * @param resourceId                the resource id
664    * @param heatFileName              the heat file name
665    * @return the resource
666    */
667   public static Resource getResource(HeatOrchestrationTemplate heatOrchestrationTemplate,
668                                      String resourceId, String heatFileName) {
669
670
671     mdcDataDebugMessage.debugEntryMessage(null, null);
672
673     Resource resource = heatOrchestrationTemplate.getResources().get(resourceId);
674     if (resource == null) {
675       MdcDataErrorMessage.createErrorMessageAndUpdateMdc(LoggerConstants.TARGET_ENTITY_DB,
676           LoggerTragetServiceName.GET_RESOURCE, ErrorLevel.ERROR.name(),
677           LoggerErrorCode.DATA_ERROR.getErrorCode(), LoggerErrorDescription.TRANSLATE_HEAT);
678       throw new CoreException(
679           new ResourceNotFoundInHeatFileErrorBuilder(resourceId, heatFileName).build());
680     }
681
682     mdcDataDebugMessage.debugExitMessage(null, null);
683     return resource;
684   }
685
686
687   /**
688    * Get resource type.
689    *
690    * @param resourceId                the resource id
691    * @param heatOrchestrationTemplate heat orchestration template
692    * @param heatFileName              heat file name
693    * @return resource type
694    */
695   public static String getResourceType(String resourceId,
696                                        HeatOrchestrationTemplate heatOrchestrationTemplate,
697                                        String heatFileName) {
698
699
700     mdcDataDebugMessage.debugEntryMessage(null, null);
701
702     mdcDataDebugMessage.debugExitMessage(null, null);
703     return HeatToToscaUtil.getResource(heatOrchestrationTemplate, resourceId, heatFileName)
704         .getType();
705   }
706
707   /**
708    * Is heat file nested boolean.
709    *
710    * @param translateTo  the translate to
711    * @param heatFileName the heat file name
712    * @return the boolean
713    */
714   public static boolean isHeatFileNested(TranslateTo translateTo, String heatFileName) {
715     return translateTo.getContext().getNestedHeatsFiles().contains(heatFileName);
716   }
717
718   /**
719    * Extract contrail get resource attached heat resource id optional.
720    *
721    * @param propertyValue the property value
722    * @return the optional
723    */
724   public static Optional<String> extractContrailGetResourceAttachedHeatResourceId(
725       Object propertyValue) {
726
727
728     mdcDataDebugMessage.debugEntryMessage(null, null);
729
730     if (propertyValue instanceof Map) {
731       if (((Map) propertyValue).containsKey(GET_ATTR)) {
732         return getResourceId(((Map) propertyValue).get(GET_ATTR));
733       } else if (((Map) propertyValue).containsKey(GET_RESOURCE)) {
734         return getHeatResourceIdFromResource((Map) propertyValue);
735       } else {
736         Collection valCollection = ((Map) propertyValue).values();
737         return evaluateHeatResourceId(valCollection);
738       }
739     } else if (propertyValue instanceof List) {
740       return evaluateHeatResourceId((List) propertyValue);
741     }
742
743     mdcDataDebugMessage.debugExitMessage(null, null);
744     return Optional.empty();
745   }
746
747   private static Optional<String> getResourceId(Object data) {
748     if (data instanceof List && CollectionUtils.size(data) > 1
749         && FQ_NAME.equals(((List) data).get(1))
750         && ((List) data).get(0) instanceof String) {
751       return Optional.of((String) ((List) data).get(0));
752     } else {
753       LOGGER.warn("invalid format of 'get_attr' function - " + data.toString());
754       return Optional.empty();
755     }
756   }
757
758   private static Optional<String> getHeatResourceIdFromResource(Map propertyValue) {
759     Object value = propertyValue.get(GET_RESOURCE);
760     if (value instanceof String) {
761       return Optional.of((String) value);
762     } else {
763       LOGGER.warn("invalid format of 'get_resource' function - " + propertyValue.toString());
764       return Optional.empty();
765     }
766   }
767
768   private static Optional<String> evaluateHeatResourceId(Collection propertyValue) {
769     for (Object prop : propertyValue) {
770       Optional<String> ret = extractContrailGetResourceAttachedHeatResourceId(prop);
771       if (ret.isPresent()) {
772         return ret;
773       }
774     }
775     return Optional.empty();
776   }
777   /**
778    * Gets tosca service model.
779    *
780    * @param context translation context
781    * @return the tosca service model
782    */
783   public static ToscaServiceModel getToscaServiceModel(TranslationContext context) {
784     mdcDataDebugMessage.debugEntryMessage(null, null);
785     mdcDataDebugMessage.debugExitMessage(null, null);
786
787     Map<String, String> metadata = new HashMap<>();
788     metadata.put(ToscaConstants.ST_METADATA_TEMPLATE_NAME, Constants.MAIN_TEMPLATE_NAME);
789     return getToscaServiceModel(context, metadata);
790   }
791
792   /**
793    * Gets tosca service model.
794    *
795    * @param context                 translation context
796    * @param entryDefinitionMetadata template name of the entry definition servie template
797    * @return the tosca service model
798    */
799   public static ToscaServiceModel getToscaServiceModel(
800       TranslationContext context,
801       Map<String, String> entryDefinitionMetadata) {
802     mdcDataDebugMessage.debugEntryMessage(null, null);
803
804     Map<String, ServiceTemplate> serviceTemplates =
805         new HashMap<>(context.getGlobalServiceTemplates());
806     Collection<ServiceTemplate> tmpServiceTemplates =
807         context.getTranslatedServiceTemplates().values();
808     for (ServiceTemplate serviceTemplate : tmpServiceTemplates) {
809       ToscaUtil.addServiceTemplateToMapWithKeyFileName(serviceTemplates, serviceTemplate);
810     }
811
812     mdcDataDebugMessage.debugExitMessage(null, null);
813     return new ToscaServiceModel(null, serviceTemplates,
814         ToscaUtil.getServiceTemplateFileName(entryDefinitionMetadata));
815   }
816
817   /**
818    * Gets service template from context.
819    *
820    * @param serviceTemplateFileName the service template file name
821    * @param context                 the context
822    * @return the service template from context
823    */
824   public static Optional<ServiceTemplate> getServiceTemplateFromContext(
825       String serviceTemplateFileName, TranslationContext context) {
826
827
828     mdcDataDebugMessage.debugEntryMessage(null, null);
829
830     for (ServiceTemplate serviceTemplate : context.getTranslatedServiceTemplates().values()) {
831       if (ToscaUtil.getServiceTemplateFileName(serviceTemplate).equals(serviceTemplateFileName)) {
832         mdcDataDebugMessage.debugExitMessage(null, null);
833         return Optional.of(serviceTemplate);
834       }
835     }
836
837     mdcDataDebugMessage.debugExitMessage(null, null);
838     return Optional.empty();
839   }
840
841   /**
842    * Adding link requerment from port node template to network node template.
843    *
844    * @param portNodeTemplate    port node template
845    * @param networkTranslatedId network node template id
846    */
847   public static RequirementAssignment addLinkReqFromPortToNetwork(NodeTemplate portNodeTemplate,
848                                                                   String networkTranslatedId) {
849
850
851     mdcDataDebugMessage.debugEntryMessage(null, null);
852
853     RequirementAssignment requirement = new RequirementAssignment();
854     requirement.setCapability(ToscaCapabilityType.NATIVE_NETWORK_LINKABLE);
855     requirement.setRelationship(ToscaRelationshipType.NATIVE_NETWORK_LINK_TO);
856     requirement.setNode(networkTranslatedId);
857     DataModelUtil.addRequirementAssignment(portNodeTemplate,
858         ToscaConstants.LINK_REQUIREMENT_ID, requirement);
859
860     mdcDataDebugMessage.debugExitMessage(null, null);
861
862     return requirement;
863   }
864
865   /**
866    * Adding binding requerment from sub interface node template to interface (port) node template.
867    *
868    * @param subInterfaceNodeTemplate sub interface template
869    * @param interfaceTranslatedId    interface node template id
870    */
871   public static void addBindingReqFromSubInterfaceToInterface(
872       NodeTemplate subInterfaceNodeTemplate, String interfaceTranslatedId) {
873
874
875     mdcDataDebugMessage.debugEntryMessage(null, null);
876
877     RequirementAssignment requirement = new RequirementAssignment();
878     requirement.setCapability(ToscaCapabilityType.NATIVE_NETWORK_BINDABLE);
879     requirement.setRelationship(ToscaRelationshipType.NATIVE_NETWORK_BINDS_TO);
880     requirement.setNode(interfaceTranslatedId);
881     DataModelUtil
882         .addRequirementAssignment(subInterfaceNodeTemplate,
883             ToscaConstants.BINDING_REQUIREMENT_ID, requirement);
884
885     mdcDataDebugMessage.debugExitMessage(null, null);
886   }
887
888   /**
889    * Get property Parameter Name Value.
890    *
891    * @param property property
892    * @return Parameter name in case the property include "get_param" function
893    */
894   public static Optional<String> getPropertyParameterNameValue(Object property) {
895     if (Objects.isNull(property)) {
896       return Optional.empty();
897     }
898     Optional<AttachedPropertyVal> extractedProperty = extractProperty(property);
899     if (extractedProperty.isPresent()) {
900       return getParameterName(extractedProperty.get());
901     }
902     return Optional.empty();
903   }
904
905   private static Optional<String> getParameterName(AttachedPropertyVal extractedProperty) {
906     if (!extractedProperty.isGetParam()) {
907       return Optional.empty();
908     }
909     Object getParamFuncValue = extractedProperty.getPropertyValue();
910     if (getParamFuncValue instanceof String) {
911       return Optional.of((String) getParamFuncValue);
912     } else {
913       return Optional.of((String) ((List) getParamFuncValue).get(0));
914     }
915   }
916
917   public static String getToscaPropertyName(TranslationContext context, String heatResourceType,
918                                             String heatPropertyName) {
919     return context.getElementMapping(heatResourceType, Constants.PROP, heatPropertyName);
920   }
921
922   /**
923    * Gets tosca property name.
924    *
925    * @param translateTo      the translate to
926    * @param heatPropertyName the heat property name
927    * @return the tosca property name
928    */
929   public static String getToscaPropertyName(TranslateTo translateTo, String heatPropertyName) {
930     return translateTo.getContext()
931         .getElementMapping(translateTo.getResource().getType(), Constants.PROP, heatPropertyName);
932   }
933
934   /**
935    * Gets tosca attribute name.
936    *
937    * @param context          the context
938    * @param heatResourceType the heat resource type
939    * @param heatAttrName     the heat attr name
940    * @return the tosca attribute name
941    */
942   public static String getToscaAttributeName(TranslationContext context, String heatResourceType,
943                                              String heatAttrName) {
944     return context.getElementMapping(heatResourceType, Constants.ATTR, heatAttrName);
945   }
946
947   /**
948    * Gets tosca attribute name.
949    *
950    * @param translateTo  the translate to
951    * @param heatAttrName the heat attr name
952    * @return the tosca attribute name
953    */
954   public static String getToscaAttributeName(TranslateTo translateTo, String heatAttrName) {
955     return translateTo.getContext()
956         .getElementMapping(translateTo.getResource().getType(), Constants.ATTR, heatAttrName);
957   }
958
959   /**
960    * Create init substitution service template service template.
961    *
962    * @param templateName the template name
963    * @return the service template
964    */
965   public static ServiceTemplate createInitSubstitutionServiceTemplate(String templateName) {
966     ServiceTemplate nestedSubstitutionServiceTemplate = new ServiceTemplate();
967     Map<String, String> templateMetadata = new HashMap<>();
968     templateMetadata.put(ToscaConstants.ST_METADATA_TEMPLATE_NAME, templateName);
969     nestedSubstitutionServiceTemplate.setMetadata(templateMetadata);
970     nestedSubstitutionServiceTemplate
971         .setTosca_definitions_version(ToscaConstants.TOSCA_DEFINITIONS_VERSION);
972     nestedSubstitutionServiceTemplate.setTopology_template(new TopologyTemplate());
973     List<Map<String, Import>> globalTypesImportList =
974         GlobalTypesGenerator.getGlobalTypesImportList();
975     globalTypesImportList.addAll(
976         HeatToToscaUtil.createImportList(Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME));
977     nestedSubstitutionServiceTemplate.setImports(globalTypesImportList);
978     return nestedSubstitutionServiceTemplate;
979   }
980
981   /**
982    * Create init global substitution service template service template.
983    *
984    * @return the service template
985    */
986   public static ServiceTemplate createInitGlobalSubstitutionServiceTemplate() {
987     ServiceTemplate globalSubstitutionServiceTemplate = new ServiceTemplate();
988     Map<String, String> templateMetadata = new HashMap<>();
989     templateMetadata.put(ToscaConstants.ST_METADATA_TEMPLATE_NAME,
990         Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME);
991     globalSubstitutionServiceTemplate.setMetadata(templateMetadata);
992     globalSubstitutionServiceTemplate
993         .setImports(GlobalTypesGenerator.getGlobalTypesImportList());
994     globalSubstitutionServiceTemplate
995         .setTosca_definitions_version(ToscaConstants.TOSCA_DEFINITIONS_VERSION);
996     return globalSubstitutionServiceTemplate;
997   }
998
999   /**
1000    * Create substitution node type node type.
1001    *
1002    * @param substitutionServiceTemplate the substitution service template
1003    * @return the node type
1004    */
1005   public NodeType createSubstitutionNodeType(ServiceTemplate substitutionServiceTemplate) {
1006     NodeType substitutionNodeType = new NodeType();
1007     substitutionNodeType.setDerived_from(ToscaNodeType.ABSTRACT_SUBSTITUTE);
1008     substitutionNodeType.setDescription(substitutionServiceTemplate.getDescription());
1009     substitutionNodeType
1010         .setProperties(manageSubstitutionNodeTypeProperties(substitutionServiceTemplate));
1011     substitutionNodeType
1012         .setAttributes(manageSubstitutionNodeTypeAttributes(substitutionServiceTemplate));
1013     return substitutionNodeType;
1014   }
1015
1016   private Map<String, PropertyDefinition> manageSubstitutionNodeTypeProperties(
1017       ServiceTemplate substitutionServiceTemplate) {
1018     mdcDataDebugMessage.debugEntryMessage(null, null);
1019
1020     Map<String, PropertyDefinition> substitutionNodeTypeProperties = new HashMap<>();
1021     Map<String, ParameterDefinition> properties =
1022         substitutionServiceTemplate.getTopology_template().getInputs();
1023     if (properties == null) {
1024       mdcDataDebugMessage.debugExitMessage(null, null);
1025       return null;
1026     }
1027
1028     PropertyDefinition propertyDefinition;
1029     String toscaPropertyName;
1030     for (Map.Entry<String, ParameterDefinition> entry : properties.entrySet()) {
1031       toscaPropertyName = entry.getKey();
1032       propertyDefinition = new PropertyDefinition();
1033       ParameterDefinition parameterDefinition =
1034           substitutionServiceTemplate.getTopology_template().getInputs().get(toscaPropertyName);
1035       propertyDefinition.setType(parameterDefinition.getType());
1036       propertyDefinition.setDescription(parameterDefinition.getDescription());
1037       propertyDefinition.setRequired(parameterDefinition.getRequired());
1038       propertyDefinition.set_default(parameterDefinition.get_default());
1039       propertyDefinition.setConstraints(parameterDefinition.getConstraints());
1040       propertyDefinition.setEntry_schema(parameterDefinition.getEntry_schema());
1041       propertyDefinition.setStatus(parameterDefinition.getStatus());
1042       substitutionNodeTypeProperties.put(toscaPropertyName, propertyDefinition);
1043     }
1044
1045     mdcDataDebugMessage.debugExitMessage(null, null);
1046     return substitutionNodeTypeProperties;
1047   }
1048
1049   private Map<String, AttributeDefinition> manageSubstitutionNodeTypeAttributes(
1050       ServiceTemplate substitutionServiceTemplate) {
1051
1052
1053     mdcDataDebugMessage.debugEntryMessage(null, null);
1054
1055     Map<String, AttributeDefinition> substitutionNodeTypeAttributes = new HashMap<>();
1056     Map<String, ParameterDefinition> attributes =
1057         substitutionServiceTemplate.getTopology_template().getOutputs();
1058     if (attributes == null) {
1059       mdcDataDebugMessage.debugExitMessage(null, null);
1060       return null;
1061     }
1062     AttributeDefinition attributeDefinition;
1063     String toscaAttributeName;
1064
1065     for (Map.Entry<String, ParameterDefinition> entry : attributes.entrySet()) {
1066       attributeDefinition = new AttributeDefinition();
1067       toscaAttributeName = entry.getKey();
1068       ParameterDefinition parameterDefinition =
1069           substitutionServiceTemplate.getTopology_template().getOutputs().get(toscaAttributeName);
1070       if (parameterDefinition.getType() != null && !parameterDefinition.getType().isEmpty()) {
1071         attributeDefinition.setType(parameterDefinition.getType());
1072       } else {
1073         attributeDefinition.setType(PropertyType.STRING.getDisplayName());
1074       }
1075       attributeDefinition.setDescription(parameterDefinition.getDescription());
1076       attributeDefinition.set_default(parameterDefinition.get_default());
1077       attributeDefinition.setEntry_schema(parameterDefinition.getEntry_schema());
1078       attributeDefinition.setStatus(parameterDefinition.getStatus());
1079       substitutionNodeTypeAttributes.put(toscaAttributeName, attributeDefinition);
1080     }
1081
1082     mdcDataDebugMessage.debugExitMessage(null, null);
1083     return substitutionNodeTypeAttributes;
1084   }
1085
1086   /**
1087    * .
1088    * Create and add substitution mapping to the nested substitution service template, and update
1089    * the subtitution node type accordingly with the exposed requerments and capabilities
1090    *
1091    * @param context                           the translation context
1092    * @param substitutionNodeTypeKey           the substitution node type key
1093    * @param nestedSubstitutionServiceTemplate the nested substitution service template
1094    * @param substitutionNodeType              the substitution node type
1095    */
1096   public static void handleSubstitutionMapping(
1097       TranslationContext context,
1098       String substitutionNodeTypeKey,
1099       ServiceTemplate nestedSubstitutionServiceTemplate,
1100       NodeType substitutionNodeType) {
1101     Map<String, Map<String, List<String>>> substitutionMapping =
1102         getSubstitutionNodeTypeExposedConnectionPoints(substitutionNodeType,
1103             nestedSubstitutionServiceTemplate, context);
1104     //add substitution mapping after capability and requirement expose calculation
1105     nestedSubstitutionServiceTemplate.getTopology_template().setSubstitution_mappings(
1106         DataModelUtil.createSubstitutionTemplateSubMapping(substitutionNodeTypeKey,
1107             substitutionNodeType, substitutionMapping));
1108   }
1109
1110   /**
1111    * Gets node type with flat hierarchy.
1112    *
1113    * @param nodeTypeId      the node type id
1114    * @param serviceTemplate the service template
1115    * @param context         the context
1116    * @return the node type with flat hierarchy
1117    */
1118   public static NodeType getNodeTypeWithFlatHierarchy(String nodeTypeId,
1119                                                       ServiceTemplate serviceTemplate,
1120                                                       TranslationContext context) {
1121     ToscaAnalyzerService toscaAnalyzerService = new ToscaAnalyzerServiceImpl();
1122     ToscaServiceModel toscaServiceModel = HeatToToscaUtil
1123         .getToscaServiceModel(context, serviceTemplate.getMetadata());
1124     return (NodeType) toscaAnalyzerService
1125         .getFlatEntity(ToscaElementTypes.NODE_TYPE, nodeTypeId, serviceTemplate, toscaServiceModel);
1126   }
1127
1128   /**
1129    * Create substitution node template node template.
1130    *
1131    * @param translateTo             the translate to
1132    * @param templateName            the template name
1133    * @param substitutionNodeTypeKey the substitution node type key
1134    * @return the node template
1135    */
1136   public NodeTemplate createSubstitutionNodeTemplate(TranslateTo translateTo, String templateName,
1137                                                      String substitutionNodeTypeKey) {
1138     NodeTemplate substitutionNodeTemplate = new NodeTemplate();
1139     List<String> directiveList = new ArrayList<>();
1140     directiveList.add(ToscaConstants.NODE_TEMPLATE_DIRECTIVE_SUBSTITUTABLE);
1141     substitutionNodeTemplate.setDirectives(directiveList);
1142     substitutionNodeTemplate.setType(substitutionNodeTypeKey);
1143     substitutionNodeTemplate.setProperties(
1144         managerSubstitutionNodeTemplateProperties(translateTo, substitutionNodeTemplate,
1145             templateName));
1146     return substitutionNodeTemplate;
1147   }
1148
1149   /**
1150    * Create abstract substitution node template.
1151    *
1152    * @param translateTo             the translate to
1153    * @param templateName            the template name
1154    * @param substitutionNodeTypeKey the substitution node type key
1155    * @return the abstract substitute node template
1156    */
1157   public static NodeTemplate createAbstractSubstitutionNodeTemplate(
1158       TranslateTo translateTo,
1159       String templateName,
1160       String substitutionNodeTypeKey) {
1161     NodeTemplate substitutionNodeTemplate = new NodeTemplate();
1162     List<String> directiveList = new ArrayList<>();
1163     directiveList.add(ToscaConstants.NODE_TEMPLATE_DIRECTIVE_SUBSTITUTABLE);
1164     substitutionNodeTemplate.setDirectives(directiveList);
1165     substitutionNodeTemplate.setType(substitutionNodeTypeKey);
1166     substitutionNodeTemplate.setProperties(
1167         managerSubstitutionNodeTemplateProperties(translateTo, substitutionNodeTemplate,
1168             templateName));
1169     return substitutionNodeTemplate;
1170   }
1171
1172
1173   /**
1174    * Checks if the source and target resource is a valid candidate for adding tosca dependency
1175    * relationship.
1176    *
1177    * @param heatOrchestrationTemplate the heat orchestration template
1178    * @param sourceResource          the source resource
1179    * @param targetResource          the target resource
1180    * @param dependencyEntity        the dependency entity
1181    * @return true if the candidate resources are a valid combination for the dependency relationship
1182    * and false otherwise
1183    */
1184   public static boolean isValidDependsOnCandidate(HeatOrchestrationTemplate
1185                                                       heatOrchestrationTemplate,
1186                                                   Resource sourceResource,
1187                                                   Resource targetResource,
1188                                                   ConsolidationEntityType dependencyEntity,
1189                                                   TranslationContext context) {
1190     dependencyEntity
1191         .setEntityType(heatOrchestrationTemplate, sourceResource, targetResource, context);
1192     ConsolidationEntityType sourceEntityType = dependencyEntity.getSourceEntityType();
1193     ConsolidationEntityType targetEntityType = dependencyEntity.getTargetEntityType();
1194
1195     return ConsolidationTypesConnectivity.isDependsOnRelationshipValid(sourceEntityType, targetEntityType);
1196   }
1197
1198   private static Map<String, Object> managerSubstitutionNodeTemplateProperties(
1199       TranslateTo translateTo,
1200       Template template,
1201       String templateName) {
1202     mdcDataDebugMessage.debugEntryMessage(null, null);
1203
1204     Map<String, Object> substitutionProperties = new HashMap<>();
1205     Map<String, Object> heatProperties = translateTo.getResource().getProperties();
1206     if (Objects.nonNull(heatProperties)) {
1207       for (Map.Entry<String, Object> entry : heatProperties.entrySet()) {
1208         Object property = TranslatorHeatToToscaPropertyConverter
1209             .getToscaPropertyValue(translateTo.getServiceTemplate(),
1210                 translateTo.getTranslatedId(), entry.getKey(),
1211                 entry.getValue(), null, translateTo.getHeatFileName(),
1212                 translateTo.getHeatOrchestrationTemplate(), template, translateTo.getContext());
1213         substitutionProperties.put(entry.getKey(), property);
1214       }
1215     }
1216
1217     mdcDataDebugMessage.debugExitMessage(null, null);
1218     return addAbstractSubstitutionProperty(templateName, substitutionProperties);
1219   }
1220
1221   private static Map<String, Object> addAbstractSubstitutionProperty(String templateName,
1222                                                                      Map<String, Object>
1223                                                                          substitutionProperties) {
1224
1225
1226     mdcDataDebugMessage.debugEntryMessage(null, null);
1227
1228     Map<String, Object> innerProps = new HashMap<>();
1229     innerProps.put(ToscaConstants.SUBSTITUTE_SERVICE_TEMPLATE_PROPERTY_NAME,
1230         ToscaUtil.getServiceTemplateFileName(templateName));
1231     substitutionProperties.put(ToscaConstants.SERVICE_TEMPLATE_FILTER_PROPERTY_NAME, innerProps);
1232
1233     mdcDataDebugMessage.debugExitMessage(null, null);
1234     return substitutionProperties;
1235   }
1236
1237   private static Map<String, Map<String, List<String>>>
1238   getSubstitutionNodeTypeExposedConnectionPoints(NodeType substitutionNodeType,
1239                                                  ServiceTemplate substitutionServiceTemplate,
1240                                                  TranslationContext context) {
1241     mdcDataDebugMessage.debugEntryMessage(null, null);
1242
1243     Map<String, NodeTemplate> nodeTemplates =
1244         substitutionServiceTemplate.getTopology_template().getNode_templates();
1245     String nodeTemplateId;
1246     NodeTemplate nodeTemplate;
1247     String nodeType;
1248     Map<String, Map<String, List<String>>> substitutionMapping = new HashMap<>();
1249     if (nodeTemplates == null) {
1250       return substitutionMapping;
1251     }
1252
1253     Map<String, List<String>> capabilitySubstitutionMapping = new HashMap<>();
1254     Map<String, List<String>> requirementSubstitutionMapping = new HashMap<>();
1255     substitutionMapping.put("capability", capabilitySubstitutionMapping);
1256     substitutionMapping.put("requirement", requirementSubstitutionMapping);
1257     List<Map<String, RequirementDefinition>> nodeTypeRequirementsDefinition;
1258     Map<String, RequirementAssignment> nodeTemplateRequirementsAssignment;
1259     List<Map<String, RequirementDefinition>> exposedRequirementsDefinition;
1260     Map<String, Map<String, RequirementAssignment>> fullFilledRequirementsDefinition =
1261         new HashMap<>();
1262     Map<String, CapabilityDefinition> nodeTypeCapabilitiesDefinition = new HashMap<>();
1263     Map<String, CapabilityDefinition> exposedCapabilitiesDefinition;
1264     ToscaAnalyzerService toscaAnalyzerService = new ToscaAnalyzerServiceImpl();
1265
1266     for (Map.Entry<String, NodeTemplate> entry : nodeTemplates.entrySet()) {
1267       nodeTemplateId = entry.getKey();
1268       nodeTemplate = entry.getValue();
1269       nodeType = nodeTemplate.getType();
1270
1271       // get requirements
1272       nodeTypeRequirementsDefinition =
1273           getNodeTypeReqs(nodeType, nodeTemplateId, substitutionServiceTemplate,
1274               requirementSubstitutionMapping, context);
1275       nodeTemplateRequirementsAssignment = DataModelUtil.getNodeTemplateRequirements(nodeTemplate);
1276       fullFilledRequirementsDefinition.put(nodeTemplateId, nodeTemplateRequirementsAssignment);
1277       //set substitution node type requirements
1278       exposedRequirementsDefinition =
1279           toscaAnalyzerService.calculateExposedRequirements(nodeTypeRequirementsDefinition,
1280           nodeTemplateRequirementsAssignment);
1281       DataModelUtil
1282           .addSubstitutionNodeTypeRequirements(substitutionNodeType, exposedRequirementsDefinition,
1283           nodeTemplateId);
1284
1285       //get capabilities
1286       addNodeTypeCapabilitiesToSubMapping(nodeTypeCapabilitiesDefinition,
1287           capabilitySubstitutionMapping, nodeType,
1288           nodeTemplateId, substitutionServiceTemplate, context);
1289     }
1290
1291     exposedCapabilitiesDefinition =
1292         toscaAnalyzerService.calculateExposedCapabilities(nodeTypeCapabilitiesDefinition,
1293         fullFilledRequirementsDefinition);
1294     DataModelUtil.addNodeTypeCapabilitiesDef(substitutionNodeType, exposedCapabilitiesDefinition);
1295
1296     mdcDataDebugMessage.debugExitMessage(null, null);
1297     return substitutionMapping;
1298   }
1299
1300   private static void addNodeTypeCapabilitiesToSubMapping(
1301       Map<String, CapabilityDefinition> nodeTypeCapabilitiesDefinition,
1302       Map<String, List<String>> capabilitySubstitutionMapping, String type, String templateName,
1303       ServiceTemplate serviceTemplate, TranslationContext context) {
1304     mdcDataDebugMessage.debugEntryMessage(null, null);
1305
1306     NodeType flatNodeType =
1307         getNodeTypeWithFlatHierarchy(type, serviceTemplate, context);
1308
1309     if (flatNodeType.getCapabilities() != null) {
1310       flatNodeType.getCapabilities()
1311           .entrySet()
1312           .stream()
1313           .filter(capabilityNodeEntry -> shouldCapabilityNeedsToBeAdded(capabilityNodeEntry.getKey()))
1314           .forEach(capabilityNodeEntry ->
1315               addCapabilityToSubMapping(
1316               templateName, capabilityNodeEntry, nodeTypeCapabilitiesDefinition, capabilitySubstitutionMapping));
1317     }
1318     mdcDataDebugMessage.debugExitMessage(null, null);
1319   }
1320
1321   private static boolean shouldCapabilityNeedsToBeAdded(String capabilityKey) {
1322     return !capabilityKey.contains(FORWARDER) || ToggleableFeature.FORWARDER_CAPABILITY.isActive();
1323   }
1324
1325   private static void addCapabilityToSubMapping(String templateName,
1326                                                 Map.Entry<String, CapabilityDefinition> capabilityNodeEntry,
1327                                                 Map<String, CapabilityDefinition> nodeTypeCapabilitiesDefinition,
1328                                                 Map<String, List<String>> capabilitySubstitutionMapping) {
1329     String capabilityKey;
1330     List<String> capabilityMapping;
1331     capabilityKey = capabilityNodeEntry.getKey() + "_" + templateName;
1332     nodeTypeCapabilitiesDefinition.put(capabilityKey, capabilityNodeEntry.getValue().clone());
1333     capabilityMapping = new ArrayList<>();
1334     capabilityMapping.add(templateName);
1335     capabilityMapping.add(capabilityNodeEntry.getKey());
1336     capabilitySubstitutionMapping.put(capabilityKey, capabilityMapping);
1337   }
1338
1339   private static List<Map<String, RequirementDefinition>> getNodeTypeReqs(
1340       String type,
1341       String templateName,
1342       ServiceTemplate serviceTemplate,
1343       Map<String, List<String>> requirementSubstitutionMapping,
1344       TranslationContext context) {
1345     mdcDataDebugMessage.debugEntryMessage(null, null);
1346     List<Map<String, RequirementDefinition>> requirementList = new ArrayList<>();
1347     NodeType flatNodeType = getNodeTypeWithFlatHierarchy(type, serviceTemplate, context);
1348     List<String> requirementMapping;
1349
1350     if (flatNodeType.getRequirements() == null) {
1351       return requirementList;
1352     }
1353
1354     for (Map<String, RequirementDefinition> requirementMap : flatNodeType.getRequirements()) {
1355       for (Map.Entry<String, RequirementDefinition> requirementNodeEntry : requirementMap
1356           .entrySet()) {
1357         ToscaExtensionYamlUtil toscaExtensionYamlUtil = new ToscaExtensionYamlUtil();
1358         RequirementDefinition requirementNodeEntryValue = toscaExtensionYamlUtil
1359             .yamlToObject(toscaExtensionYamlUtil.objectToYaml(requirementNodeEntry.getValue()),
1360                 RequirementDefinition.class);
1361         if (Objects.isNull(requirementNodeEntryValue.getOccurrences())) {
1362           requirementNodeEntryValue.setOccurrences(new Object[]{1, 1});
1363         }
1364         Map<String, RequirementDefinition> requirementDef = new HashMap<>();
1365         requirementDef.put(requirementNodeEntry.getKey(), requirementNodeEntryValue);
1366         DataModelUtil.addRequirementToList(requirementList, requirementDef);
1367         requirementMapping = new ArrayList<>();
1368         requirementMapping.add(templateName);
1369         requirementMapping.add(requirementNodeEntry.getKey());
1370         requirementSubstitutionMapping
1371             .put(requirementNodeEntry.getKey() + "_" + templateName, requirementMapping);
1372         if (Objects.isNull(requirementNodeEntryValue.getNode())) {
1373           requirementNodeEntryValue.setOccurrences(new Object[]{1, 1});
1374         }
1375       }
1376     }
1377
1378     mdcDataDebugMessage.debugExitMessage(null, null);
1379     return requirementList;
1380   }
1381
1382   /**
1383    * Fetch global substitution service template service template.
1384    *
1385    * @param serviceTemplate the service template
1386    * @param context         the context
1387    * @return the service template
1388    */
1389   public static ServiceTemplate fetchGlobalSubstitutionServiceTemplate(
1390       ServiceTemplate serviceTemplate,
1391       TranslationContext context) {
1392     ServiceTemplate globalSubstitutionServiceTemplate =
1393         context.getTranslatedServiceTemplates()
1394             .get(Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME);
1395     if (globalSubstitutionServiceTemplate == null) {
1396       globalSubstitutionServiceTemplate =
1397           HeatToToscaUtil.createInitGlobalSubstitutionServiceTemplate();
1398       context.getTranslatedServiceTemplates()
1399           .put(Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME,
1400               globalSubstitutionServiceTemplate);
1401     }
1402     boolean isImportAddedToServiceTemplate =
1403         DataModelUtil.isImportAddedToServiceTemplate(serviceTemplate.getImports(), Constants
1404             .GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME);
1405     if (!isImportAddedToServiceTemplate) {
1406       serviceTemplate.getImports()
1407           .addAll(
1408               HeatToToscaUtil.createImportList(Constants.GLOBAL_SUBSTITUTION_TYPES_TEMPLATE_NAME));
1409     }
1410     return globalSubstitutionServiceTemplate;
1411   }
1412
1413   public static List<Map<String, Import>> createImportList(String templateName) {
1414     List<Map<String, Import>> imports = new ArrayList<>();
1415     Map<String, Import> importsMap = new HashMap<>();
1416     importsMap.put(templateName, HeatToToscaUtil.createServiceTemplateImport(templateName));
1417     imports.add(importsMap);
1418     return imports;
1419   }
1420
1421   /**
1422    * Create service template import import.
1423    *
1424    * @param serviceTemplate the service template
1425    * @return the import
1426    */
1427   public static Import createServiceTemplateImport(ServiceTemplate serviceTemplate) {
1428     Import serviceTemplateImport = new Import();
1429     serviceTemplateImport.setFile(ToscaUtil.getServiceTemplateFileName(serviceTemplate));
1430     return serviceTemplateImport;
1431   }
1432
1433   /**
1434    * Create service template import import.
1435    *
1436    * @param metadataTemplateName the service template name
1437    * @return the import
1438    */
1439   public static Import createServiceTemplateImport(String metadataTemplateName) {
1440     Import serviceTemplateImport = new Import();
1441     serviceTemplateImport.setFile(ToscaUtil.getServiceTemplateFileName(metadataTemplateName));
1442     return serviceTemplateImport;
1443   }
1444
1445   public static ToscaServiceModel createToscaServiceModel(ServiceTemplate
1446                                                               entryDefinitionServiceTemplate,
1447                                                           TranslationContext translationContext) {
1448
1449
1450     mdcDataDebugMessage.debugEntryMessage(null, null);
1451
1452     mdcDataDebugMessage.debugExitMessage(null, null);
1453     return new ToscaServiceModel(getCsarArtifactFiles(translationContext),
1454         getServiceTemplates(translationContext),
1455         ToscaUtil.getServiceTemplateFileName(entryDefinitionServiceTemplate));
1456   }
1457
1458   private static FileContentHandler getCsarArtifactFiles(TranslationContext translationContext) {
1459
1460     mdcDataDebugMessage.debugEntryMessage(null, null);
1461
1462     FileContentHandler artifactFiles = new FileContentHandler();
1463     artifactFiles.setFiles(translationContext.getFiles());
1464     artifactFiles.setFiles(translationContext.getExternalArtifacts());
1465
1466     HeatTreeManager heatTreeManager =
1467         HeatTreeManagerUtil.initHeatTreeManager(translationContext.getFiles());
1468     heatTreeManager.createTree();
1469     ValidationStructureList validationStructureList =
1470         new ValidationStructureList(heatTreeManager.getTree());
1471     byte[] validationStructureFile =
1472         FileUtils.convertToBytes(validationStructureList, FileUtils.FileExtension.JSON);
1473     artifactFiles.addFile("HEAT.meta", validationStructureFile);
1474
1475     mdcDataDebugMessage.debugExitMessage(null, null);
1476     return artifactFiles;
1477   }
1478
1479
1480   private static Map<String, ServiceTemplate> getServiceTemplates(TranslationContext
1481                                                                       translationContext) {
1482
1483
1484     mdcDataDebugMessage.debugEntryMessage(null, null);
1485
1486     List<ServiceTemplate> serviceTemplates = new ArrayList<>();
1487     serviceTemplates.addAll(GlobalTypesGenerator
1488         .getGlobalTypesServiceTemplate(OnboardingTypesEnum.ZIP).values());
1489     serviceTemplates.addAll(translationContext.getTranslatedServiceTemplates().values());
1490     Map<String, ServiceTemplate> serviceTemplatesMap = new HashMap<>();
1491
1492     for (ServiceTemplate template : serviceTemplates) {
1493       serviceTemplatesMap.put(ToscaUtil.getServiceTemplateFileName(template), template);
1494     }
1495
1496     mdcDataDebugMessage.debugExitMessage(null, null);
1497     return serviceTemplatesMap;
1498   }
1499
1500 }