Initial OpenECOMP SDC commit
[sdc.git] / catalog-be / src / main / java / org / openecomp / sdc / be / components / impl / ImportUtils.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * SDC
4  * ================================================================================
5  * Copyright (C) 2017 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  * 
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  * 
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  */
20
21 package org.openecomp.sdc.be.components.impl;
22
23 import java.lang.reflect.Type;
24 import java.util.ArrayList;
25 import java.util.Arrays;
26 import java.util.HashMap;
27 import java.util.Iterator;
28 import java.util.List;
29 import java.util.Map;
30 import java.util.Map.Entry;
31 import java.util.function.Consumer;
32 import java.util.function.Function;
33
34 import org.apache.commons.lang3.StringEscapeUtils;
35 import org.apache.commons.lang3.text.translate.CharSequenceTranslator;
36 import org.openecomp.sdc.be.datatypes.elements.SchemaDefinition;
37 import org.openecomp.sdc.be.model.AttributeDefinition;
38 import org.openecomp.sdc.be.model.HeatParameterDefinition;
39 import org.openecomp.sdc.be.model.InputDefinition;
40 import org.openecomp.sdc.be.model.LifecycleStateEnum;
41 import org.openecomp.sdc.be.model.PropertyConstraint;
42 import org.openecomp.sdc.be.model.PropertyDefinition;
43 import org.openecomp.sdc.be.model.heat.HeatParameterType;
44 import org.openecomp.sdc.be.model.operations.impl.PropertyOperation.PropertyConstraintDeserialiser;
45 import org.openecomp.sdc.be.model.tosca.ToscaPropertyType;
46 import org.openecomp.sdc.common.api.ArtifactTypeEnum;
47 import org.openecomp.sdc.common.util.GsonFactory;
48 import org.yaml.snakeyaml.DumperOptions;
49 import org.yaml.snakeyaml.Yaml;
50 import org.yaml.snakeyaml.constructor.Constructor;
51 import org.yaml.snakeyaml.representer.Representer;
52 import org.yaml.snakeyaml.resolver.Resolver;
53
54 import com.google.gson.Gson;
55 import com.google.gson.GsonBuilder;
56 import com.google.gson.reflect.TypeToken;
57
58 import fj.data.Either;
59
60 public final class ImportUtils {
61         private ImportUtils() {
62
63         }
64
65         private static CustomResolver customResolver = new CustomResolver();
66
67         private static class CustomResolver extends Resolver {
68                 protected void addImplicitResolvers() {
69                         // avoid implicit resolvers
70                 }
71         }
72
73         public static Either<List<HeatParameterDefinition>, ResultStatusEnum> getHeatParamsWithoutImplicitTypes(String heatDecodedPayload, String artifactType) {
74                 Map<String, Object> heatData = (Map<String, Object>) new Yaml(new Constructor(), new Representer(), new DumperOptions(), customResolver).load(heatDecodedPayload);
75                 return getHeatParameters(heatData, artifactType);
76         }
77
78         public static class Constants {
79
80                 public static final String FIRST_CERTIFIED_VERSION_VERSION = "1.0";
81                 public static final String FIRST_NON_CERTIFIED_VERSION = "0.1";
82                 public static final String VENDOR_NAME = "ATT (Tosca)";
83                 public static final String VENDOR_RELEASE = "1.0.0.wd03";
84                 public static final LifecycleStateEnum NORMATIVE_TYPE_LIFE_CYCLE = LifecycleStateEnum.CERTIFIED;
85                 public static final boolean NORMATIVE_TYPE_HIGHEST_VERSION = true;
86                 // public static final String ABSTRACT_CATEGORY = "Generic/Abstract";
87                 public static final String ABSTRACT_CATEGORY_NAME = "Generic";
88                 public static final String ABSTRACT_SUBCATEGORY = "Abstract";
89                 public static final String DEFAULT_ICON = "defaulticon";
90                 public static final String INNER_VFC_DESCRIPTION = "Not reusable inner VFC";
91                 public static final String USER_DEFINED_RESOURCE_NAMESPACE_PREFIX = "org.openecomp.resource.";
92                 public static final List<String> TOSCA_DEFINITION_VERSIONS = Arrays.asList(new String[] { "tosca_simple_yaml_1_0_0", "tosca_simple_profile_for_nfv_1_0_0", "tosca_simple_yaml_1_0" });
93                 public static final List<String> TOSCA_YML_CSAR_VALID_SUFFIX = Arrays.asList(new String[] { ".yml", ".yaml", ".csar" });
94                 public static final String UI_JSON_PAYLOAD_NAME = "payloadName";
95                 public static final String ABSTRACT_NODE = "abstact";
96         }
97
98         public enum ResultStatusEnum {
99                 ELEMENT_NOT_FOUND, GENERAL_ERROR, OK, INVALID_PROPERTY_DEFAULT_VALUE, INVALID_PROPERTY_TYPE, INVALID_PROPERTY_VALUE, MISSING_ENTRY_SCHEMA_TYPE
100         }
101
102         public enum ToscaElementTypeEnum {
103                 BOOLEAN, STRING, MAP, LIST, ALL
104         }
105
106         public enum ToscaTagNamesEnum {
107                 DERIVED_FROM("derived_from"), IS_PASSWORD("is_password"),
108                 // Properties
109                 PROPERTIES("properties"), TYPE("type"), STATUS("status"), ENTRY_SCHEMA("entry_schema"), REQUIRED("required"), DESCRIPTION("description"), DEFAULT_VALUE("default"), VALUE("value"), CONSTRAINTS("constraints"),
110                 // Group Types
111                 MEMBERS("members"), METADATA("metadata"),
112                 // Policy Types
113                 TARGETS("targets"),
114                 // Capabilities
115                 CAPABILITIES("capabilities"), VALID_SOURCE_TYPES("valid_source_types"),
116                 // Requirements
117                 REQUIREMENTS("requirements"), NODE("node"), RELATIONSHIP("relationship"), CAPABILITY("capability"), INTERFACES("interfaces"),
118                 // Heat env Validation
119                 PARAMETERS("parameters"),
120                 // Import Validations
121                 TOSCA_VERSION("tosca_definitions_version"), TOPOLOGY_TEMPLATE("topology_template"), NODE_TYPES("node_types"), OCCURRENCES("occurrences"), NODE_TEMPLATES("node_templates"), GROUPS("groups"), INPUTS("inputs"),
122                 // Attributes
123                 ATTRIBUTES("attributes"), LABEL("label"), HIDDEN("hidden"), IMMUTABLE("immutable"), GET_INPUT("get_input");
124
125                 private String elementName;
126
127                 private ToscaTagNamesEnum(String elementName) {
128                         this.elementName = elementName;
129                 }
130
131                 public String getElementName() {
132                         return elementName;
133                 }
134         }
135
136         @SuppressWarnings("unchecked")
137         private static void handleElementNameNotFound(String elementName, Object elementValue, ToscaElementTypeEnum elementType, List<Object> returnedList) {
138                 if (elementValue instanceof Map) {
139                         ImportUtils.findToscaElements((Map<String, Object>) elementValue, elementName, elementType, returnedList);
140                 } else if (elementValue instanceof List) {
141                         ImportUtils.findAllToscaElementsInList((List<Object>) elementValue, elementName, elementType, returnedList);
142                 }
143         }
144
145         @SuppressWarnings("unchecked")
146         private static void handleElementNameFound(String elementName, ToscaElementTypeEnum elementType, List<Object> returnedList, Object elementValue) {
147
148                 if (elementValue instanceof Boolean) {
149                         if (elementType == ToscaElementTypeEnum.BOOLEAN || elementType == ToscaElementTypeEnum.ALL) {
150                                 returnedList.add(elementValue);
151                         }
152                 }
153
154                 else if (elementValue instanceof String) {
155                         if (elementType == ToscaElementTypeEnum.STRING || elementType == ToscaElementTypeEnum.ALL) {
156                                 returnedList.add(elementValue);
157                         }
158                 } else if (elementValue instanceof Map) {
159                         if (elementType == ToscaElementTypeEnum.MAP || elementType == ToscaElementTypeEnum.ALL) {
160                                 returnedList.add(elementValue);
161                         }
162                         ImportUtils.findToscaElements((Map<String, Object>) elementValue, elementName, elementType, returnedList);
163
164                 } else if (elementValue instanceof List) {
165                         if (elementType == ToscaElementTypeEnum.LIST || elementType == ToscaElementTypeEnum.ALL) {
166                                 returnedList.add(elementValue);
167                         }
168                         ImportUtils.findAllToscaElementsInList((List<Object>) elementValue, elementName, elementType, returnedList);
169
170                 }
171                 // For Integer, Double etc...
172                 else if (elementType == ToscaElementTypeEnum.ALL) {
173                         if (elementValue != null) {
174                                 returnedList.add(String.valueOf(elementValue));
175                         } else {
176                                 returnedList.add(elementValue);
177                         }
178
179                 }
180         }
181
182         private static void findAllToscaElementsInList(List<Object> list, String elementName, ToscaElementTypeEnum elementType, List<Object> returnedList) {
183                 Iterator<Object> listItr = list.iterator();
184                 while (listItr.hasNext()) {
185                         Object elementValue = listItr.next();
186                         handleElementNameNotFound(elementName, elementValue, elementType, returnedList);
187                 }
188
189         }
190
191         public static Either<Object, ResultStatusEnum> findToscaElement(Map<String, Object> toscaJson, ToscaTagNamesEnum elementName, ToscaElementTypeEnum elementType) {
192                 List<Object> foundElements = new ArrayList<>();
193                 Either<Object, ResultStatusEnum> returnedElement = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
194                 ImportUtils.findToscaElements(toscaJson, elementName.getElementName(), elementType, foundElements);
195                 if (foundElements.size() > 0) {
196                         returnedElement = Either.left(foundElements.get(0));
197                 }
198                 return returnedElement;
199
200         }
201
202         /**
203          * Recursively searches for all tosca elements with key equals to elementName and value equals to elementType. <br>
204          * Returns Either element with:<br>
205          * List with all value if values found<br>
206          * Or ELEMENT_NOT_FOUND ActionStatus
207          * 
208          * @param toscaJson
209          * @param toscaTagName
210          * @return
211          */
212         public static Either<List<Object>, ResultStatusEnum> findToscaElements(Map<String, Object> toscaJson, String elementName, ToscaElementTypeEnum elementType, List<Object> returnedList) {
213                 Either<List<Object>, ResultStatusEnum> returnedElement = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
214                 String skipKey = null;
215                 if (toscaJson.containsKey(elementName)) {
216                         Object elementValue = toscaJson.get(elementName);
217                         handleElementNameFound(elementName, elementType, returnedList, elementValue);
218                         skipKey = elementName;
219                 }
220
221                 Iterator<Entry<String, Object>> keyValItr = toscaJson.entrySet().iterator();
222                 while (keyValItr.hasNext()) {
223                         Entry<String, Object> keyValEntry = keyValItr.next();
224                         if (!String.valueOf(keyValEntry.getKey()).equals(skipKey)) {
225                                 handleElementNameNotFound(elementName, keyValEntry.getValue(), elementType, returnedList);
226                         }
227                 }
228
229                 if (returnedList.size() > 0) {
230                         returnedElement = Either.left(returnedList);
231                 }
232
233                 return returnedElement;
234         }
235
236         @SuppressWarnings("unchecked")
237         public static <T> Either<List<T>, ResultStatusEnum> findFirstToscaListElement(Map<String, Object> toscaJson, ToscaTagNamesEnum toscaTagName) {
238                 Either<List<T>, ResultStatusEnum> returnedElement = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
239                 Either<Object, ResultStatusEnum> findFirstToscaElement = findToscaElement(toscaJson, toscaTagName, ToscaElementTypeEnum.LIST);
240                 if (findFirstToscaElement.isLeft()) {
241                         returnedElement = Either.left((List<T>) findFirstToscaElement.left().value());
242                 }
243                 return returnedElement;
244
245         }
246
247         @SuppressWarnings("unchecked")
248         public static <T> Either<Map<String, T>, ResultStatusEnum> findFirstToscaMapElement(Map<String, Object> toscaJson, ToscaTagNamesEnum toscaTagName) {
249                 Either<Map<String, T>, ResultStatusEnum> returnedElement = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
250                 Either<Object, ResultStatusEnum> findFirstToscaElement = findToscaElement(toscaJson, toscaTagName, ToscaElementTypeEnum.MAP);
251                 if (findFirstToscaElement.isLeft()) {
252                         returnedElement = Either.left((Map<String, T>) findFirstToscaElement.left().value());
253                 }
254                 return returnedElement;
255
256         }
257
258         public static Either<String, ResultStatusEnum> findFirstToscaStringElement(Map<String, Object> toscaJson, ToscaTagNamesEnum toscaTagName) {
259                 Either<String, ResultStatusEnum> returnedElement = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
260                 Either<Object, ResultStatusEnum> findFirstToscaElements = findToscaElement(toscaJson, toscaTagName, ToscaElementTypeEnum.STRING);
261                 if (findFirstToscaElements.isLeft()) {
262                         returnedElement = Either.left((String) findFirstToscaElements.left().value());
263                 }
264                 return returnedElement;
265         }
266
267         /**
268          * searches for first Tosca in Json map (toscaJson) boolean element by name (toscaTagName) returns found element or ELEMENT_NOT_FOUND status
269          * 
270          * @param toscaJson
271          * @param toscaTagName
272          * @return
273          */
274         public static Either<String, ResultStatusEnum> findFirstToscaBooleanElement(Map<String, Object> toscaJson, ToscaTagNamesEnum toscaTagName) {
275                 Either<String, ResultStatusEnum> returnedElement = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
276                 Either<Object, ResultStatusEnum> findFirstToscaElements = findToscaElement(toscaJson, toscaTagName, ToscaElementTypeEnum.BOOLEAN);
277                 if (findFirstToscaElements.isLeft()) {
278                         returnedElement = Either.left(String.valueOf(findFirstToscaElements.left().value()));
279                 }
280                 return returnedElement;
281         }
282
283         private static void setPropertyConstraints(Map<String, Object> propertyValue, PropertyDefinition property) {
284                 Either<List<Object>, ResultStatusEnum> propertyFieldconstraints = findFirstToscaListElement(propertyValue, ToscaTagNamesEnum.CONSTRAINTS);
285                 if (propertyFieldconstraints.isLeft()) {
286                         List<Object> jsonConstraintList = propertyFieldconstraints.left().value();
287
288                         List<PropertyConstraint> constraintList = new ArrayList<>();
289                         Type constraintType = new TypeToken<PropertyConstraint>() {
290                         }.getType();
291                         Gson gson = new GsonBuilder().registerTypeAdapter(constraintType, new PropertyConstraintDeserialiser()).create();
292
293                         for (Object constraintJson : jsonConstraintList) {
294                                 PropertyConstraint propertyConstraint = gson.fromJson(gson.toJson(constraintJson), constraintType);
295                                 constraintList.add(propertyConstraint);
296                         }
297                         property.setConstraints(constraintList);
298                 }
299         }
300
301         public static PropertyDefinition createModuleProperty(Map<String, Object> propertyValue) {
302
303                 PropertyDefinition propertyDef = new PropertyDefinition();
304                 ImportUtils.setField(propertyValue, ToscaTagNamesEnum.TYPE, type -> propertyDef.setType(type));
305                 ImportUtils.setPropertyFieldRequired(propertyValue, propertyDef);
306                 ImportUtils.setField(propertyValue, ToscaTagNamesEnum.DESCRIPTION, desc -> propertyDef.setDescription(desc));
307
308                 Either<Object, ResultStatusEnum> findToscaElement = ImportUtils.findToscaElement(propertyValue, ToscaTagNamesEnum.DEFAULT_VALUE, ToscaElementTypeEnum.ALL);
309                 if (findToscaElement.isLeft()) {
310                         String propertyJsonStringValue = getPropertyJsonStringValue(findToscaElement.left().value(), propertyDef.getType());
311                         propertyDef.setDefaultValue(propertyJsonStringValue);
312                 }
313                 ImportUtils.setField(propertyValue, ToscaTagNamesEnum.IS_PASSWORD, pass -> propertyDef.setPassword(Boolean.parseBoolean(pass)));
314                 ImportUtils.setField(propertyValue, ToscaTagNamesEnum.STATUS, status -> propertyDef.setStatus(status));
315                 ImportUtils.setPropertyScheme(propertyValue, propertyDef);
316                 ImportUtils.setPropertyConstraints(propertyValue, propertyDef);
317
318                 return propertyDef;
319         }
320
321         public static InputDefinition createModuleInput(Map<String, Object> inputValue) {
322
323                 InputDefinition inputDef = new InputDefinition();
324                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.TYPE, type -> inputDef.setType(type));
325                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.REQUIRED, req -> inputDef.setRequired(Boolean.parseBoolean(req)));
326                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.DESCRIPTION, desc -> inputDef.setDescription(desc));
327
328                 Either<Object, ResultStatusEnum> findToscaElement = ImportUtils.findToscaElement(inputValue, ToscaTagNamesEnum.DEFAULT_VALUE, ToscaElementTypeEnum.ALL);
329                 if (findToscaElement.isLeft()) {
330                         String propertyJsonStringValue = getPropertyJsonStringValue(findToscaElement.left().value(), inputDef.getType());
331                         inputDef.setDefaultValue(propertyJsonStringValue);
332                 }
333                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.IS_PASSWORD, pass -> inputDef.setPassword(Boolean.parseBoolean(pass)));
334                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.STATUS, status -> inputDef.setStatus(status));
335                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.LABEL, label -> inputDef.setLabel(label));
336                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.HIDDEN, hidden -> inputDef.setHidden(Boolean.parseBoolean(hidden)));
337                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.HIDDEN, immutable -> inputDef.setImmutable(Boolean.parseBoolean(immutable)));
338                 ImportUtils.setField(inputValue, ToscaTagNamesEnum.LABEL, label -> inputDef.setLabel(label));
339                 ImportUtils.setPropertyScheme(inputValue, inputDef);
340                 ImportUtils.setPropertyConstraints(inputValue, inputDef);
341
342                 return inputDef;
343         }
344
345         public static AttributeDefinition createModuleAttribute(Map<String, Object> attributeMap) {
346
347                 AttributeDefinition attributeDef = new AttributeDefinition();
348                 ImportUtils.setField(attributeMap, ToscaTagNamesEnum.TYPE, type -> attributeDef.setType(type));
349                 ImportUtils.setField(attributeMap, ToscaTagNamesEnum.DESCRIPTION, desc -> attributeDef.setDescription(desc));
350                 ImportUtils.setField(attributeMap, ToscaTagNamesEnum.STATUS, status -> attributeDef.setStatus(status));
351                 Either<Object, ResultStatusEnum> eitherDefaultValue = ImportUtils.findToscaElement(attributeMap, ToscaTagNamesEnum.DEFAULT_VALUE, ToscaElementTypeEnum.ALL);
352                 if (eitherDefaultValue.isLeft()) {
353                         String attributeDefaultValue = getPropertyJsonStringValue(eitherDefaultValue.left().value(), attributeDef.getType());
354                         attributeDef.setDefaultValue(attributeDefaultValue);
355                 }
356                 Either<Object, ResultStatusEnum> eitherValue = ImportUtils.findToscaElement(attributeMap, ToscaTagNamesEnum.VALUE, ToscaElementTypeEnum.ALL);
357                 if (eitherValue.isLeft()) {
358                         String attributeValue = getPropertyJsonStringValue(eitherValue.left().value(), attributeDef.getType());
359                         attributeDef.setValue(attributeValue);
360                 }
361                 ImportUtils.setAttributeScheme(attributeMap, attributeDef);
362                 return attributeDef;
363         }
364
365         private static void setPropertyFieldStatus(Map<String, Object> propertyValue, PropertyDefinition propertyDef) {
366                 Either<String, ResultStatusEnum> propertyFieldIsStatus = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.STATUS);
367                 if (propertyFieldIsStatus.isLeft()) {
368                         propertyDef.setStatus(propertyFieldIsStatus.left().value());
369                 }
370
371         }
372
373         private static void setAttributeFieldStatus(Map<String, Object> propertyValue, AttributeDefinition propertyDef) {
374                 Either<String, ResultStatusEnum> propertyFieldIsStatus = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.STATUS);
375                 if (propertyFieldIsStatus.isLeft()) {
376                         propertyDef.setStatus(propertyFieldIsStatus.left().value());
377                 }
378
379         }
380
381         private static void setPropertyScheme(Map<String, Object> propertyValue, PropertyDefinition propertyDefinition) {
382                 Either<SchemaDefinition, ResultStatusEnum> eitherSchema = getSchema(propertyValue);
383                 if (eitherSchema.isLeft()) {
384                         SchemaDefinition schemaDef = new SchemaDefinition();
385                         schemaDef.setProperty(eitherSchema.left().value().getProperty());
386                         propertyDefinition.setSchema(schemaDef);
387                 }
388
389         }
390
391         private static void setAttributeScheme(Map<String, Object> propertyValue, AttributeDefinition propertyDefinition) {
392                 Either<SchemaDefinition, ResultStatusEnum> eitherSchema = getSchema(propertyValue);
393                 if (eitherSchema.isLeft()) {
394                         SchemaDefinition schemaDef = new SchemaDefinition();
395                         schemaDef.setProperty(eitherSchema.left().value().getProperty());
396                         propertyDefinition.setSchema(schemaDef);
397                 }
398
399         }
400
401         private static Either<SchemaDefinition, ResultStatusEnum> getSchema(Map<String, Object> propertyValue) {
402                 Either<SchemaDefinition, ResultStatusEnum> result = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
403                 Either<Object, ResultStatusEnum> propertyFieldEntryScheme = findToscaElement(propertyValue, ToscaTagNamesEnum.ENTRY_SCHEMA, ToscaElementTypeEnum.ALL);
404                 if (propertyFieldEntryScheme.isLeft()) {
405                         if (propertyFieldEntryScheme.left().value() instanceof String) {
406                                 String schemaType = (String) propertyFieldEntryScheme.left().value();
407                                 SchemaDefinition schema = new SchemaDefinition();
408                                 PropertyDefinition schemeProperty = new PropertyDefinition();
409                                 schemeProperty.setType(schemaType);
410                                 schema.setProperty(schemeProperty);
411                                 result = Either.left(schema);
412
413                         } else if (propertyFieldEntryScheme.left().value() instanceof Map) {
414                                 PropertyDefinition schemeProperty = createModuleProperty((Map<String, Object>) propertyFieldEntryScheme.left().value());
415                                 SchemaDefinition schema = new SchemaDefinition();
416                                 schema.setProperty(schemeProperty);
417                                 result = Either.left(schema);
418
419                         }
420
421                 }
422                 return result;
423         }
424
425         private static void setPropertyFieldIsPassword(Map<String, Object> propertyValue, PropertyDefinition dataDefinition) {
426                 Either<String, ResultStatusEnum> propertyFieldIsPassword = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.IS_PASSWORD);
427                 if (propertyFieldIsPassword.isLeft()) {
428                         dataDefinition.setPassword(Boolean.parseBoolean(propertyFieldIsPassword.left().value()));
429                 }
430         }
431
432         private static ResultStatusEnum setPropertyFieldDefaultValue(Map<String, Object> propertyValue, PropertyDefinition dataDefinition) {
433                 Either<Object, ResultStatusEnum> propertyFieldDefaultValue = findToscaElement(propertyValue, ToscaTagNamesEnum.DEFAULT_VALUE, ToscaElementTypeEnum.ALL);
434                 Gson gson = GsonFactory.getGson();
435                 if (propertyFieldDefaultValue.isLeft()) {
436                         Object defaultValue = propertyFieldDefaultValue.left().value();
437                         String type = dataDefinition.getType();
438                         ToscaPropertyType innerToscaType = ToscaPropertyType.isValidType(type);
439                         // esofer - supporting customized data types. The validation of the
440                         // type will be in the creation of the property.
441                         // if(innerToscaType == null){
442                         // return ResultStatusEnum.MISSING_ENTRY_SCHEMA_TYPE;
443                         // }
444                         // customized data types value is represented as json.
445                         // Also customized data types which are scalar ones, for example,
446                         // data type which derived from integer, their value will be
447                         // represented as json.
448                         if (innerToscaType == null || innerToscaType.equals(ToscaPropertyType.LIST) || innerToscaType.equals(ToscaPropertyType.MAP)) {
449                                 String jsonObj = null;
450                                 if (defaultValue != null) {
451                                         jsonObj = gson.toJson(defaultValue);
452                                 }
453
454                                 dataDefinition.setDefaultValue(jsonObj);
455                         } else {
456                                 dataDefinition.setDefaultValue(String.valueOf(defaultValue));
457                         }
458
459                 }
460
461                 return ResultStatusEnum.OK;
462         }
463
464         private static ResultStatusEnum setAttributeFieldDefaultValue(Map<String, Object> propertyValue, AttributeDefinition dataDefinition) {
465                 Either<Object, ResultStatusEnum> propertyFieldDefaultValue = findToscaElement(propertyValue, ToscaTagNamesEnum.DEFAULT_VALUE, ToscaElementTypeEnum.ALL);
466                 Gson gson = GsonFactory.getGson();
467                 if (propertyFieldDefaultValue.isLeft()) {
468                         Object defaultValue = propertyFieldDefaultValue.left().value();
469                         String type = dataDefinition.getType();
470                         ToscaPropertyType innerToscaType = ToscaPropertyType.isValidType(type);
471                         // esofer - supporting customized data types. The validation of the
472                         // type will be in the creation of the property.
473                         // if(innerToscaType == null){
474                         // return ResultStatusEnum.MISSING_ENTRY_SCHEMA_TYPE;
475                         // }
476                         // customized data types value is represented as json.
477                         // Also customized data types which are scalar ones, for example,
478                         // data type which derived from integer, their value will be
479                         // represented as json.
480                         if (innerToscaType == null || innerToscaType.equals(ToscaPropertyType.LIST) || innerToscaType.equals(ToscaPropertyType.MAP)) {
481                                 String jsonObj = null;
482                                 if (defaultValue != null) {
483                                         jsonObj = gson.toJson(defaultValue);
484                                 }
485
486                                 dataDefinition.setDefaultValue(jsonObj);
487                         } else {
488                                 dataDefinition.setDefaultValue(String.valueOf(defaultValue));
489                         }
490
491                 }
492
493                 return ResultStatusEnum.OK;
494         }
495
496         public static void setField(Map<String, Object> toscaJson, ToscaTagNamesEnum tagName, Consumer<String> setter) {
497                 Either<String, ResultStatusEnum> fieldStringValue = findFirstToscaStringElement(toscaJson, tagName);
498                 if (fieldStringValue.isLeft()) {
499                         setter.accept(fieldStringValue.left().value());
500                 }
501
502         }
503
504         private static void setPropertyFieldDescription(Map<String, Object> propertyValue, PropertyDefinition dataDefinition) {
505                 Either<String, ResultStatusEnum> propertyFieldDescription = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.DESCRIPTION);
506                 if (propertyFieldDescription.isLeft()) {
507                         dataDefinition.setDescription(propertyFieldDescription.left().value());
508                 }
509         }
510
511         private static void setPropertyFieldRequired(Map<String, Object> propertyValue, PropertyDefinition dataDefinition) {
512                 Either<String, ResultStatusEnum> propertyFieldRequired = findFirstToscaBooleanElement(propertyValue, ToscaTagNamesEnum.REQUIRED);
513                 if (propertyFieldRequired.isLeft()) {
514                         dataDefinition.setRequired(Boolean.parseBoolean(propertyFieldRequired.left().value()));
515                 }
516         }
517
518         private static void setAttributeFieldType(Map<String, Object> propertyValue, AttributeDefinition dataDefinition) {
519                 Either<String, ResultStatusEnum> propertyFieldType = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.TYPE);
520                 if (propertyFieldType.isLeft()) {
521                         dataDefinition.setType(propertyFieldType.left().value());
522                 }
523         }
524
525         private static void setPropertyFieldType(Map<String, Object> propertyValue, PropertyDefinition dataDefinition) {
526                 Either<String, ResultStatusEnum> propertyFieldType = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.TYPE);
527                 if (propertyFieldType.isLeft()) {
528                         dataDefinition.setType(propertyFieldType.left().value());
529                 }
530         }
531
532         private static void setAttributeFieldDescription(Map<String, Object> propertyValue, AttributeDefinition dataDefinition) {
533                 Either<String, ResultStatusEnum> propertyFieldDescription = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.DESCRIPTION);
534                 if (propertyFieldDescription.isLeft()) {
535                         dataDefinition.setDescription(propertyFieldDescription.left().value());
536                 }
537         }
538
539         public static Either<Map<String, PropertyDefinition>, ResultStatusEnum> getProperties(Map<String, Object> toscaJson) {
540                 Function<String, PropertyDefinition> elementGenByName = elementName -> createProperties(elementName);
541                 Function<Map<String, Object>, PropertyDefinition> func = map -> createModuleProperty(map);
542
543                 return getElements(toscaJson, ToscaTagNamesEnum.PROPERTIES, elementGenByName, func);
544
545         }
546
547         public static Either<Map<String, InputDefinition>, ResultStatusEnum> getInputs(Map<String, Object> toscaJson) {
548                 Function<String, InputDefinition> elementGenByName = elementName -> createInputs(elementName);
549                 Function<Map<String, Object>, InputDefinition> func = map -> createModuleInput(map);
550
551                 return getElements(toscaJson, ToscaTagNamesEnum.INPUTS, elementGenByName, func);
552
553         }
554
555         public static Either<Map<String, AttributeDefinition>, ResultStatusEnum> getAttributes(Map<String, Object> toscaJson) {
556                 Function<String, AttributeDefinition> elementGenByName = elementName -> createAttribute(elementName);
557                 Function<Map<String, Object>, AttributeDefinition> func = map -> createModuleAttribute(map);
558
559                 return getElements(toscaJson, ToscaTagNamesEnum.ATTRIBUTES, elementGenByName, func);
560         }
561
562         public static <ElementDefinition> Either<Map<String, ElementDefinition>, ResultStatusEnum> getElements(Map<String, Object> toscaJson, ToscaTagNamesEnum elementTagName, Function<String, ElementDefinition> elementGenByName,
563                         Function<Map<String, Object>, ElementDefinition> func) {
564                 Either<Map<String, ElementDefinition>, ResultStatusEnum> eitherResult = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
565                 Either<Map<String, Object>, ResultStatusEnum> toscaAttributes = findFirstToscaMapElement(toscaJson, elementTagName);
566                 if (toscaAttributes.isLeft()) {
567                         Map<String, Object> jsonAttributes = toscaAttributes.left().value();
568                         Map<String, ElementDefinition> moduleAttributes = new HashMap<>();
569                         Iterator<Entry<String, Object>> propertiesNameValue = jsonAttributes.entrySet().iterator();
570                         while (propertiesNameValue.hasNext()) {
571                                 Entry<String, Object> attributeNameValue = propertiesNameValue.next();
572                                 if (attributeNameValue.getValue() instanceof Map) {
573                                         @SuppressWarnings("unchecked")
574                                         ElementDefinition attribute = func.apply((Map<String, Object>) attributeNameValue.getValue());
575                                         moduleAttributes.put(String.valueOf(attributeNameValue.getKey()), attribute);
576                                 } else {
577
578                                         ElementDefinition element = elementGenByName.apply(String.valueOf(attributeNameValue.getValue()));
579
580                                         moduleAttributes.put(String.valueOf(attributeNameValue.getKey()), element);
581                                 }
582
583                         }
584
585                         if (moduleAttributes.size() > 0) {
586                                 eitherResult = Either.left(moduleAttributes);
587                         }
588
589                 }
590                 return eitherResult;
591
592         }
593
594         private static AttributeDefinition createAttribute(String name) {
595                 AttributeDefinition attribute = new AttributeDefinition();
596
597                 attribute.setName(name);
598                 return attribute;
599         }
600
601         private static PropertyDefinition createProperties(String name) {
602                 PropertyDefinition property = new PropertyDefinition();
603                 property.setDefaultValue(name);
604                 property.setName(name);
605                 return property;
606         }
607
608         private static InputDefinition createInputs(String name) {
609                 InputDefinition input = new InputDefinition();
610
611                 input.setName(name);
612                 return input;
613         }
614
615         public static Either<List<HeatParameterDefinition>, ResultStatusEnum> getHeatParameters(Map<String, Object> heatData, String artifactType) {
616
617                 Either<List<HeatParameterDefinition>, ResultStatusEnum> eitherResult = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
618                 Either<Map<String, Object>, ResultStatusEnum> toscaProperties = findFirstToscaMapElement(heatData, ToscaTagNamesEnum.PARAMETERS);
619                 if (toscaProperties.isLeft()) {
620                         Map<String, Object> jsonProperties = toscaProperties.left().value();
621                         List<HeatParameterDefinition> moduleProperties = new ArrayList<>();
622                         Iterator<Entry<String, Object>> propertiesNameValue = jsonProperties.entrySet().iterator();
623                         while (propertiesNameValue.hasNext()) {
624                                 Entry<String, Object> propertyNameValue = propertiesNameValue.next();
625                                 if (propertyNameValue.getValue() instanceof Map) {
626                                         if (!artifactType.equals(ArtifactTypeEnum.HEAT_ENV.getType())) {
627                                                 @SuppressWarnings("unchecked")
628                                                 Either<HeatParameterDefinition, ResultStatusEnum> propertyStatus = createModuleHeatParameter((Map<String, Object>) propertyNameValue.getValue());
629                                                 if (propertyStatus.isRight()) {
630                                                         return Either.right(propertyStatus.right().value());
631                                                 }
632                                                 HeatParameterDefinition property = propertyStatus.left().value();
633                                                 property.setName(String.valueOf(propertyNameValue.getKey()));
634                                                 moduleProperties.add(property);
635                                         } else {
636                                                 addHeatParamDefinition(moduleProperties, propertyNameValue, true);
637                                         }
638                                 } else {
639                                         addHeatParamDefinition(moduleProperties, propertyNameValue, false);
640                                 }
641
642                         }
643
644                         if (moduleProperties.size() > 0) {
645                                 eitherResult = Either.left(moduleProperties);
646                         }
647
648                 }
649                 return eitherResult;
650
651         }
652
653         private static void addHeatParamDefinition(List<HeatParameterDefinition> moduleProperties, Entry<String, Object> propertyNameValue, boolean isJson) {
654                 HeatParameterDefinition property = new HeatParameterDefinition();
655                 Object value = propertyNameValue.getValue();
656                 if (value != null) {
657                         property.setDefaultValue(isJson ? new Gson().toJson(value).toString() : StringEscapeUtils.escapeJava(String.valueOf(value)));
658                 }
659                 property.setName(String.valueOf(propertyNameValue.getKey()));
660                 moduleProperties.add(property);
661         }
662
663         private static Either<HeatParameterDefinition, ResultStatusEnum> createModuleHeatParameter(Map<String, Object> propertyValue) {
664                 HeatParameterDefinition propertyDef = new HeatParameterDefinition();
665                 String type;
666                 Either<String, ResultStatusEnum> propertyFieldType = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.TYPE);
667                 if (propertyFieldType.isLeft()) {
668                         type = propertyFieldType.left().value();
669                         propertyDef.setType(type);
670                 } else {
671                         return Either.right(ResultStatusEnum.INVALID_PROPERTY_TYPE);
672                 }
673                 Either<String, ResultStatusEnum> propertyFieldDescription = findFirstToscaStringElement(propertyValue, ToscaTagNamesEnum.DESCRIPTION);
674                 if (propertyFieldDescription.isLeft()) {
675                         propertyDef.setDescription(propertyFieldDescription.left().value());
676                 }
677
678                 Either<Object, ResultStatusEnum> propertyFieldDefaultVal = findToscaElement(propertyValue, ToscaTagNamesEnum.DEFAULT_VALUE, ToscaElementTypeEnum.ALL);
679                 if (propertyFieldDefaultVal.isLeft()) {
680                         if (propertyFieldDefaultVal.left().value() == null) {
681                                 return Either.right(ResultStatusEnum.INVALID_PROPERTY_VALUE);
682                         }
683                         Object value = propertyFieldDefaultVal.left().value();
684                         String defaultValue = type.equals(HeatParameterType.JSON.getType()) ? new Gson().toJson(value).toString() : StringEscapeUtils.escapeJava(String.valueOf(value));
685                         propertyDef.setDefaultValue(defaultValue);
686                         propertyDef.setCurrentValue(defaultValue);
687                 }
688
689                 return Either.left(propertyDef);
690         }
691
692         public static String getPropertyJsonStringValue(Object value, String type) {
693                 Gson gson = new Gson();
694                 if (type == null) {
695                         return null;
696                 }
697                 ToscaPropertyType validType = ToscaPropertyType.isValidType(type);
698                 if (validType == null || validType.equals(ToscaPropertyType.MAP) || validType.equals(ToscaPropertyType.LIST)) {
699                         return gson.toJson(value);
700                 }
701                 return value.toString();
702         }
703
704         /**
705          * removes from Json map (toscaJson) first element found by name (elementName) note that this method could update the received argument toscaJson
706          * 
707          * @param toscaJson
708          * @param elementName
709          */
710         public static void removeElementFromJsonMap(Map<String, Object> toscaJson, String elementName) {
711                 for (Entry<String, Object> entry : toscaJson.entrySet()) {
712                         String key = entry.getKey();
713                         Object value = entry.getValue();
714                         if (key.equals(elementName)) {
715                                 toscaJson.remove(elementName);
716                                 return;
717                         } else if (value instanceof Map) {
718                                 removeElementFromJsonMap((Map<String, Object>) value, elementName);
719                         }
720                 }
721         }
722 }