Import TOSCA data_types defined in VSP

Import TOSCA data_types defined in a VSP, storing it inside
the vertex metadata, so the data type is a private resource
for the created VF.

Change-Id: If888b65c7cf7a5f6d5907f2e911ea0d6455e6603
Signed-off-by: André Schmid <andre.schmid@est.tech>
(cherry picked from commit I6e96a4aef99cdaa4f8af8f5d656d56154de89441)
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/csar/YamlTemplateParsingHandler.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/csar/YamlTemplateParsingHandler.java
index 0006f83..d406c69 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/csar/YamlTemplateParsingHandler.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/csar/YamlTemplateParsingHandler.java
@@ -85,6 +85,7 @@
 import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
 import org.openecomp.sdc.be.model.CapabilityDefinition;
 import org.openecomp.sdc.be.model.ComponentInstanceProperty;
+import org.openecomp.sdc.be.model.DataTypeDefinition;
 import org.openecomp.sdc.be.model.GroupDefinition;
 import org.openecomp.sdc.be.model.GroupTypeDefinition;
 import org.openecomp.sdc.be.model.InputDefinition;
@@ -100,6 +101,7 @@
 import org.openecomp.sdc.be.model.UploadReqInfo;
 import org.openecomp.sdc.be.model.tosca.ToscaPropertyType;
 import org.openecomp.sdc.be.utils.TypeUtils;
+import org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum;
 import org.openecomp.sdc.common.log.wrappers.Logger;
 import org.springframework.stereotype.Component;
 import org.yaml.snakeyaml.parser.ParserException;
@@ -138,6 +140,7 @@
         parsedToscaYamlInfo.setInputs(getInputs(mappedToscaTemplate));
         parsedToscaYamlInfo.setInstances(getInstances(fileName, mappedToscaTemplate, createdNodesToscaResourceNames));
         parsedToscaYamlInfo.setGroups(getGroups(fileName, mappedToscaTemplate, component.getModel()));
+        parsedToscaYamlInfo.setDataTypes(getDataTypes(mappedToscaTemplate));
         if (component instanceof Resource) {
             parsedToscaYamlInfo.setPolicies(getPolicies(fileName, mappedToscaTemplate, component.getModel()));
         }
@@ -181,6 +184,26 @@
         return inputs;
     }
 
+    private Map<String, DataTypeDefinition> getDataTypes(final Map<String, Object> toscaJson) {
+        try {
+            final Map<String, DataTypeDefinition> dataTypes = ImportUtils.getDataTypes(toscaJson);
+
+            if (log.isDebugEnabled()) {
+                if (MapUtils.isEmpty(dataTypes)) {
+                    log.debug("No {} found.", ToscaTagNamesEnum.DATA_TYPES.getElementName());
+                } else {
+                    log.debug("{} found: {}", ToscaTagNamesEnum.DATA_TYPES.getElementName(), dataTypes.keySet());
+                }
+            }
+
+            return dataTypes;
+        } catch (final Exception ex) {
+            log.error("Unable to process datatypes", ex);
+        }
+
+        return Collections.emptyMap();
+    }
+
     private Map<String, PolicyDefinition> getPolicies(String fileName, Map<String, Object> toscaJson, String model) {
         Map<String, Object> foundPolicies = findFirstToscaMapElement(toscaJson, POLICIES).left().on(err -> logPoliciesNotFound(fileName));
         if (MapUtils.isNotEmpty(foundPolicies)) {
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/BaseBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/BaseBusinessLogic.java
index db03c72..717caad 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/BaseBusinessLogic.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/BaseBusinessLogic.java
@@ -421,7 +421,7 @@
     Either<Boolean, ResponseFormat> validatePropertyDefaultValue(IComplexDefaultValue property, Map<String, DataTypeDefinition> dataTypes) {
         String type;
         String innerType = null;
-        if (!propertyOperation.isPropertyTypeValid(property, null)) {
+        if (!propertyOperation.isPropertyTypeValid(property, null, dataTypes.values())) {
             log.info("Invalid type for property '{}' type '{}'", property.getName(), property.getType());
             ResponseFormat responseFormat = componentsUtils
                 .getResponseFormat(ActionStatus.INVALID_PROPERTY_TYPE, property.getType(), property.getName());
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/DataTypeBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/DataTypeBusinessLogic.java
index 4012228..0bd434c 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/DataTypeBusinessLogic.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/DataTypeBusinessLogic.java
@@ -21,31 +21,34 @@
 
 import fj.data.Either;
 import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.List;
+import java.util.Map;
 import java.util.Optional;
+import org.apache.commons.collections.MapUtils;
+import org.openecomp.sdc.be.components.impl.exceptions.DataTypeNotProvidedException;
 import org.openecomp.sdc.be.model.Component;
 import org.openecomp.sdc.be.model.ComponentParametersView;
 import org.openecomp.sdc.be.model.DataTypeDefinition;
-import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ArtifactsOperations;
-import org.openecomp.sdc.be.model.jsonjanusgraph.operations.InterfaceOperation;
-import org.openecomp.sdc.be.model.operations.api.IElementOperation;
-import org.openecomp.sdc.be.model.operations.api.IGroupInstanceOperation;
-import org.openecomp.sdc.be.model.operations.api.IGroupOperation;
-import org.openecomp.sdc.be.model.operations.api.IGroupTypeOperation;
+import org.openecomp.sdc.be.model.cache.ApplicationDataTypeCache;
+import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ToscaOperationFacade;
+import org.openecomp.sdc.be.model.operations.StorageException;
 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
-import org.openecomp.sdc.be.model.operations.impl.InterfaceLifecycleOperation;
+import org.openecomp.sdc.be.model.operations.impl.DataTypeOperation;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.util.CollectionUtils;
 
 @org.springframework.stereotype.Component("dataTypeBusinessLogic")
-public class DataTypeBusinessLogic extends BaseBusinessLogic {
+public class DataTypeBusinessLogic {
+
+    private final ToscaOperationFacade toscaOperationFacade;
+    private final DataTypeOperation dataTypeOperation;
 
     @Autowired
-    public DataTypeBusinessLogic(IElementOperation elementDao, IGroupOperation groupOperation, IGroupInstanceOperation groupInstanceOperation,
-                                 IGroupTypeOperation groupTypeOperation, InterfaceOperation interfaceOperation,
-                                 InterfaceLifecycleOperation interfaceLifecycleTypeOperation, ArtifactsOperations artifactToscaOperation) {
-        super(elementDao, groupOperation, groupInstanceOperation, groupTypeOperation, interfaceOperation, interfaceLifecycleTypeOperation,
-            artifactToscaOperation);
+    public DataTypeBusinessLogic(final ToscaOperationFacade toscaOperationFacade,
+                                 final DataTypeOperation dataTypeOperation) {
+        this.toscaOperationFacade = toscaOperationFacade;
+        this.dataTypeOperation = dataTypeOperation;
     }
 
     /**
@@ -139,4 +142,97 @@
         // return deleted data type if ok
         return Either.left(dataTypeResult.get());
     }
+
+    /**
+     * Associates a TOSCA data_type to a component.
+     *
+     * @param componentId the component id
+     * @param dataTypeMap a map of data_type name and the data_type representation to associate to the component
+     * @return the list of associated data_type
+     */
+    public List<DataTypeDefinition> addToComponent(final String componentId,
+                                                   final Map<String, DataTypeDefinition> dataTypeMap) {
+        final List<DataTypeDefinition> addedDataTypeList = new ArrayList<>();
+        final List<DataTypeDefinition> parsedDataTypeDefinitionList = parseToDataTypeDefinitionList(dataTypeMap);
+        for (final DataTypeDefinition dataTypeDefinition : parsedDataTypeDefinitionList) {
+            addedDataTypeList.add(addToComponent(componentId, dataTypeDefinition));
+        }
+
+        return addedDataTypeList;
+    }
+
+    /**
+     * Associates a data_type to a component. Creates the data_type if it does not exists.
+     *
+     * @param componentId the component id
+     * @param dataTypeDefinitionToAdd the data_type to add to the component
+     * @return the associated data_type
+     */
+    public DataTypeDefinition addToComponent(final String componentId, final DataTypeDefinition dataTypeDefinitionToAdd) {
+        DataTypeDefinition dataTypeDefinition = dataTypeOperation.findDataTypeByName(dataTypeDefinitionToAdd.getName())
+            .orElse(null);
+        if (dataTypeDefinition == null) {
+            dataTypeDefinition = dataTypeDefinitionToAdd;
+        }
+
+        final Map<String, DataTypeDefinition> dataTypesMap = new HashMap<>();
+        dataTypesMap.put(dataTypeDefinitionToAdd.getName(), dataTypeDefinition);
+
+        final Either<List<DataTypeDefinition>, StorageOperationStatus> operationResult =
+            toscaOperationFacade.addDataTypesToComponent(dataTypesMap, componentId);
+        if (operationResult.isRight()) {
+            final StorageOperationStatus storageOperationStatus = operationResult.right().value();
+            throw new StorageException(storageOperationStatus);
+        }
+
+        return dataTypeDefinition;
+    }
+
+    private List<DataTypeDefinition> parseToDataTypeDefinitionList(final Map<String, DataTypeDefinition> dataTypeMap) {
+        final List<DataTypeDefinition> dataTypeDefinitionList = new ArrayList<>();
+        dataTypeMap.forEach((key, dataTypeDefinition) -> {
+            dataTypeDefinition.setName(key);
+            dataTypeDefinitionList.add(dataTypeDefinition);
+        });
+
+        dataTypeDefinitionList.forEach(dataTypeDefinition -> loadParentHierarchy(dataTypeDefinition, dataTypeDefinitionList));
+
+        return dataTypeDefinitionList;
+    }
+
+    private void loadParentHierarchy(final DataTypeDefinition dataTypeDefinition,
+                                     final List<DataTypeDefinition> componentDataTypeList) {
+        if (dataTypeDefinition.getDerivedFrom() != null) {
+            return;
+        }
+        if (dataTypeDefinition.getDerivedFromName() == null) {
+            return;
+        }
+
+        DataTypeDefinition parentDataType =
+            dataTypeOperation.findDataTypeByName(dataTypeDefinition.getDerivedFromName()).orElse(null);
+        if (parentDataType != null) {
+            dataTypeDefinition.setDerivedFrom(parentDataType);
+            return;
+        }
+
+        parentDataType = componentDataTypeList.stream()
+            .filter(dataTypeDefinition1 -> dataTypeDefinition1.getName().equals(dataTypeDefinition.getDerivedFromName()))
+            .findFirst().orElse(null);
+        if (parentDataType == null) {
+            final String errorMsg =
+                String.format("Data type '%s' was not provided", dataTypeDefinition.getDerivedFromName());
+            throw new DataTypeNotProvidedException(errorMsg);
+        }
+        dataTypeDefinition.setDerivedFrom(parentDataType);
+        loadParentHierarchy(dataTypeDefinition.getDerivedFrom(), componentDataTypeList);
+    }
+
+    public void addToComponent(final Component component, final Map<String, DataTypeDefinition> dataTypes) {
+        if (MapUtils.isEmpty(dataTypes)) {
+            return;
+        }
+        parseToDataTypeDefinitionList(dataTypes).forEach(component::addToDataTypes);
+    }
+
 }
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ImportUtils.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ImportUtils.java
index f537267..100cd3b 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ImportUtils.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ImportUtils.java
@@ -44,6 +44,7 @@
 import org.apache.commons.lang3.StringEscapeUtils;
 import org.onap.sdc.tosca.datatypes.model.EntrySchema;
 import org.openecomp.sdc.be.components.impl.exceptions.ByActionStatusComponentException;
+import org.openecomp.sdc.be.components.impl.exceptions.ToscaElementException;
 import org.openecomp.sdc.be.config.BeEcompErrorManager;
 import org.openecomp.sdc.be.dao.api.ActionStatus;
 import org.openecomp.sdc.be.datatypes.elements.Annotation;
@@ -53,6 +54,7 @@
 import org.openecomp.sdc.be.impl.ComponentsUtils;
 import org.openecomp.sdc.be.model.AnnotationTypeDefinition;
 import org.openecomp.sdc.be.model.AttributeDefinition;
+import org.openecomp.sdc.be.model.DataTypeDefinition;
 import org.openecomp.sdc.be.model.HeatParameterDefinition;
 import org.openecomp.sdc.be.model.InputDefinition;
 import org.openecomp.sdc.be.model.LifecycleStateEnum;
@@ -516,6 +518,18 @@
         return getElements(toscaJson, TypeUtils.ToscaTagNamesEnum.INPUTS, ImportUtils::createInputs, ImportUtils::createModuleInput);
     }
 
+    public static Map<String, DataTypeDefinition> getDataTypes(final Map<String, Object> toscaJson) throws ToscaElementException {
+        final Either<Map<String, DataTypeDefinition>, ResultStatusEnum> elements =
+            getElements(toscaJson, ToscaTagNamesEnum.DATA_TYPES, ImportUtils::createDataType, ImportUtils::createDataTypeDefinitionAttribute);
+
+        if (elements.isRight()) {
+            throw new ToscaElementException(elements.right().value(),
+                String.format("Could not retrieve %s", ToscaTagNamesEnum.DATA_TYPES.getElementName()));
+        }
+
+        return elements.left().value();
+    }
+
     public static <T> Either<Map<String, T>, ResultStatusEnum> getElements(Map<String, Object> toscaJson, TypeUtils.ToscaTagNamesEnum elementTagName,
                                                                            Function<String, T> elementGenByName,
                                                                            Function<Map<String, Object>, T> func) {
@@ -569,6 +583,21 @@
         return annotation;
     }
 
+    private static DataTypeDefinition createDataTypeDefinitionAttribute(final Map<String, Object> attributeMap) {
+        final DataTypeDefinition dataType = new DataTypeDefinition();
+        setField(attributeMap, TypeUtils.ToscaTagNamesEnum.DESCRIPTION, dataType::setDescription);
+        setField(attributeMap, TypeUtils.ToscaTagNamesEnum.DERIVED_FROM, dataType::setDerivedFromName);
+        CommonImportManager.setProperties(attributeMap, dataType::setProperties);
+        return dataType;
+
+    }
+
+    private static DataTypeDefinition createDataType(final String dataTypeName) {
+        final DataTypeDefinition dataType = new DataTypeDefinition();
+        dataType.setName(dataTypeName);
+        return dataType;
+    }
+
     public static Either<List<HeatParameterDefinition>, ResultStatusEnum> getHeatParameters(Map<String, Object> heatData, String artifactType) {
         Either<List<HeatParameterDefinition>, ResultStatusEnum> eitherResult = Either.right(ResultStatusEnum.ELEMENT_NOT_FOUND);
         Either<Map<String, Object>, ResultStatusEnum> toscaProperties = findFirstToscaMapElement(heatData, TypeUtils.ToscaTagNamesEnum.PARAMETERS);
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogic.java
index 28faf73..caddc9b 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogic.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogic.java
@@ -572,6 +572,9 @@
         List<InputDefinition> resourceProperties = component.getInputs();
 
         final Map<String, DataTypeDefinition> dataTypes = componentsUtils.getAllDataTypes(applicationDataTypeCache, component.getModel());
+        if (CollectionUtils.isNotEmpty(component.getDataTypes())) {
+            component.getDataTypes().forEach(dataTypeDefinition -> dataTypes.put(dataTypeDefinition.getName(), dataTypeDefinition));
+        }
 
         for (Map.Entry<String, InputDefinition> inputDefinition : inputs.entrySet()) {
             String inputName = inputDefinition.getKey();
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogic.java
index 018deca..953278f 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogic.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogic.java
@@ -227,6 +227,7 @@
     private PropertyDataValueMergeBusinessLogic propertyDataValueMergeBusinessLogic;
     @Autowired
     private SoftwareInformationBusinessLogic softwareInformationBusinessLogic;
+    private final DataTypeBusinessLogic dataTypeBusinessLogic;
 
 
     @Autowired
@@ -247,7 +248,8 @@
                                  final ComponentValidator componentValidator, final ComponentIconValidator componentIconValidator,
                                  final ComponentProjectCodeValidator componentProjectCodeValidator,
                                  final ComponentDescriptionValidator componentDescriptionValidator, final PolicyBusinessLogic policyBusinessLogic,
-                                 final ModelBusinessLogic modelBusinessLogic) {
+                                 final ModelBusinessLogic modelBusinessLogic,
+                                 final DataTypeBusinessLogic dataTypeBusinessLogic) {
         super(elementDao, groupOperation, groupInstanceOperation, groupTypeOperation, groupBusinessLogic, interfaceOperation,
             interfaceLifecycleTypeOperation, artifactsBusinessLogic, artifactToscaOperation, componentContactIdValidator, componentNameValidator,
             componentTagsValidator, componentValidator, componentIconValidator, componentProjectCodeValidator, componentDescriptionValidator);
@@ -264,6 +266,7 @@
         this.propertyBusinessLogic = propertyBusinessLogic;
         this.policyBusinessLogic = policyBusinessLogic;
         this.modelBusinessLogic = modelBusinessLogic;
+        this.dataTypeBusinessLogic = dataTypeBusinessLogic;
     }
 
     static <T> Either<T, RuntimeException> rollbackWithEither(final JanusGraphDao janusGraphDao, final ActionStatus actionStatus,
@@ -1479,6 +1482,9 @@
                     parsedToscaYamlInfo.getSubstitutionMappingNodeType());
             } else {
                 final Resource genericResource = fetchAndSetDerivedFromGenericType(resource, null);
+                if (resource.getModel() == null) {
+                    dataTypeBusinessLogic.addToComponent(resource, parsedToscaYamlInfo.getDataTypes());
+                }
                 resource = createResourceTransaction(resource, csarInfo.getModifier(), isNormative);
                 log.trace("************* createResourceFromYaml after full create resource {}", yamlName);
                 log.trace("************* Going to add inputs from yaml {}", yamlName);
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceImportManager.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceImportManager.java
index 1503835..fbbd9fd 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceImportManager.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceImportManager.java
@@ -21,9 +21,7 @@
  */
 package org.openecomp.sdc.be.components.impl;
 
-import static org.openecomp.sdc.be.model.jsonjanusgraph.operations.ToscaElementOperation.createDataType;
-import static org.openecomp.sdc.be.model.jsonjanusgraph.operations.ToscaElementOperation.createDataTypeDefinitionWithName;
-
+import fj.data.Either;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.HashMap;
@@ -36,9 +34,7 @@
 import java.util.function.Function;
 import java.util.regex.Pattern;
 import java.util.stream.Collectors;
-
 import javax.servlet.ServletContext;
-
 import org.apache.commons.codec.binary.Base64;
 import org.apache.commons.collections4.MapUtils;
 import org.apache.commons.lang3.StringUtils;
@@ -79,6 +75,7 @@
 import org.openecomp.sdc.be.model.User;
 import org.openecomp.sdc.be.model.category.CategoryDefinition;
 import org.openecomp.sdc.be.model.category.SubCategoryDefinition;
+import org.openecomp.sdc.be.model.jsonjanusgraph.operations.NodeTypeOperation;
 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ToscaOperationFacade;
 import org.openecomp.sdc.be.model.operations.api.IGraphLockOperation;
 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
@@ -98,8 +95,6 @@
 import org.springframework.web.context.WebApplicationContext;
 import org.yaml.snakeyaml.Yaml;
 
-import fj.data.Either;
-
 @Component("resourceImportManager")
 public class ResourceImportManager {
 
@@ -116,13 +111,16 @@
     private IGraphLockOperation graphLockOperation;
     private ToscaOperationFacade toscaOperationFacade;
     private ResponseFormatManager responseFormatManager;
+    private final NodeTypeOperation nodeTypeOperation;
 
     @Autowired
     public ResourceImportManager(ComponentsUtils componentsUtils, CapabilityTypeOperation capabilityTypeOperation,
-                                 final InterfaceDefinitionHandler interfaceDefinitionHandler) {
+                                 final InterfaceDefinitionHandler interfaceDefinitionHandler,
+                                 final NodeTypeOperation nodeTypeOperation) {
         this.componentsUtils = componentsUtils;
         this.capabilityTypeOperation = capabilityTypeOperation;
         this.interfaceDefinitionHandler = interfaceDefinitionHandler;
+        this.nodeTypeOperation = nodeTypeOperation;
     }
 
     public ServiceBusinessLogic getServiceBusinessLogic() {
@@ -924,13 +922,13 @@
                 for (final Entry<String, Object> attributeNameValue : foundElements.entrySet()) {
                     final Object value = attributeNameValue.getValue();
                     if (value instanceof Map) {
-                        final DataTypeDefinition dataTypeDefinition = createDataTypeDefinitionWithName(attributeNameValue);
+                        final DataTypeDefinition dataTypeDefinition = nodeTypeOperation.createDataTypeDefinitionFromJson(attributeNameValue);
                         final DataTypeDefinition dataTypeDefinitionParent = dataTypeCacheAll.left().value()
                             .get(dataTypeDefinition.getDerivedFromName());
                         dataTypeDefinition.setDerivedFrom(dataTypeDefinitionParent);
                         dataTypeDefinitionList.add(dataTypeDefinition);
                     } else {
-                        dataTypeDefinitionList.add(createDataType(String.valueOf(value)));
+                        dataTypeDefinitionList.add(nodeTypeOperation.createDataType(String.valueOf(value)));
                     }
                 }
             }
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/exceptions/DataTypeNotProvidedException.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/exceptions/DataTypeNotProvidedException.java
new file mode 100644
index 0000000..eebb39a
--- /dev/null
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/exceptions/DataTypeNotProvidedException.java
@@ -0,0 +1,29 @@
+/*
+ * -
+ *  ============LICENSE_START=======================================================
+ *  Copyright (C) 2021 Nordix Foundation.
+ *  ================================================================================
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *       http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ *
+ *  SPDX-License-Identifier: Apache-2.0
+ *  ============LICENSE_END=========================================================
+ */
+
+package org.openecomp.sdc.be.components.impl.exceptions;
+
+public class DataTypeNotProvidedException extends RuntimeException {
+
+    public DataTypeNotProvidedException(final String s) {
+        super(s);
+    }
+}
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/exceptions/ToscaElementException.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/exceptions/ToscaElementException.java
new file mode 100644
index 0000000..d439a27
--- /dev/null
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/exceptions/ToscaElementException.java
@@ -0,0 +1,37 @@
+/*
+ * -
+ *  ============LICENSE_START=======================================================
+ *  Copyright (C) 2021 Nordix Foundation.
+ *  ================================================================================
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *       http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ *
+ *  SPDX-License-Identifier: Apache-2.0
+ *  ============LICENSE_END=========================================================
+ */
+
+package org.openecomp.sdc.be.components.impl.exceptions;
+
+import lombok.Getter;
+import org.openecomp.sdc.be.components.impl.ImportUtils.ResultStatusEnum;
+
+@Getter
+public class ToscaElementException extends Exception {
+
+    private final ResultStatusEnum resultStatus;
+
+    public ToscaElementException(ResultStatusEnum resultStatus, String msg) {
+        super(msg);
+        this.resultStatus = resultStatus;
+    }
+    
+}
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/impl/ComponentsUtils.java b/catalog-be/src/main/java/org/openecomp/sdc/be/impl/ComponentsUtils.java
index af05825..76c2206 100644
--- a/catalog-be/src/main/java/org/openecomp/sdc/be/impl/ComponentsUtils.java
+++ b/catalog-be/src/main/java/org/openecomp/sdc/be/impl/ComponentsUtils.java
@@ -32,6 +32,7 @@
 import java.lang.reflect.Type;
 import java.util.ArrayList;
 import java.util.Collections;
+import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
 import java.util.Optional;
@@ -1561,7 +1562,7 @@
                 throw new ByActionStatusComponentException(ActionStatus.GENERAL_ERROR);
             }
         }
-        return allDataTypes.left().value();
+        return new HashMap<>(allDataTypes.left().value());
     }
 
 }
diff --git a/catalog-be/src/test/java/org/openecomp/sdc/be/components/ResourceImportManagerTest.java b/catalog-be/src/test/java/org/openecomp/sdc/be/components/ResourceImportManagerTest.java
index 1609299..aa91b76 100644
--- a/catalog-be/src/test/java/org/openecomp/sdc/be/components/ResourceImportManagerTest.java
+++ b/catalog-be/src/test/java/org/openecomp/sdc/be/components/ResourceImportManagerTest.java
@@ -74,6 +74,7 @@
 import org.openecomp.sdc.be.model.Resource;
 import org.openecomp.sdc.be.model.UploadResourceInfo;
 import org.openecomp.sdc.be.model.User;
+import org.openecomp.sdc.be.model.jsonjanusgraph.operations.NodeTypeOperation;
 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ToscaOperationFacade;
 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
 import org.openecomp.sdc.be.model.operations.impl.CapabilityTypeOperation;
@@ -102,13 +103,14 @@
 
     static UserBusinessLogic userAdmin = Mockito.mock(UserBusinessLogic.class);
     static ToscaOperationFacade toscaOperationFacade =  Mockito.mock(ToscaOperationFacade.class);
+    static NodeTypeOperation nodeTypeOperation =  Mockito.mock(NodeTypeOperation.class);
 
     protected static final ComponentsUtils componentsUtils = Mockito.mock(ComponentsUtils.class);
     private static final CapabilityTypeOperation capabilityTypeOperation = Mockito.mock(CapabilityTypeOperation.class);
 
     @BeforeAll
     public static void beforeClass() {
-        importManager = new ResourceImportManager(componentsUtils, capabilityTypeOperation, interfaceDefinitionHandler);
+        importManager = new ResourceImportManager(componentsUtils, capabilityTypeOperation, interfaceDefinitionHandler, nodeTypeOperation);
         importManager.setAuditingManager(auditingManager);
         when(toscaOperationFacade.getLatestByToscaResourceName(Mockito.anyString(), Mockito.any())).thenReturn(Either.left(null));
         when(toscaOperationFacade.getLatestByToscaResourceNameAndModel(Mockito.anyString(), Mockito.any())).thenReturn(Either.left(null));
diff --git a/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/DataTypeBusinessLogicTest.java b/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/DataTypeBusinessLogicTest.java
index cc05eaf..fb87c92 100644
--- a/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/DataTypeBusinessLogicTest.java
+++ b/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/DataTypeBusinessLogicTest.java
@@ -20,15 +20,35 @@
 
 package org.openecomp.sdc.be.components.impl;
 
+import static org.hamcrest.CoreMatchers.is;
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.containsInAnyOrder;
+import static org.hamcrest.Matchers.empty;
+import static org.hamcrest.Matchers.not;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertThrows;
+import static org.junit.Assert.assertTrue;
+import static org.mockito.ArgumentMatchers.argThat;
+import static org.mockito.ArgumentMatchers.eq;
+import static org.mockito.Mockito.when;
+
+import com.google.common.collect.ImmutableMap;
 import fj.data.Either;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Optional;
+import java.util.function.BiFunction;
 import org.junit.Before;
 import org.junit.Test;
 import org.mockito.InjectMocks;
 import org.mockito.Mock;
 import org.mockito.Mockito;
 import org.mockito.MockitoAnnotations;
+import org.openecomp.sdc.be.components.impl.exceptions.DataTypeNotProvidedException;
 import org.openecomp.sdc.be.components.validation.UserValidations;
-import org.openecomp.sdc.be.impl.ComponentsUtils;
 import org.openecomp.sdc.be.model.ComponentInstance;
 import org.openecomp.sdc.be.model.ComponentInstanceInput;
 import org.openecomp.sdc.be.model.ComponentParametersView;
@@ -36,21 +56,12 @@
 import org.openecomp.sdc.be.model.Service;
 import org.openecomp.sdc.be.model.User;
 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ToscaOperationFacade;
+import org.openecomp.sdc.be.model.operations.StorageException;
 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
+import org.openecomp.sdc.be.model.operations.impl.DataTypeOperation;
 import org.openecomp.sdc.be.model.tosca.ToscaPropertyType;
 import org.openecomp.sdc.be.user.UserBusinessLogic;
 
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.ArgumentMatchers.eq;
-import static org.mockito.Mockito.when;
-
 public class DataTypeBusinessLogicTest {
 
     private static final String COMPONENT_INSTANCE_ID = "instanceId";
@@ -60,9 +71,6 @@
     private static final String DATATYPE_NAME = "org.onap.datatypes.mytype";
 
     @Mock
-    private ComponentsUtils componentsUtilsMock;
-
-    @Mock
     private UserBusinessLogic userAdminMock;
 
     @Mock
@@ -72,19 +80,16 @@
     private UserValidations userValidations;
 
     @Mock
-    private ComponentInstanceBusinessLogic componentInstanceBusinessLogic;
+    private DataTypeOperation dataTypeOperation;
 
     @InjectMocks
-    private DataTypeBusinessLogic testInstance;
+    private DataTypeBusinessLogic dataTypeBusinessLogic;
 
     private Service service;
 
     @Before
     public void setUp() throws Exception {
-        MockitoAnnotations.initMocks(this);
-
-        testInstance.setToscaOperationFacade(toscaOperationFacadeMock);
-
+        MockitoAnnotations.openMocks(this);
         service = new Service();
         service.setUniqueId(COMPONENT_INSTANCE_ID);
         ComponentInstance componentInstance = new ComponentInstance();
@@ -102,7 +107,7 @@
         instanceInputMap.put(COMPONENT_INSTANCE_ID, Collections.singletonList(componentInstanceInput));
         instanceInputMap.put("someInputId", Collections.singletonList(new ComponentInstanceInput()));
         service.setComponentInstancesInputs(instanceInputMap);
-        when(userValidations.validateUserExists(eq(USER_ID))).thenReturn(new User());
+        when(userValidations.validateUserExists(USER_ID)).thenReturn(new User());
         when(userAdminMock.getUser(USER_ID, false)).thenReturn(new User());
     }
 
@@ -110,7 +115,7 @@
     public void test_getPrivateDataTypes() throws Exception {
         setMockitoWhenGetToscaElementCalled();
 
-        Either<List<DataTypeDefinition>, StorageOperationStatus> result = testInstance.getPrivateDataTypes(COMPONENT_ID);
+        Either<List<DataTypeDefinition>, StorageOperationStatus> result = dataTypeBusinessLogic.getPrivateDataTypes(COMPONENT_ID);
         assertTrue(result.isLeft());
         List<DataTypeDefinition> dataTypes = result.left().value();
         assertEquals(service.getDataTypes(), dataTypes);
@@ -121,7 +126,7 @@
         setMockitoWhenGetToscaElementCalled();
 
         Either<DataTypeDefinition, StorageOperationStatus> result =
-            testInstance.getPrivateDataType(COMPONENT_ID, DATATYPE_NAME);
+            dataTypeBusinessLogic.getPrivateDataType(COMPONENT_ID, DATATYPE_NAME);
         assertTrue(result.isLeft());
         DataTypeDefinition dataType = result.left().value();
         assertEquals(service.getDataTypes().get(0), dataType);
@@ -134,7 +139,7 @@
             .thenReturn(StorageOperationStatus.OK);
 
         Either<DataTypeDefinition, StorageOperationStatus> result =
-            testInstance.deletePrivateDataType(COMPONENT_ID, DATATYPE_NAME);
+            dataTypeBusinessLogic.deletePrivateDataType(COMPONENT_ID, DATATYPE_NAME);
         assertTrue(result.isLeft());
         DataTypeDefinition dataType = result.left().value();
         assertEquals(service.getDataTypes().get(0), dataType);
@@ -146,7 +151,7 @@
             .thenReturn(StorageOperationStatus.OK);
 
         Either<DataTypeDefinition, StorageOperationStatus> result =
-            testInstance.deletePrivateDataType(service, DATATYPE_NAME);
+            dataTypeBusinessLogic.deletePrivateDataType(service, DATATYPE_NAME);
         assertTrue(result.isLeft());
         DataTypeDefinition dataType = result.left().value();
         assertEquals(service.getDataTypes().get(0), dataType);
@@ -156,4 +161,88 @@
         when(toscaOperationFacadeMock.getToscaElement(eq(COMPONENT_ID), Mockito.any(ComponentParametersView.class)))
                 .thenReturn(Either.left(service));
     }
+
+    @Test
+    public void testAddToComponent() {
+        //given
+        final DataTypeDefinition dataTypeDefinition1 =
+            createDataTypeDefinition("data.type.1", ToscaPropertyType.ROOT.getType());
+        final DataTypeDefinition dataTypeDefinition2 =
+            createDataTypeDefinition("data.type.2", ToscaPropertyType.ROOT.getType());
+        final DataTypeDefinition dataTypeDefinition3 =
+            createDataTypeDefinition("data.type.child", dataTypeDefinition2.getName());
+
+        final DataTypeDefinition dataTypeDefinitionRoot =
+            createDataTypeDefinition(ToscaPropertyType.ROOT.getType(), null);
+
+
+        final List<DataTypeDefinition> expectedDataTypeDefinitionList
+            = Arrays.asList(dataTypeDefinition1, dataTypeDefinition2, dataTypeDefinition3);
+
+        final ImmutableMap<String, DataTypeDefinition> dataTypeDefinitionMap =
+            ImmutableMap.of(dataTypeDefinition1.getName(), dataTypeDefinition1,
+                dataTypeDefinition2.getName(), dataTypeDefinition2,
+                dataTypeDefinition3.getName(), dataTypeDefinition3);
+
+        when(dataTypeOperation.findDataTypeByName(ToscaPropertyType.ROOT.getType()))
+            .thenReturn(Optional.of(dataTypeDefinitionRoot));
+        when(dataTypeOperation.findDataTypeByName(dataTypeDefinition1.getName())).thenReturn(Optional.of(dataTypeDefinition1));
+        when(dataTypeOperation.findDataTypeByName(dataTypeDefinition2.getName())).thenReturn(Optional.empty());
+        when(dataTypeOperation.findDataTypeByName(dataTypeDefinition3.getName())).thenReturn(Optional.empty());
+        final BiFunction<Map<String, DataTypeDefinition>, DataTypeDefinition, Boolean> keyMatcher =
+            (argument, dataTypeDefinition) -> argument != null && argument.containsKey(dataTypeDefinition.getName());
+        final String serviceId = service.getUniqueId();
+        when(toscaOperationFacadeMock
+            .addDataTypesToComponent(argThat(map -> keyMatcher.apply(map, dataTypeDefinition1)),
+                eq(serviceId)))
+            .thenReturn(Either.left(Collections.singletonList(dataTypeDefinition1)));
+        when(toscaOperationFacadeMock
+            .addDataTypesToComponent(argThat(map -> keyMatcher.apply(map, dataTypeDefinition2)),
+                eq(serviceId)))
+            .thenReturn(Either.left(Collections.singletonList(dataTypeDefinition2)));
+        when(toscaOperationFacadeMock
+            .addDataTypesToComponent(argThat(map -> keyMatcher.apply(map, dataTypeDefinition3)),
+                eq(serviceId)))
+            .thenReturn(Either.left(Collections.singletonList(dataTypeDefinition3)));
+        //when
+        final List<DataTypeDefinition> actualDataTypeDefinitionList =
+            dataTypeBusinessLogic.addToComponent(serviceId, dataTypeDefinitionMap);
+
+        //then
+        assertThat("Result should not be empty", actualDataTypeDefinitionList, is(not(empty())));
+        assertThat("Result should contains expected data type definitions",
+            actualDataTypeDefinitionList, containsInAnyOrder(expectedDataTypeDefinitionList.toArray()));
+
+        //given
+        when(toscaOperationFacadeMock
+            .addDataTypesToComponent(argThat(map -> keyMatcher.apply(map, dataTypeDefinition2)),
+                eq(serviceId)))
+            .thenReturn(Either.right(StorageOperationStatus.GENERAL_ERROR));
+        //then
+        assertThrows(StorageException.class, () -> dataTypeBusinessLogic.addToComponent(serviceId, dataTypeDefinitionMap));
+    }
+
+    @Test
+    public void testAddToComponentDataTypeNotProvidedException() {
+        //given
+        final DataTypeDefinition dataTypeDefinition =
+            createDataTypeDefinition("data.type.child", "not.provided.data.type");
+        final ImmutableMap<String, DataTypeDefinition> dataTypeDefinitionMap =
+            ImmutableMap.of(dataTypeDefinition.getName(), dataTypeDefinition);
+
+        //when
+        when(dataTypeOperation.findDataTypeByName(dataTypeDefinition.getName())).thenReturn(Optional.empty());
+        //then
+        final String uniqueId = service.getUniqueId();
+        assertThrows(DataTypeNotProvidedException.class, () -> dataTypeBusinessLogic.addToComponent(uniqueId, dataTypeDefinitionMap));
+    }
+
+    private DataTypeDefinition createDataTypeDefinition(final String name, final String derivedFrom) {
+        DataTypeDefinition dataType = new DataTypeDefinition();
+        dataType.setName(name);
+        dataType.setDerivedFromName(derivedFrom);
+        return dataType;
+    }
+
+
 }
diff --git a/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogicTest.java b/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogicTest.java
index 9700a86..5ee8ff1 100644
--- a/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogicTest.java
+++ b/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogicTest.java
@@ -468,7 +468,7 @@
         // for BaseOperation.getAllDataTypes:
         when(applicationDataTypeCache.getAll(null)).thenReturn(Either.left(new HashMap<>())); // don't use Collections.emptyMap
         // for BaseOperation.validatePropertyDefaultValue:
-        when(propertyOperation.isPropertyTypeValid(any(), any())).thenReturn(true);
+        when(propertyOperation.isPropertyTypeValid(any(), any(), any())).thenReturn(true);
         when(propertyOperation.isPropertyInnerTypeValid(any(),any())).thenReturn(new ImmutablePair<>(listInput.getSchemaType(), true));
         when(propertyOperation.isPropertyDefaultValueValid(any(), any())).thenReturn(true);
         // for createListInputsInGraph:
@@ -555,7 +555,7 @@
     }
 
     @Test
-    public void test_createListInput_fail_prepareAndValidateInput() throws Exception {
+    public void test_createListInput_fail_prepareAndValidateInput() {
         ComponentInstListInput createListInputParams = setUpCreateListInputParams();
         ComponentInstInputsMap componentInstInputsMap = createListInputParams.getComponentInstInputsMap();
         InputDefinition listInput = createListInputParams.getListInput();
@@ -566,12 +566,12 @@
         when(propertyDeclarationOrchestrator.getPropOwnerId(componentInstInputsMap)).thenReturn(COMPONENT_INSTANCE_ID);
         when(applicationDataTypeCache.getAll(null)).thenReturn(Either.left(new HashMap<>())); // don't use Collections.emptyMap
         // for BaseOperation.validatePropertyDefaultValue:
-        when(propertyOperation.isPropertyTypeValid(any(), any())).thenReturn(false);
+        when(propertyOperation.isPropertyTypeValid(any(), any(), any())).thenReturn(false);
 
         Either<List<InputDefinition>, ResponseFormat> result =
                 testInstance.createListInput(USER_ID, COMPONENT_ID, ComponentTypeEnum.SERVICE, createListInputParams, true, false);
         assertThat(result.isRight()).isTrue();
-        verify(propertyOperation, times(1)).isPropertyTypeValid(any(), any());
+        verify(propertyOperation, times(1)).isPropertyTypeValid(any(), any(), any());
     }
 
     @Test
@@ -586,7 +586,7 @@
         when(propertyDeclarationOrchestrator.getPropOwnerId(componentInstInputsMap)).thenReturn(COMPONENT_INSTANCE_ID);
         when(applicationDataTypeCache.getAll(null)).thenReturn(Either.left(new HashMap<>())); // don't use Collections.emptyMap
         // for BaseOperation.validatePropertyDefaultValue:
-        when(propertyOperation.isPropertyTypeValid(any(), any())).thenReturn(true);
+        when(propertyOperation.isPropertyTypeValid(any(), any(), any())).thenReturn(true);
         when(propertyOperation.isPropertyInnerTypeValid(any(),any())).thenReturn(new ImmutablePair<>(listInput.getSchemaType(), true));
         when(propertyOperation.isPropertyDefaultValueValid(any(), any())).thenReturn(true);
         when(toscaOperationFacadeMock.addInputsToComponent(anyMap(), eq(COMPONENT_ID))).thenReturn(Either.right(StorageOperationStatus.NOT_FOUND));
diff --git a/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogicTest.java b/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogicTest.java
index 2f4239f..0ccb2ec 100644
--- a/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogicTest.java
+++ b/catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogicTest.java
@@ -209,6 +209,7 @@
 	private final UiComponentDataConverter uiComponentDataConverter = Mockito.mock(UiComponentDataConverter.class);
 	private final ToscaExportHandler toscaExportHandler = Mockito.mock(ToscaExportHandler.class);
 	private final PolicyBusinessLogic policyBusinessLogic = Mockito.mock(PolicyBusinessLogic.class);
+	private final DataTypeBusinessLogic dataTypeBusinessLogic = Mockito.mock(DataTypeBusinessLogic.class);
 
 	private YamlTemplateParsingHandler yamlTemplateParsingHandler = Mockito.mock(YamlTemplateParsingHandler.class);
 	@InjectMocks
@@ -315,7 +316,7 @@
 				csarArtifactsAndGroupsBusinessLogic, mergeInstanceUtils, uiComponentDataConverter, csarBusinessLogic,
 				artifactToscaOperation, propertyBusinessLogic, componentContactIdValidator, componentNameValidator,
 				componentTagsValidator, componentValidator,	componentIconValidator, componentProjectCodeValidator,
-				componentDescriptionValidator, policyBusinessLogic, modelBusinessLogic);
+				componentDescriptionValidator, policyBusinessLogic, modelBusinessLogic, dataTypeBusinessLogic);
 		bl.setElementDao(mockElementDao);
 		bl.setUserAdmin(mockUserAdmin);
 		bl.setCapabilityTypeOperation(capabilityTypeOperation);
diff --git a/catalog-be/src/test/java/org/openecomp/sdc/be/components/lifecycle/CheckoutTest.java b/catalog-be/src/test/java/org/openecomp/sdc/be/components/lifecycle/CheckoutTest.java
index 46040ca..5ce34e3 100644
--- a/catalog-be/src/test/java/org/openecomp/sdc/be/components/lifecycle/CheckoutTest.java
+++ b/catalog-be/src/test/java/org/openecomp/sdc/be/components/lifecycle/CheckoutTest.java
@@ -29,6 +29,7 @@
 import org.openecomp.sdc.be.components.csar.CsarBusinessLogic;
 import org.openecomp.sdc.be.components.impl.ComponentInstanceBusinessLogic;
 import org.openecomp.sdc.be.components.impl.CompositionBusinessLogic;
+import org.openecomp.sdc.be.components.impl.DataTypeBusinessLogic;
 import org.openecomp.sdc.be.components.impl.InputsBusinessLogic;
 import org.openecomp.sdc.be.components.impl.ModelBusinessLogic;
 import org.openecomp.sdc.be.components.impl.OutputsBusinessLogic;
@@ -70,6 +71,7 @@
     private final ComponentNameValidator componentNameValidator = new ComponentNameValidator(componentsUtils, toscaOperationFacade);
     private final PolicyBusinessLogic policyBusinessLogic = Mockito.mock(PolicyBusinessLogic.class);
     private final ModelBusinessLogic modelBusinessLogic = Mockito.mock(ModelBusinessLogic.class);
+    private final DataTypeBusinessLogic dataTypeBusinessLogic = Mockito.mock(DataTypeBusinessLogic.class);
     @InjectMocks
     ResourceBusinessLogic bl = new ResourceBusinessLogic(elementDao, groupOperation, groupInstanceOperation, groupTypeOperation,
         groupBusinessLogic, interfaceOperation, interfaceLifecycleTypeOperation, artifactsBusinessLogic,
@@ -77,7 +79,8 @@
         resourceDataMergeBusinessLogic, csarArtifactsAndGroupsBusinessLogic, mergeInstanceUtils,
         uiComponentDataConverter, csarBusinessLogic, artifactToscaOperation, propertyBusinessLogic,
         componentContactIdValidator, componentNameValidator, componentTagsValidator, componentValidator,
-            componentIconValidator, componentProjectCodeValidator, componentDescriptionValidator ,policyBusinessLogic, modelBusinessLogic);
+        componentIconValidator, componentProjectCodeValidator, componentDescriptionValidator ,policyBusinessLogic, modelBusinessLogic,
+        dataTypeBusinessLogic);
 
     @Before
     public void setup() {
diff --git a/catalog-be/src/test/java/org/openecomp/sdc/be/servlets/ArchiveEndpointTest.java b/catalog-be/src/test/java/org/openecomp/sdc/be/servlets/ArchiveEndpointTest.java
index 18cdb42..3b3bed1 100644
--- a/catalog-be/src/test/java/org/openecomp/sdc/be/servlets/ArchiveEndpointTest.java
+++ b/catalog-be/src/test/java/org/openecomp/sdc/be/servlets/ArchiveEndpointTest.java
@@ -82,6 +82,8 @@
 import org.openecomp.sdc.be.model.LifecycleStateEnum;
 import org.openecomp.sdc.be.model.User;
 import org.openecomp.sdc.be.model.catalog.CatalogComponent;
+import org.openecomp.sdc.be.model.converter.PropertyDataConverter;
+import org.openecomp.sdc.be.model.converter.SchemaDefinitionConverter;
 import org.openecomp.sdc.be.model.jsonjanusgraph.config.ContainerInstanceTypesData;
 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ArchiveOperation;
 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.CategoryOperation;
@@ -267,6 +269,16 @@
             return new ModelOperation(null, null, null, null);
         }
 
+        @Bean
+        PropertyDataConverter propertyDataConverter() {
+            return new PropertyDataConverter();
+        }
+
+        @Bean
+        SchemaDefinitionConverter schemaDefinitionConverter() {
+            return new SchemaDefinitionConverter();
+        }
+
         private void initGraphForTest() {
             //Create Catalog Root
             catalogVertex = GraphTestUtils.createRootCatalogVertex(janusGraphDao);
diff --git a/catalog-be/src/test/resources/paths/path-context.xml b/catalog-be/src/test/resources/paths/path-context.xml
index 752e4ec..500033e 100644
--- a/catalog-be/src/test/resources/paths/path-context.xml
+++ b/catalog-be/src/test/resources/paths/path-context.xml
@@ -58,7 +58,8 @@
 		org.openecomp.sdc.be.components.csar,
 		org.openecomp.sdc.be.datamodel.utils,
 		org.openecomp.sdc.be.model.utils,
-		org.openecomp.sdc.be.dao.jsongraph">
+		org.openecomp.sdc.be.dao.jsongraph,
+		org.openecomp.sdc.be.model.converter">
 
     </context:component-scan>
     <bean id="tosca-operation-facade"
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/config/CatalogModelSpringConfig.java b/catalog-model/src/main/java/org/openecomp/sdc/be/config/CatalogModelSpringConfig.java
index 1991438..1d3975e 100644
--- a/catalog-model/src/main/java/org/openecomp/sdc/be/config/CatalogModelSpringConfig.java
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/config/CatalogModelSpringConfig.java
@@ -26,15 +26,14 @@
 
 @Configuration
 @ComponentScan({
-    // @formatter:off
     "org.openecomp.sdc.be.model.operations.impl",
     "org.openecomp.sdc.be.model.cache",
     "org.openecomp.sdc.be.client",
+    "org.openecomp.sdc.be.model.converter",
     "org.openecomp.sdc.be.model.jsonjanusgraph.utils",
     "org.openecomp.sdc.be.model.jsonjanusgraph.operations",
     "org.openecomp.sdc.be.model.jsonjanusgraph.config",
     "org.openecomp.sdc.be.dao.cassandra"})
-// @formatter:on
 public class CatalogModelSpringConfig {
 
     @Bean
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/Component.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/Component.java
index e0ca719..55ccc81 100644
--- a/catalog-model/src/main/java/org/openecomp/sdc/be/model/Component.java
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/Component.java
@@ -714,4 +714,26 @@
         componentMetadata.put(ILogConfiguration.MDC_SUPPORTABLITY_CSAR_VERSION, this.getCsarVersion());
         return componentMetadata;
     }
+
+    /**
+     * Adds a list of data type definition to the internal data type list.
+     *
+     * @param dataTypeDefinitionList the list of data type definition to be added
+     */
+    public void addToDataTypes(final List<DataTypeDefinition> dataTypeDefinitionList) {
+        dataTypeDefinitionList.forEach(this::addToDataTypes);
+    }
+
+    /**
+     * Add a data type to the list of data types. Initializes the list if not yet initialized.
+     *
+     * @param dataTypeDefinition the data type definition to add
+     */
+    public void addToDataTypes(final DataTypeDefinition dataTypeDefinition) {
+        if (dataTypes == null) {
+            dataTypes = new ArrayList<>();
+        }
+        dataTypes.add(dataTypeDefinition);
+    }
+
 }
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/ParsedToscaYamlInfo.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/ParsedToscaYamlInfo.java
index ce7c6de..e11cf24 100644
--- a/catalog-model/src/main/java/org/openecomp/sdc/be/model/ParsedToscaYamlInfo.java
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/ParsedToscaYamlInfo.java
@@ -19,6 +19,7 @@
  */
 package org.openecomp.sdc.be.model;
 
+import java.util.HashMap;
 import java.util.Map;
 import lombok.Getter;
 import lombok.Setter;
@@ -29,9 +30,12 @@
 @Setter
 public class ParsedToscaYamlInfo {
 
-    Map<String, InputDefinition> inputs;
-    Map<String, UploadComponentInstanceInfo> instances;
-    Map<String, GroupDefinition> groups;
-    Map<String, PolicyDefinition> policies;
-    String substitutionMappingNodeType;
+    private Map<String, InputDefinition> inputs;
+    private Map<String, UploadComponentInstanceInfo> instances;
+    private Map<String, GroupDefinition> groups;
+    private Map<String, PolicyDefinition> policies;
+    private Map<String, DataTypeDefinition> dataTypes = new HashMap<>();
+    private String substitutionMappingNodeType;
+
 }
+
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/converter/PropertyDataConverter.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/converter/PropertyDataConverter.java
new file mode 100644
index 0000000..7028ea1
--- /dev/null
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/converter/PropertyDataConverter.java
@@ -0,0 +1,149 @@
+/*
+ * -
+ *  ============LICENSE_START=======================================================
+ *  Copyright (C) 2021 Nordix Foundation.
+ *  ================================================================================
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *       http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ *
+ *  SPDX-License-Identifier: Apache-2.0
+ *  ============LICENSE_END=========================================================
+ */
+
+package org.openecomp.sdc.be.model.converter;
+
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.DEFAULT_VALUE;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.DEFINITION;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.DESCRIPTION;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.HIDDEN;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.IMMUTABLE;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.INPUT_ID;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.INPUT_PATH;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.INSTANCE_UNIQUE_ID;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.LABEL;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.NAME;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PARENT_PROPERTY_TYPE;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PASSWORD;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PROPERTY_CONSTRAINTS;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PROPERTY_ID;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.REQUIRED;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.SCHEMA;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.STATUS;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.SUB_PROPERTY_INPUT_PATH;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.TYPE;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.UNIQUE_ID;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.VALUE;
+
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+import java.util.function.Consumer;
+import java.util.stream.Collectors;
+import org.apache.commons.collections.CollectionUtils;
+import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
+import org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Component;
+
+/**
+ * Converter to create {@link PropertyDataDefinition} instances from other data sources.
+ */
+@Component("propertyDataConverter")
+public class PropertyDataConverter {
+
+    private SchemaDefinitionConverter schemaDefinitionConverter;
+
+    /**
+     * Parses all property data JSON entry map the given list to {@link PropertyDataDefinition}.
+     *
+     * @param propertiesDataList the list of property data JSON entry map
+     * @return a list with all property data JSON entry map parsed as a PropertyDataDefinition
+     */
+    public List<PropertyDataDefinition> parseProperties(final List<Map<String, Object>> propertiesDataList) {
+        if (CollectionUtils.isEmpty(propertiesDataList)) {
+            return Collections.emptyList();
+        }
+
+        return propertiesDataList.stream()
+            .map(this::createPropertyData)
+            .collect(Collectors.toList());
+    }
+
+    /**
+     * Creates a {@link PropertyDataDefinition} from JSON entry map.
+     *
+     * @param propertyToscaMap the JSON entry map representing a {@link PropertyDataDefinition}
+     * @return a new instance of {@link PropertyDataDefinition}
+     */
+    public PropertyDataDefinition createPropertyData(final Map<String, Object> propertyToscaMap) {
+        final PropertyDataDefinition propertyData = new PropertyDataDefinition();
+        setPropertyValue(UNIQUE_ID, String.class, propertyToscaMap, propertyData::setUniqueId);
+        setPropertyValue(TYPE, String.class, propertyToscaMap, propertyData::setType);
+        setPropertyValue(REQUIRED, Boolean.class, propertyToscaMap, propertyData::setRequired);
+        setPropertyValue(NAME, String.class, propertyToscaMap, propertyData::setName);
+        setPropertyValue(VALUE, String.class, propertyToscaMap, propertyData::setValue);
+        setPropertyValue(LABEL, String.class, propertyToscaMap, propertyData::setLabel);
+        setPropertyValue(HIDDEN, Boolean.class, propertyToscaMap, propertyData::setHidden);
+        setPropertyValue(IMMUTABLE, Boolean.class, propertyToscaMap, propertyData::setImmutable);
+        setPropertyValue(PASSWORD, Boolean.class, propertyToscaMap, propertyData::setPassword);
+        setPropertyValue(DEFINITION, Boolean.class, propertyToscaMap, propertyData::setDefinition);
+        setPropertyValue(DESCRIPTION, String.class, propertyToscaMap, propertyData::setDescription);
+        setPropertyValue(DEFAULT_VALUE, String.class, propertyToscaMap, propertyData::setDefaultValue);
+        setPropertyValue(INPUT_PATH, String.class, propertyToscaMap, propertyData::setInputPath);
+        setPropertyValue(STATUS, String.class, propertyToscaMap, propertyData::setStatus);
+        setPropertyValue(INPUT_ID, String.class, propertyToscaMap, propertyData::setInputId);
+        setPropertyValue(INSTANCE_UNIQUE_ID, String.class, propertyToscaMap, propertyData::setInstanceUniqueId);
+        setPropertyValue(PROPERTY_ID, String.class, propertyToscaMap, propertyData::setPropertyId);
+        setPropertyValue(PARENT_PROPERTY_TYPE, String.class, propertyToscaMap, propertyData::setParentPropertyType);
+        setPropertyValue(SUB_PROPERTY_INPUT_PATH,
+            String.class, propertyToscaMap, propertyData::setSubPropertyInputPath);
+        setSchema(propertyToscaMap, propertyData);
+        setPropertyConstraints(propertyToscaMap, propertyData);
+
+        return propertyData;
+    }
+
+    private <T> void setPropertyValue(final JsonPresentationFields propertyField, final Class<T> propertyClass,
+                                      final Map<String, Object> propertyToscaMap, final Consumer<T> setter) {
+        final Object valueObj = propertyToscaMap.get(propertyField.getPresentation());
+        if (propertyClass.isInstance(valueObj)) {
+            setter.accept((T) valueObj);
+        }
+    }
+
+    private void setPropertyConstraints(final Map<String, Object> propertyValue,
+                                        final PropertyDataDefinition property) {
+        final String propertyConstraintsEntry = PROPERTY_CONSTRAINTS.getPresentation();
+        if (!propertyValue.containsKey(propertyConstraintsEntry)) {
+            return;
+        }
+        final Object constraintListObj = propertyValue.get(propertyConstraintsEntry);
+        if (constraintListObj instanceof List) {
+            property.setPropertyConstraints((List<String>) constraintListObj);
+        }
+    }
+
+    private void setSchema(final Map<String, Object> propertyValue, final PropertyDataDefinition propertyDefinition) {
+        final Object schemaObj = propertyValue.get(SCHEMA.getPresentation());
+        if (schemaObj == null) {
+            return;
+        }
+        schemaDefinitionConverter.parseTo(schemaObj).ifPresent(propertyDefinition::setSchema);
+    }
+
+    //circular dependency
+    @Autowired
+    public void setSchemaDefinitionConverter(final SchemaDefinitionConverter schemaDefinitionConverter) {
+        this.schemaDefinitionConverter = schemaDefinitionConverter;
+    }
+
+}
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/converter/SchemaDefinitionConverter.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/converter/SchemaDefinitionConverter.java
new file mode 100644
index 0000000..0275c6f
--- /dev/null
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/converter/SchemaDefinitionConverter.java
@@ -0,0 +1,64 @@
+/*
+ * -
+ *  ============LICENSE_START=======================================================
+ *  Copyright (C) 2021 Nordix Foundation.
+ *  ================================================================================
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *       http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ *
+ *  SPDX-License-Identifier: Apache-2.0
+ *  ============LICENSE_END=========================================================
+ */
+
+package org.openecomp.sdc.be.model.converter;
+
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PROPERTY;
+
+import java.util.Map;
+import java.util.Optional;
+import org.openecomp.sdc.be.datatypes.elements.SchemaDefinition;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Component;
+
+/**
+ * Converter to create {@link SchemaDefinition} instances from other data sources.
+ */
+@Component("schemaDefinitionConverter")
+public class SchemaDefinitionConverter {
+
+    private PropertyDataConverter propertyDataConverter;
+
+    /**
+     * Parses a json object as map to a {@link SchemaDefinition} instance.
+     *
+     * @param schemaJsonAsMapObj the json map representing the {@link SchemaDefinition}
+     * @return an instance of {@link SchemaDefinition}
+     */
+    public Optional<SchemaDefinition> parseTo(final Object schemaJsonAsMapObj) {
+        if (schemaJsonAsMapObj instanceof Map) {
+            final Map<String, Object> schemaMap = (Map<String, Object>) schemaJsonAsMapObj;
+            final Object schemaPropertyObj = schemaMap.get(PROPERTY.getPresentation());
+            if (schemaPropertyObj instanceof Map) {
+                final SchemaDefinition schema = new SchemaDefinition();
+                schema.setProperty(propertyDataConverter.createPropertyData((Map<String, Object>) schemaPropertyObj));
+                return Optional.of(schema);
+            }
+        }
+        return Optional.empty();
+    }
+
+    //circular dependency
+    @Autowired
+    public void setPropertyDataConverter(final PropertyDataConverter propertyDataConverter) {
+        this.propertyDataConverter = propertyDataConverter;
+    }
+}
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/TopologyTemplateOperation.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/TopologyTemplateOperation.java
index 78aa4c7..4ff3233 100644
--- a/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/TopologyTemplateOperation.java
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/TopologyTemplateOperation.java
@@ -116,7 +116,7 @@
             topologyTemplate.setUniqueId(resourceUniqueId);
         }
         GraphVertex topologyTemplateVertex = new GraphVertex();
-        topologyTemplateVertex = fillMetadata(topologyTemplateVertex, topologyTemplate, JsonParseFlagEnum.ParseAll);
+        fillMetadata(topologyTemplateVertex, topologyTemplate, JsonParseFlagEnum.ParseAll);
         Either<GraphVertex, JanusGraphOperationStatus> createdVertex = janusGraphDao.createVertex(topologyTemplateVertex);
         if (createdVertex.isRight()) {
             JanusGraphOperationStatus status = createdVertex.right().value();
@@ -583,16 +583,23 @@
         return StorageOperationStatus.OK;
     }
 
-    private GraphVertex fillMetadata(GraphVertex nodeTypeVertex, TopologyTemplate topologyTemplate, JsonParseFlagEnum flag) {
+    private void fillMetadata(GraphVertex nodeTypeVertex, TopologyTemplate topologyTemplate, JsonParseFlagEnum flag) {
         nodeTypeVertex.setLabel(VertexTypeEnum.TOPOLOGY_TEMPLATE);
         fillCommonMetadata(nodeTypeVertex, topologyTemplate);
+        fillDataTypes(nodeTypeVertex, topologyTemplate);
         if (flag == JsonParseFlagEnum.ParseAll || flag == JsonParseFlagEnum.ParseJson) {
             nodeTypeVertex.setJson(topologyTemplate.getCompositions());
         }
         nodeTypeVertex.addMetadataProperty(GraphPropertyEnum.CSAR_UUID, topologyTemplate.getMetadataValue(JsonPresentationFields.CSAR_UUID));
         nodeTypeVertex.addMetadataProperty(GraphPropertyEnum.DISTRIBUTION_STATUS,
             topologyTemplate.getMetadataValue(JsonPresentationFields.DISTRIBUTION_STATUS));
-        return nodeTypeVertex;
+    }
+
+    private void fillDataTypes(final GraphVertex nodeTypeVertex, final TopologyTemplate topologyTemplate) {
+        if (MapUtils.isEmpty(topologyTemplate.getDataTypes())) {
+            return;
+        }
+        nodeTypeVertex.setJsonMetadataField(JsonPresentationFields.DATA_TYPES, topologyTemplate.getDataTypes());
     }
 
     private StorageOperationStatus assosiateMetadataToCategory(GraphVertex nodeTypeVertex, TopologyTemplate topologyTemplate) {
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/ToscaElementOperation.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/ToscaElementOperation.java
index a288953..02c95d4 100644
--- a/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/ToscaElementOperation.java
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/ToscaElementOperation.java
@@ -69,6 +69,7 @@
 import org.openecomp.sdc.be.model.catalog.CatalogComponent;
 import org.openecomp.sdc.be.model.category.CategoryDefinition;
 import org.openecomp.sdc.be.model.category.SubCategoryDefinition;
+import org.openecomp.sdc.be.model.converter.PropertyDataConverter;
 import org.openecomp.sdc.be.model.jsonjanusgraph.datamodel.NodeType;
 import org.openecomp.sdc.be.model.jsonjanusgraph.datamodel.TopologyTemplate;
 import org.openecomp.sdc.be.model.jsonjanusgraph.datamodel.ToscaElement;
@@ -99,33 +100,7 @@
     protected CategoryOperation categoryOperation;
     @Autowired
     protected ModelOperation modelOperation;
-
-    public static DataTypeDefinition createDataType(final String dataTypeName) {
-        final DataTypeDefinition dataType = new DataTypeDefinition();
-        dataType.setName(dataTypeName);
-        return dataType;
-    }
-
-    public static DataTypeDefinition createDataTypeDefinitionWithName(final Entry<String, Object> attributeNameValue) {
-        final Map<String, Object> attributeMap = (Map<String, Object>) attributeNameValue.getValue();
-        final DataTypeDefinition dataType = createDataType(attributeNameValue.getKey());
-        setField(attributeMap, TypeUtils.ToscaTagNamesEnum.DESCRIPTION, dataType::setDescription);
-        setField(attributeMap, TypeUtils.ToscaTagNamesEnum.DERIVED_FROM_NAME, dataType::setDerivedFromName);
-        // TODO - find the way to set the properties
-
-//        CommonImportManager.setProperties(attributeMap, dataType::setProperties);
-        final Object derivedFrom = attributeMap.get(JsonPresentationFields.DERIVED_FROM.getPresentation());
-        if (derivedFrom instanceof Map) {
-            final Map<String, Object> derivedFromMap = (Map<String, Object>) derivedFrom;
-            final DataTypeDefinition parentDataTypeDataDefinition = new DataTypeDefinition();
-            parentDataTypeDataDefinition.setName((String) derivedFromMap.get(JsonPresentationFields.NAME.getPresentation()));
-            parentDataTypeDataDefinition.setUniqueId((String) derivedFromMap.get(JsonPresentationFields.UNIQUE_ID.getPresentation()));
-            parentDataTypeDataDefinition.setCreationTime((Long) derivedFromMap.get(JsonPresentationFields.CREATION_TIME.getPresentation()));
-            parentDataTypeDataDefinition.setModificationTime((Long) derivedFromMap.get(JsonPresentationFields.MODIFICATION_TIME.getPresentation()));
-            dataType.setDerivedFrom(parentDataTypeDataDefinition);
-        }
-        return dataType;
-    }
+    protected PropertyDataConverter propertyDataConverter;
 
     protected Gson getGson() {
         return gson;
@@ -959,48 +934,108 @@
 
     @SuppressWarnings("unchecked")
     protected <T extends ToscaElement> T convertToComponent(GraphVertex componentV) {
-        ToscaElement toscaElement = null;
+        ToscaElement toscaElement;
         VertexTypeEnum label = componentV.getLabel();
         switch (label) {
             case NODE_TYPE:
                 toscaElement = new NodeType();
                 break;
             case TOPOLOGY_TEMPLATE:
-                toscaElement = new TopologyTemplate();
+                toscaElement = handleTopologyTemplate(componentV);
                 break;
             default:
-                log.debug("Not supported tosca type {}", label);
-                break;
+                final String errorMsg = String.format("Tosca type '%s' not supported", label);
+                log.debug(errorMsg);
+                throw new UnsupportedOperationException(errorMsg);
         }
-        if (toscaElement != null) {
-            final Map<String, Object> jsonMetada = componentV.getMetadataJson();
-            if (MapUtils.isNotEmpty(jsonMetada)) {
-                toscaElement.setMetadata(jsonMetada);
-                final Object toscaVersion = jsonMetada.get(ToscaTagNamesEnum.TOSCA_VERSION.getElementName());
-                if (toscaVersion != null) {
-                    toscaElement.setToscaVersion((String) toscaVersion);
-                }
-                final Object dataTypes = jsonMetada.get(ToscaTagNamesEnum.DATA_TYPES.getElementName());
-                if (dataTypes != null) {
-                    final Map<String, DataTypeDataDefinition> dataTypeDefinitionMap = new HashMap<>();
-                    final Map<String, Object> toscaAttributes = (Map<String, Object>) dataTypes;
-                    for (final Entry<String, Object> attributeNameValue : toscaAttributes.entrySet()) {
-                        final Object value = attributeNameValue.getValue();
-                        final String key = attributeNameValue.getKey();
-                        if (value instanceof Map) {
-                            final DataTypeDefinition dataTypeDefinition = createDataTypeDefinitionWithName(attributeNameValue);
-                            dataTypeDefinitionMap.put(dataTypeDefinition.getName(), dataTypeDefinition);
-                        } else {
-                            dataTypeDefinitionMap.put(key, createDataType(String.valueOf(value)));
-                        }
-                    }
-                    toscaElement.setDataTypes(dataTypeDefinitionMap);
-                }
+        final Map<String, Object> jsonMetadata = componentV.getMetadataJson();
+        toscaElement.setMetadata(jsonMetadata);
+        if (jsonMetadata != null) {
+            final Object toscaVersion = jsonMetadata.get(ToscaTagNamesEnum.TOSCA_VERSION.getElementName());
+            if (toscaVersion != null) {
+                toscaElement.setToscaVersion((String) toscaVersion);
             }
         }
         return (T) toscaElement;
     }
 
+    private TopologyTemplate handleTopologyTemplate(final GraphVertex componentVertex) {
+        final TopologyTemplate topologyTemplate = new TopologyTemplate();
+        handleDataTypes(topologyTemplate, componentVertex);
+        return topologyTemplate;
+    }
+
+    private void handleDataTypes(final TopologyTemplate topologyTemplate, final GraphVertex componentVertex) {
+        final Object dataTypeEntryObj = componentVertex.getJsonMetadataField(JsonPresentationFields.DATA_TYPES);
+        if (dataTypeEntryObj == null) {
+            return;
+        }
+        if (!(dataTypeEntryObj instanceof Map)) {
+            log.error("Invalid '{}' metadata type. Expected {}.",
+                JsonPresentationFields.DATA_TYPES.getPresentation(), Map.class);
+            return;
+        }
+        @SuppressWarnings("unchecked")
+        final Map<String, Object> dataTypeMap = (Map<String, Object>) dataTypeEntryObj;
+        if (MapUtils.isEmpty(dataTypeMap)) {
+            return;
+        }
+
+        final Map<String, DataTypeDataDefinition> dataTypeDefinitionMap = new HashMap<>();
+        for (final Entry<String, Object> dataTypeEntry : dataTypeMap.entrySet()) {
+            final String dataTypeName = dataTypeEntry.getKey();
+            final Object dataTypeObj = dataTypeEntry.getValue();
+            if (dataTypeObj instanceof Map) {
+                final DataTypeDefinition dataTypeDefinition = createDataTypeDefinitionFromJson(dataTypeEntry);
+                dataTypeDefinitionMap.put(dataTypeDefinition.getName(), dataTypeDefinition);
+            } else {
+                final DataTypeDefinition dataType = new DataTypeDefinition();
+                dataType.setName(String.valueOf(dataType));
+                dataTypeDefinitionMap.put(dataTypeName, dataType);
+            }
+        }
+        topologyTemplate.setDataTypes(dataTypeDefinitionMap);
+    }
+
+    public DataTypeDefinition createDataType(final String dataTypeName) {
+        final DataTypeDefinition dataType = new DataTypeDefinition();
+        dataType.setName(dataTypeName);
+        return dataType;
+    }
+
+    public DataTypeDefinition createDataTypeDefinitionFromJson(final Entry<String, Object> dataTypeMap) {
+        final DataTypeDefinition dataType = new DataTypeDefinition();
+        dataType.setName(dataTypeMap.getKey());
+        @SuppressWarnings("unchecked")
+        final Map<String, Object> attributeMap = (Map<String, Object>) dataTypeMap.getValue();
+        setField(attributeMap, TypeUtils.ToscaTagNamesEnum.DESCRIPTION, dataType::setDescription);
+        setField(attributeMap, TypeUtils.ToscaTagNamesEnum.DERIVED_FROM_NAME, dataType::setDerivedFromName);
+        final List<PropertyDataDefinition> propertyDataDefinitionList = handlePropertiesDataFromJson(attributeMap);
+        dataType.setPropertiesData(propertyDataDefinitionList);
+        final Object derivedFrom = attributeMap.get(JsonPresentationFields.DERIVED_FROM.getPresentation());
+        if (derivedFrom instanceof Map) {
+            @SuppressWarnings("unchecked")
+            final Map<String, Object> derivedFromMap = (Map<String, Object>) derivedFrom;
+            final DataTypeDefinition parentDataTypeDataDefinition = new DataTypeDefinition();
+            parentDataTypeDataDefinition.setName((String) derivedFromMap.get(JsonPresentationFields.NAME.getPresentation()));
+            parentDataTypeDataDefinition.setUniqueId((String) derivedFromMap.get(JsonPresentationFields.UNIQUE_ID.getPresentation()));
+            parentDataTypeDataDefinition.setCreationTime((Long) derivedFromMap.get(JsonPresentationFields.CREATION_TIME.getPresentation()));
+            parentDataTypeDataDefinition.setModificationTime((Long) derivedFromMap.get(JsonPresentationFields.MODIFICATION_TIME.getPresentation()));
+            dataType.setDerivedFrom(parentDataTypeDataDefinition);
+        }
+        return dataType;
+    }
+
+    protected List<PropertyDataDefinition> handlePropertiesDataFromJson(final Map<String, Object> attributeMap) {
+        final Object propertiesDataObj = attributeMap.get("propertiesData");
+        if (!(propertiesDataObj instanceof List)) {
+            return Collections.emptyList();
+        }
+        @SuppressWarnings("unchecked")
+        final List<Map<String, Object>> propertiesDataList = (List<Map<String, Object>>) propertiesDataObj;
+        return propertyDataConverter.parseProperties(propertiesDataList);
+    }
+
     protected JanusGraphOperationStatus setResourceCategoryFromGraphV(Vertex vertex, CatalogComponent catalogComponent) {
         List<CategoryDefinition> categories = new ArrayList<>();
         SubCategoryDefinition subcategory;
@@ -1492,4 +1527,10 @@
     protected abstract <T extends ToscaElement> StorageOperationStatus updateDerived(T toscaElementToUpdate, GraphVertex updateElementV);
 
     public abstract <T extends ToscaElement> void fillToscaElementVertexData(GraphVertex elementV, T toscaElementToUpdate, JsonParseFlagEnum flag);
+
+    @Autowired
+    public void setPropertyDataConverter(final PropertyDataConverter propertyDataConverter) {
+        this.propertyDataConverter = propertyDataConverter;
+    }
+
 }
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/utils/ModelConverter.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/utils/ModelConverter.java
index 079f5a4..e34f23c 100644
--- a/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/utils/ModelConverter.java
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/jsonjanusgraph/utils/ModelConverter.java
@@ -1130,9 +1130,42 @@
         convertPolicies(component, topologyTemplate);
         convertRequirements(component, topologyTemplate);
         convertRelationsToComposition(component, topologyTemplate);
+        convertDataTypes(component, topologyTemplate);
         return topologyTemplate;
     }
 
+    private static void convertDataTypes(final Component component, final TopologyTemplate topologyTemplate) {
+        final List<DataTypeDefinition> dataTypeDefinitionList = component.getDataTypes();
+        if (CollectionUtils.isEmpty(dataTypeDefinitionList)) {
+            return;
+        }
+        final Map<String, DataTypeDataDefinition> dataTypeMap = dataTypeDefinitionList.stream()
+            .collect(
+                Collectors.toMap(DataTypeDataDefinition::getName,
+                    ModelConverter::parseTo,
+                    (dataTypeDataDefinition, dataTypeDataDefinition2) -> dataTypeDataDefinition)
+            );
+        topologyTemplate.setDataTypes(dataTypeMap);
+    }
+
+    private static DataTypeDataDefinition parseTo(final DataTypeDefinition dataTypeDefinition) {
+        final DataTypeDataDefinition dataTypeDataDefinition = new DataTypeDataDefinition(dataTypeDefinition);
+        final List<PropertyDataDefinition> propertyDataList = new ArrayList<>();
+        DataTypeDefinition currentDataType = dataTypeDefinition;
+
+        do {
+            if (CollectionUtils.isNotEmpty(currentDataType.getProperties())) {
+                propertyDataList.addAll(currentDataType.getProperties().stream()
+                    .map(PropertyDataDefinition::new)
+                    .collect(Collectors.toList()));
+            }
+            currentDataType = currentDataType.getDerivedFrom();
+        } while (currentDataType != null);
+
+        dataTypeDataDefinition.setPropertiesData(propertyDataList);
+        return dataTypeDataDefinition;
+    }
+
     private static void convertTopologyTemplateInterfaces(Resource resource, TopologyTemplate topologyTemplate) {
         Map<String, InterfaceDefinition> interfaces = resource.getInterfaces();
         if (interfaces != null && !interfaces.isEmpty()) {
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/DataTypeOperation.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/DataTypeOperation.java
index d6cca3f..0161f7a 100644
--- a/catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/DataTypeOperation.java
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/DataTypeOperation.java
@@ -24,13 +24,15 @@
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
-import java.util.stream.Collectors;
+import java.util.Optional;
 import org.apache.commons.collections.CollectionUtils;
-import org.apache.commons.collections4.MapUtils;
+import org.apache.commons.lang3.tuple.ImmutablePair;
 import org.openecomp.sdc.be.config.BeEcompErrorManager;
 import org.openecomp.sdc.be.config.BeEcompErrorManager.ErrorSeverity;
+import org.openecomp.sdc.be.dao.graph.datatype.GraphEdge;
 import org.openecomp.sdc.be.dao.janusgraph.HealingJanusGraphGenericDao;
 import org.openecomp.sdc.be.dao.janusgraph.JanusGraphOperationStatus;
+import org.openecomp.sdc.be.dao.neo4j.GraphEdgeLabels;
 import org.openecomp.sdc.be.datatypes.enums.NodeTypeEnum;
 import org.openecomp.sdc.be.model.DataTypeDefinition;
 import org.openecomp.sdc.be.resources.data.DataTypeData;
@@ -46,12 +48,15 @@
     private static final Logger LOGGER = LoggerFactory.getLogger(DataTypeOperation.class);
 
     private final ModelOperation modelOperation;
+    private final PropertyOperation propertyOperation;
 
     @Autowired
     public DataTypeOperation(final HealingJanusGraphGenericDao janusGraphGenericDao,
-                             final ModelOperation modelOperation) {
+                             final ModelOperation modelOperation,
+                             final PropertyOperation propertyOperation) {
         this.janusGraphGenericDao = janusGraphGenericDao;
         this.modelOperation = modelOperation;
+        this.propertyOperation = propertyOperation;
     }
 
     public List<DataTypeData> getAllDataTypeNodes() {
@@ -132,4 +137,59 @@
         return getDataTypes.left().value();
     }
 
+    public Optional<DataTypeDefinition> findDataTypeByName(final String name) {
+        final String uid = UniqueIdBuilder.buildDataTypeUid(null, name);
+        return findById(uid);
+    }
+
+    public Optional<DataTypeDefinition> findDataTypeByName(final String name, final String model) {
+        final String uid = UniqueIdBuilder.buildDataTypeUid(model, name);
+        return findById(uid);
+    }
+
+    /**
+     * Build Data type object from graph by unique id
+     *
+     * @param id
+     * @return
+     */
+    public Optional<DataTypeDefinition> findById(final String id) {
+        Either<DataTypeData, JanusGraphOperationStatus> dataTypesRes = janusGraphGenericDao
+            .getNode(UniqueIdBuilder.getKeyByNodeType(NodeTypeEnum.DataType), id, DataTypeData.class);
+        if (dataTypesRes.isRight()) {
+            JanusGraphOperationStatus status = dataTypesRes.right().value();
+//            log.debug(DATA_TYPE_CANNOT_BE_FOUND_IN_GRAPH_STATUS_IS, id, status);
+            throw new RuntimeException();
+        }
+        DataTypeData ctData = dataTypesRes.left().value();
+        DataTypeDefinition dataTypeDefinition = new DataTypeDefinition(ctData.getDataTypeDataDefinition());
+        JanusGraphOperationStatus propertiesStatus = propertyOperation.fillProperties(id, dataTypeDefinition);
+        if (propertiesStatus != JanusGraphOperationStatus.OK) {
+//            log.error(FAILED_TO_FETCH_PROPERTIES_OF_DATA_TYPE, id);
+            throw new RuntimeException();
+        }
+        Either<ImmutablePair<DataTypeData, GraphEdge>, JanusGraphOperationStatus> parentNode = janusGraphGenericDao
+            .getChild(UniqueIdBuilder.getKeyByNodeType(NodeTypeEnum.DataType), id, GraphEdgeLabels.DERIVED_FROM, NodeTypeEnum.DataType,
+                DataTypeData.class);
+//        log.debug("After retrieving DERIVED_FROM node of {}. status is {}", id, parentNode);
+        if (parentNode.isRight()) {
+            JanusGraphOperationStatus janusGraphOperationStatus = parentNode.right().value();
+            if (janusGraphOperationStatus != JanusGraphOperationStatus.NOT_FOUND) {
+//                log.error("Failed to find the parent data type of data type {}. status is {}", id, janusGraphOperationStatus);
+                throw new RuntimeException();
+            }
+        } else {
+            // retrieving parent information
+            final DataTypeData dataType = parentNode.left().value().getKey();
+            final Optional<DataTypeDefinition> dataTypeOpt = findById(dataType.getUniqueId());
+            if (dataTypeOpt.isEmpty()) {
+                throw new RuntimeException();
+            }
+            final DataTypeDefinition parentDataTypeDefinition = dataTypeOpt.get();
+            dataTypeDefinition.setDerivedFrom(parentDataTypeDefinition);
+        }
+
+        return Optional.of(dataTypeDefinition);
+    }
+
 }
diff --git a/catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/PropertyOperation.java b/catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/PropertyOperation.java
index 01dbb07..96becbb 100644
--- a/catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/PropertyOperation.java
+++ b/catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/PropertyOperation.java
@@ -124,11 +124,9 @@
     private DataTypeOperation dataTypeOperation;
 
     @Autowired
-    public PropertyOperation(HealingJanusGraphGenericDao janusGraphGenericDao, DerivedFromOperation derivedFromOperation,
-                             DataTypeOperation dataTypeOperation) {
+    public PropertyOperation(HealingJanusGraphGenericDao janusGraphGenericDao, DerivedFromOperation derivedFromOperation) {
         this.janusGraphGenericDao = janusGraphGenericDao;
         this.derivedFromOperation = derivedFromOperation;
-        this.dataTypeOperation = dataTypeOperation;
     }
 
     public PropertyDefinition convertPropertyDataToPropertyDefinition(PropertyData propertyDataResult, String propertyName, String resourceId) {
@@ -817,19 +815,35 @@
     }
 
     public boolean isPropertyTypeValid(final IComplexDefaultValue property, final String model) {
-        if (property == null) {
+        return isPropertyTypeValid(property, model, null);
+    }
+
+    public boolean isPropertyTypeValid(final IComplexDefaultValue property, final String model,
+                                       final Collection<DataTypeDefinition> componentDataTypeCollection) {
+        if (property == null || property.getType() == null) {
             return false;
         }
-        if (ToscaPropertyType.isValidType(property.getType()) == null) {
-            Either<Boolean, JanusGraphOperationStatus> definedInDataTypes = isDefinedInDataTypes(property.getType(), model);
-            if (definedInDataTypes.isRight()) {
-                return false;
-            } else {
-                Boolean isExist = definedInDataTypes.left().value();
-                return isExist.booleanValue();
+
+        final ToscaPropertyType toscaPropertyType = ToscaPropertyType.isValidType(property.getType());
+        if (toscaPropertyType != null) {
+            return true;
+        }
+
+        if (CollectionUtils.isNotEmpty(componentDataTypeCollection)) {
+            final boolean matches = componentDataTypeCollection.stream()
+                .anyMatch(dataTypeDefinition -> dataTypeDefinition.getName().equals(property.getType()));
+            if (matches) {
+                return true;
             }
         }
-        return true;
+
+        final Either<Boolean, JanusGraphOperationStatus> definedInDataTypes = isDefinedInDataTypes(property.getType(), model);
+
+        if (definedInDataTypes.isLeft()) {
+            return definedInDataTypes.left().value();
+        }
+
+        return false;
     }
 
     @Override
@@ -1335,7 +1349,7 @@
         return result;
     }
 
-    private JanusGraphOperationStatus fillProperties(String uniqueId, DataTypeDefinition dataTypeDefinition) {
+    public JanusGraphOperationStatus fillProperties(String uniqueId, DataTypeDefinition dataTypeDefinition) {
         Either<Map<String, PropertyDefinition>, JanusGraphOperationStatus> findPropertiesOfNode = this
             .findPropertiesOfNode(NodeTypeEnum.DataType, uniqueId);
         if (findPropertiesOfNode.isRight()) {
@@ -2264,4 +2278,10 @@
             return null;
         }
     }
+
+    //circular dependency
+    @Autowired
+    public void setDataTypeOperation(final DataTypeOperation dataTypeOperation) {
+        this.dataTypeOperation = dataTypeOperation;
+    }
 }
diff --git a/catalog-model/src/test/java/org/openecomp/sdc/be/model/config/ModelOperationsSpringConfig.java b/catalog-model/src/test/java/org/openecomp/sdc/be/model/config/ModelOperationsSpringConfig.java
index 28e17b5..969e24e 100644
--- a/catalog-model/src/test/java/org/openecomp/sdc/be/model/config/ModelOperationsSpringConfig.java
+++ b/catalog-model/src/test/java/org/openecomp/sdc/be/model/config/ModelOperationsSpringConfig.java
@@ -30,6 +30,7 @@
     "org.openecomp.sdc.be.model.jsonjanusgraph.operations",
     "org.openecomp.sdc.be.model.jsonjanusgraph.utils",
     "org.openecomp.sdc.be.model.jsonjanusgraph.config",
-        "org.openecomp.sdc.be.model.operations.impl"})
+    "org.openecomp.sdc.be.model.operations.impl",
+    "org.openecomp.sdc.be.model.converter"})
 @PropertySource("classpath:dao.properties")
 public class ModelOperationsSpringConfig { }
diff --git a/catalog-model/src/test/java/org/openecomp/sdc/be/model/converter/PropertyDataConverterTest.java b/catalog-model/src/test/java/org/openecomp/sdc/be/model/converter/PropertyDataConverterTest.java
new file mode 100644
index 0000000..ddd169f
--- /dev/null
+++ b/catalog-model/src/test/java/org/openecomp/sdc/be/model/converter/PropertyDataConverterTest.java
@@ -0,0 +1,246 @@
+/*
+ * -
+ *  ============LICENSE_START=======================================================
+ *  Copyright (C) 2021 Nordix Foundation.
+ *  ================================================================================
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *       http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ *
+ *  SPDX-License-Identifier: Apache-2.0
+ *  ============LICENSE_END=========================================================
+ */
+
+package org.openecomp.sdc.be.model.converter;
+
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.containsInAnyOrder;
+import static org.hamcrest.Matchers.empty;
+import static org.hamcrest.Matchers.is;
+import static org.hamcrest.Matchers.notNullValue;
+import static org.hamcrest.Matchers.nullValue;
+import static org.mockito.Mockito.when;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.DEFAULT_VALUE;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.DEFINITION;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.DESCRIPTION;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.HIDDEN;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.IMMUTABLE;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.INPUT_ID;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.INPUT_PATH;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.INSTANCE_UNIQUE_ID;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.LABEL;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.NAME;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PARENT_PROPERTY_TYPE;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PASSWORD;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PROPERTY;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PROPERTY_CONSTRAINTS;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PROPERTY_ID;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.REQUIRED;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.SCHEMA;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.STATUS;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.SUB_PROPERTY_INPUT_PATH;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.TYPE;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.UNIQUE_ID;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.VALUE;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Optional;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+import org.mockito.Mock;
+import org.mockito.MockitoAnnotations;
+import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
+import org.openecomp.sdc.be.datatypes.elements.SchemaDefinition;
+
+class PropertyDataConverterTest {
+
+    private PropertyDataConverter propertyDataConverter;
+    @Mock
+    private SchemaDefinitionConverter schemaDefinitionConverter;
+
+    @BeforeEach
+    void setUp() {
+        MockitoAnnotations.openMocks(this);
+        propertyDataConverter = new PropertyDataConverter();
+        propertyDataConverter.setSchemaDefinitionConverter(schemaDefinitionConverter);
+    }
+
+    @Test
+    void parsePropertiesSuccessTest() {
+        final List<Map<String, Object>> propertyDataList = new ArrayList<>();
+        final HashMap<String, Object> propertyJsonMap1 = new HashMap<>();
+        propertyJsonMap1.put("type", "string");
+        propertyDataList.add(propertyJsonMap1);
+        final HashMap<String, Object> propertyJsonMap2 = new HashMap<>();
+        propertyJsonMap2.put("type", "boolean");
+        propertyDataList.add(propertyJsonMap2);
+        final HashMap<String, Object> propertyJsonMap3 = new HashMap<>();
+        propertyJsonMap3.put("type", "a.tosca.type");
+        propertyDataList.add(propertyJsonMap3);
+        final List<PropertyDataDefinition> actualPropertyDataList = propertyDataConverter
+            .parseProperties(propertyDataList);
+        assertThat(actualPropertyDataList, is(notNullValue()));
+        assertThat(actualPropertyDataList.size(), is(propertyDataList.size()));
+    }
+
+    @Test
+    void parseEmptyPropertiesListTest() {
+        List<PropertyDataDefinition> propertyDataDefinitions =
+            propertyDataConverter.parseProperties(null);
+        assertThat("Should not be null", propertyDataDefinitions, is(notNullValue()));
+        assertThat("Should be empty", propertyDataDefinitions, is(empty()));
+        propertyDataDefinitions =
+            propertyDataConverter.parseProperties(Collections.emptyList());
+        assertThat("Should not be null", propertyDataDefinitions, is(notNullValue()));
+        assertThat("Should be empty", propertyDataDefinitions, is(empty()));
+    }
+
+    @Test
+    void createPropertyDataSuccessTest() {
+        final Map<String, Object> propertyJsonMap = new HashMap<>();
+        final PropertyDataDefinition expectedPropertyData = new PropertyDataDefinition();
+
+        final String uniqueId = "uniqueId";
+        expectedPropertyData.setUniqueId(uniqueId);
+        propertyJsonMap.put(UNIQUE_ID.getPresentation(), uniqueId);
+
+        final String type = "type";
+        expectedPropertyData.setType(type);
+        propertyJsonMap.put(TYPE.getPresentation(), type);
+
+        final Boolean required = Boolean.FALSE;
+        expectedPropertyData.setRequired(required);
+        propertyJsonMap.put(REQUIRED.getPresentation(), required);
+
+        final String name = "name";
+        expectedPropertyData.setName(name);
+        propertyJsonMap.put(NAME.getPresentation(), name);
+
+        final String label = "label";
+        expectedPropertyData.setLabel(label);
+        propertyJsonMap.put(LABEL.getPresentation(), label);
+
+        final String value = "value";
+        expectedPropertyData.setValue(value);
+        propertyJsonMap.put(VALUE.getPresentation(), value);
+
+        final Boolean hidden = Boolean.FALSE;
+        expectedPropertyData.setHidden(hidden);
+        propertyJsonMap.put(HIDDEN.getPresentation(), hidden);
+
+        final Boolean immutable = Boolean.TRUE;
+        expectedPropertyData.setImmutable(immutable);
+        propertyJsonMap.put(IMMUTABLE.getPresentation(), immutable);
+
+        final boolean password = false;
+        expectedPropertyData.setPassword(password);
+        propertyJsonMap.put(PASSWORD.getPresentation(), password);
+
+        final boolean definition = false;
+        expectedPropertyData.setDefinition(definition);
+        propertyJsonMap.put(DEFINITION.getPresentation(), definition);
+
+        final String description = "description";
+        expectedPropertyData.setDescription(description);
+        propertyJsonMap.put(DESCRIPTION.getPresentation(), description);
+
+        final String defaultValue = "defaultValue";
+        expectedPropertyData.setDefaultValue(defaultValue);
+        propertyJsonMap.put(DEFAULT_VALUE.getPresentation(), defaultValue);
+
+        final String inputPath = "inputPath";
+        expectedPropertyData.setInputPath(inputPath);
+        propertyJsonMap.put(INPUT_PATH.getPresentation(), inputPath);
+
+        final String status = "status";
+        expectedPropertyData.setStatus(status);
+        propertyJsonMap.put(STATUS.getPresentation(), status);
+
+        final String inputId = "inputId";
+        expectedPropertyData.setInputId(inputId);
+        propertyJsonMap.put(INPUT_ID.getPresentation(), inputId);
+
+        final String instanceUniqueId = "instanceUniqueId";
+        expectedPropertyData.setInstanceUniqueId(instanceUniqueId);
+        propertyJsonMap.put(INSTANCE_UNIQUE_ID.getPresentation(), instanceUniqueId);
+
+        final String propertyId = "propertyId";
+        expectedPropertyData.setPropertyId(propertyId);
+        propertyJsonMap.put(PROPERTY_ID.getPresentation(), propertyId);
+
+        final String parentPropertyType = "parentPropertyType";
+        expectedPropertyData.setParentPropertyType(parentPropertyType);
+        propertyJsonMap.put(PARENT_PROPERTY_TYPE.getPresentation(), parentPropertyType);
+
+        final String subPropertyType = "subPropertyType";
+        expectedPropertyData.setSubPropertyInputPath(subPropertyType);
+        propertyJsonMap.put(SUB_PROPERTY_INPUT_PATH.getPresentation(), subPropertyType);
+
+        PropertyDataDefinition actualPropertyData = propertyDataConverter.createPropertyData(propertyJsonMap);
+        assertThat(actualPropertyData.getUniqueId(), is(expectedPropertyData.getUniqueId()));
+        assertThat(actualPropertyData.getRequired(), is(expectedPropertyData.getRequired()));
+        assertThat(actualPropertyData.getName(), is(expectedPropertyData.getName()));
+        assertThat(actualPropertyData.getLabel(), is(expectedPropertyData.getLabel()));
+        assertThat(actualPropertyData.getValue(), is(expectedPropertyData.getValue()));
+        assertThat(actualPropertyData.getHidden(), is(expectedPropertyData.getHidden()));
+        assertThat(actualPropertyData.getImmutable(), is(expectedPropertyData.getImmutable()));
+        assertThat(actualPropertyData.isPassword(), is(expectedPropertyData.isPassword()));
+        assertThat(actualPropertyData.getDefinition(), is(expectedPropertyData.getDefinition()));
+        assertThat(actualPropertyData.getDescription(), is(expectedPropertyData.getDescription()));
+        assertThat(actualPropertyData.getDefaultValue(), is(expectedPropertyData.getDefaultValue()));
+        assertThat(actualPropertyData.getInputPath(), is(expectedPropertyData.getInputPath()));
+        assertThat(actualPropertyData.getStatus(), is(expectedPropertyData.getStatus()));
+        assertThat(actualPropertyData.getInputId(), is(expectedPropertyData.getInputId()));
+        assertThat(actualPropertyData.getInstanceUniqueId(), is(expectedPropertyData.getInstanceUniqueId()));
+        assertThat(actualPropertyData.getPropertyId(), is(expectedPropertyData.getPropertyId()));
+        assertThat(actualPropertyData.getParentPropertyType(), is(expectedPropertyData.getParentPropertyType()));
+        assertThat(actualPropertyData.getSubPropertyInputPath(), is(expectedPropertyData.getSubPropertyInputPath()));
+        assertThat(actualPropertyData.getSchema(), is(nullValue()));
+        assertThat(actualPropertyData.getPropertyConstraints(), is(nullValue()));
+
+        //schema
+        final Map<String, Object> propertySchemaMap = new HashMap<>();
+        propertySchemaMap.put(TYPE.getPresentation(), "string");
+        final Map<String, Object> schemaMap = new HashMap<>();
+        schemaMap.put(PROPERTY.getPresentation(), propertySchemaMap);
+        propertyJsonMap.put(SCHEMA.getPresentation(), schemaMap);
+        final SchemaDefinition schemaDefinition = new SchemaDefinition();
+        final PropertyDataDefinition schemaPropertyData = new PropertyDataDefinition();
+        schemaPropertyData.setType("string");
+        schemaDefinition.setProperty(schemaPropertyData);
+        expectedPropertyData.setSchema(schemaDefinition);
+        when(schemaDefinitionConverter.parseTo(schemaMap)).thenReturn(Optional.of(schemaDefinition));
+        //constraints
+        final List<String> propertyConstraintList = new ArrayList<>();
+        propertyConstraintList.add("constraint1");
+        propertyConstraintList.add("constraint2");
+        expectedPropertyData.setPropertyConstraints(propertyConstraintList);
+        propertyJsonMap.put(PROPERTY_CONSTRAINTS.getPresentation(), propertyConstraintList);
+        actualPropertyData = propertyDataConverter.createPropertyData(propertyJsonMap);
+        assertThat(actualPropertyData.getSchema(), is(notNullValue()));
+        assertThat(actualPropertyData.getSchema().getType(), is(expectedPropertyData.getSchema().getType()));
+        assertThat(actualPropertyData.getPropertyConstraints(), is(notNullValue()));
+        assertThat(actualPropertyData.getPropertyConstraints().size(), is(expectedPropertyData.getPropertyConstraints().size()));
+        assertThat(actualPropertyData.getPropertyConstraints(), containsInAnyOrder(propertyConstraintList.toArray()));
+    }
+
+    @Test
+    void createEmptyPropertyDataTest() {
+        final Map<String, Object> propertyJsonMap = new HashMap<>();
+        final PropertyDataDefinition propertyData = propertyDataConverter.createPropertyData(propertyJsonMap);
+        final PropertyDataDefinition expectedPropertyData = new PropertyDataDefinition();
+        assertThat("Should be the equal", propertyData, is(expectedPropertyData));
+    }
+}
\ No newline at end of file
diff --git a/catalog-model/src/test/java/org/openecomp/sdc/be/model/converter/SchemaDefinitionConverterTest.java b/catalog-model/src/test/java/org/openecomp/sdc/be/model/converter/SchemaDefinitionConverterTest.java
new file mode 100644
index 0000000..ad6b7da
--- /dev/null
+++ b/catalog-model/src/test/java/org/openecomp/sdc/be/model/converter/SchemaDefinitionConverterTest.java
@@ -0,0 +1,81 @@
+/*
+ * -
+ *  ============LICENSE_START=======================================================
+ *  Copyright (C) 2021 Nordix Foundation.
+ *  ================================================================================
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *       http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ *
+ *  SPDX-License-Identifier: Apache-2.0
+ *  ============LICENSE_END=========================================================
+ */
+
+package org.openecomp.sdc.be.model.converter;
+
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.is;
+import static org.hamcrest.Matchers.notNullValue;
+import static org.mockito.Mockito.when;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.PROPERTY;
+import static org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields.TYPE;
+
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Optional;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Test;
+import org.mockito.Mock;
+import org.mockito.MockitoAnnotations;
+import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
+import org.openecomp.sdc.be.datatypes.elements.SchemaDefinition;
+
+class SchemaDefinitionConverterTest {
+
+    private SchemaDefinitionConverter schemaDefinitionConverter;
+    @Mock
+    private PropertyDataConverter propertyDataConverter;
+
+    @BeforeEach
+    void setUp() {
+        MockitoAnnotations.openMocks(this);
+        schemaDefinitionConverter = new SchemaDefinitionConverter();
+        schemaDefinitionConverter.setPropertyDataConverter(propertyDataConverter);
+    }
+
+    @Test
+    void parseToSuccessTest() {
+        //given
+        final Map<String, Object> propertySchemaMap = new HashMap<>();
+        propertySchemaMap.put(TYPE.getPresentation(), "string");
+        final Map<String, Object> schemaMap = new HashMap<>();
+        schemaMap.put(PROPERTY.getPresentation(), propertySchemaMap);
+        final PropertyDataDefinition schemaPropertyData = new PropertyDataDefinition();
+        schemaPropertyData.setType("string");
+        //when
+        when(propertyDataConverter.createPropertyData(propertySchemaMap)).thenReturn(schemaPropertyData);
+        final SchemaDefinition actualSchemaDefinition = schemaDefinitionConverter.parseTo(schemaMap).orElse(null);
+        //then
+        assertThat(actualSchemaDefinition, is(notNullValue()));
+        assertThat(actualSchemaDefinition.getProperty(), is(notNullValue()));
+        assertThat(actualSchemaDefinition.getProperty().getType(), is(schemaPropertyData.getType()));
+    }
+
+    @Test
+    void parseToEmptyJsonMap() {
+        //given
+        final Map<String, Object> schemaMap = new HashMap<>();
+        //when
+        final Optional<SchemaDefinition> actualSchemaDefinition = schemaDefinitionConverter.parseTo(schemaMap);
+        //then
+        assertThat(actualSchemaDefinition.isPresent(), is(false));
+    }
+}
\ No newline at end of file
diff --git a/catalog-model/src/test/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/ToscaElementOperationTest.java b/catalog-model/src/test/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/ToscaElementOperationTest.java
index 3da37c0..8dd6b9f 100644
--- a/catalog-model/src/test/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/ToscaElementOperationTest.java
+++ b/catalog-model/src/test/java/org/openecomp/sdc/be/model/jsonjanusgraph/operations/ToscaElementOperationTest.java
@@ -266,7 +266,7 @@
     @Test
     public void testCreateDataType() {
         final String expected = "newDataType";
-        final DataTypeDefinition result = ToscaElementOperation.createDataType(expected);
+        final DataTypeDefinition result = toscaElementOperation.createDataType(expected);
         assertNotNull(result);
         assertEquals(expected, result.getName());
     }
@@ -293,7 +293,7 @@
         attributeMap.put(JsonPresentationFields.DERIVED_FROM.getPresentation(), derivedFromMap);
 
         final Entry<String, Object> attributeNameValue = new EntryData<>(expected, attributeMap);
-        final DataTypeDefinition result = ToscaElementOperation.createDataTypeDefinitionWithName(attributeNameValue);
+        final DataTypeDefinition result = toscaElementOperation.createDataTypeDefinitionFromJson(attributeNameValue);
 
         assertNotNull(result);
         assertEquals(derivedFromName, result.getDerivedFromName());
diff --git a/catalog-model/src/test/java/org/openecomp/sdc/be/model/operations/impl/PropertyOperationTest.java b/catalog-model/src/test/java/org/openecomp/sdc/be/model/operations/impl/PropertyOperationTest.java
index 793af71..f0a70e3 100644
--- a/catalog-model/src/test/java/org/openecomp/sdc/be/model/operations/impl/PropertyOperationTest.java
+++ b/catalog-model/src/test/java/org/openecomp/sdc/be/model/operations/impl/PropertyOperationTest.java
@@ -24,7 +24,12 @@
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertNull;
 import static org.junit.Assert.assertTrue;
+import static org.mockito.ArgumentMatchers.any;
+import static org.mockito.ArgumentMatchers.eq;
+import static org.mockito.Mockito.doCallRealMethod;
+import static org.mockito.Mockito.doReturn;
 import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.spy;
 
 import fj.data.Either;
 import java.util.ArrayList;
@@ -73,12 +78,12 @@
 
     final DataTypeOperation dataTypeOperation = mock(DataTypeOperation.class);
 
-    PropertyOperation propertyOperation = new PropertyOperation(janusGraphGenericDao, null, dataTypeOperation);
+    PropertyOperation propertyOperation = new PropertyOperation(janusGraphGenericDao, null);
 
     @Before
     public void setup() {
+        propertyOperation.setDataTypeOperation(dataTypeOperation);
         propertyOperation.setJanusGraphGenericDao(janusGraphGenericDao);
-
     }
 
     private PropertyDefinition buildPropertyDefinition() {
@@ -457,7 +462,9 @@
 	}
 
 	private PropertyOperation createTestSubject() {
-		return new PropertyOperation(new HealingJanusGraphGenericDao(new JanusGraphClient()), null, dataTypeOperation);
+        final var propertyOperation = new PropertyOperation(new HealingJanusGraphGenericDao(new JanusGraphClient()), null);
+        propertyOperation.setDataTypeOperation(dataTypeOperation);
+        return propertyOperation;
 	}
 
 	@Test
@@ -783,19 +790,78 @@
 		Assert.assertEquals(false, result);
 	}
 
-	
-	@Test
-	public void testIsPropertyTypeValid() throws Exception {
-		PropertyOperation testSubject;
-		IComplexDefaultValue property = null;
-		boolean result;
 
-		// test 1
-		testSubject = createTestSubject();
-		property = null;
-		result = testSubject.isPropertyTypeValid(property, null);
-		Assert.assertEquals(false, result);
-	}
+    @Test
+    public void testIsPropertyTypeValidForNullPropertyOrPropertyType() {
+        final PropertyOperation propertyOperation = createTestSubject();
+        assertFalse("Property type should not be valid", propertyOperation.isPropertyTypeValid(null, null, null));
+        assertFalse("Property type should not be valid",
+            propertyOperation.isPropertyTypeValid(new PropertyDefinition(), "model"));
+        assertFalse("Property type should not be valid", propertyOperation.isPropertyTypeValid(null, null, null));
+        assertFalse("Property type should not be valid",
+            propertyOperation.isPropertyTypeValid(new PropertyDefinition(), "model", null));
+    }
+
+    @Test
+    public void testIsPropertyTypeValidForFoundType() {
+        final PropertyOperation propertyOperation = spy(createTestSubject());
+        final String nonToscaType = "non.tosca.type";
+        final PropertyDefinition propertyDefinition = buildPropertyDefinition();
+        propertyDefinition.setType(nonToscaType);
+        doCallRealMethod().when(propertyOperation).isPropertyTypeValid(any(), any(), any());
+        doReturn(Either.left(true)).when(propertyOperation).isDefinedInDataTypes(any(), any());
+        assertTrue("Property type should be valid", propertyOperation.isPropertyTypeValid(propertyDefinition, null, null));
+        assertTrue("Property type should be valid", propertyOperation.isPropertyTypeValid(propertyDefinition, null));
+    }
+
+    @Test
+    public void testIsPropertyTypeValidForNotFoundType() {
+        final PropertyOperation propertyOperation = spy(createTestSubject());
+        final var nonToscaType = "non.tosca.type";
+        final PropertyDefinition propertyDefinition = buildPropertyDefinition();
+        propertyDefinition.setType(nonToscaType);
+        doReturn(Either.right(JanusGraphOperationStatus.NOT_FOUND))
+            .when(propertyOperation).isDefinedInDataTypes(any(), any());
+        final var model = "";
+        assertFalse("Property type should not be valid", propertyOperation.isPropertyTypeValid(propertyDefinition, model));
+        assertFalse("Property type should not be valid",
+            propertyOperation.isPropertyTypeValid(propertyDefinition, model, Collections.emptyList()));
+        doReturn(Either.left(false)).when(propertyOperation).isDefinedInDataTypes(any(), any());
+        assertFalse("Property type should not be valid",
+            propertyOperation.isPropertyTypeValid(propertyDefinition, model));
+        assertFalse("Property type should not be valid",
+            propertyOperation.isPropertyTypeValid(propertyDefinition, model, Collections.emptyList()));
+    }
+
+    @Test
+    public void testIsPropertyTypeValidForValidToscaType() {
+        final PropertyOperation propertyOperation = createTestSubject();
+        final PropertyDefinition propertyDefinition = buildPropertyDefinition();
+        assertTrue("Property type should be valid",
+            propertyOperation.isPropertyTypeValid(propertyDefinition, ""));
+        assertTrue("Property type should be valid",
+            propertyOperation.isPropertyTypeValid(propertyDefinition, "", Collections.emptyList()));
+    }
+
+    @Test
+    public void testIsPropertyTypeValidForNonToscaTypeProvidedInList() {
+        final PropertyOperation propertyOperation = spy(createTestSubject());
+        final String nonToscaType = "non.tosca.type";
+        final String model = "model";
+        final PropertyDefinition propertyDefinition = buildPropertyDefinition();
+        propertyDefinition.setType(nonToscaType);
+        doCallRealMethod().when(propertyOperation).isPropertyTypeValid(any(), eq(model), any());
+        doReturn(Either.right(JanusGraphOperationStatus.NOT_FOUND)).when(propertyOperation).isDefinedInDataTypes(any(), any());
+        final List<DataTypeDefinition> dataTypeDefinitionList = new ArrayList<>();
+        final DataTypeDefinition dataTypeDefinition = new DataTypeDefinition();
+        dataTypeDefinition.setName(nonToscaType);
+        dataTypeDefinitionList.add(dataTypeDefinition);
+        assertTrue("Property type should match a data type in list",
+            propertyOperation.isPropertyTypeValid(propertyDefinition, model, dataTypeDefinitionList));
+        dataTypeDefinition.setName(nonToscaType + "dummyValue");
+        assertFalse("Property type should match a data type in list",
+            propertyOperation.isPropertyTypeValid(propertyDefinition, model, dataTypeDefinitionList));
+    }
 
 	
 	@Test
@@ -878,19 +944,19 @@
 		Either<DataTypeDefinition, StorageOperationStatus> result;
 		
         Mockito.doReturn(Either.left(new DataTypeData(dataTypeDefinition))).when(janusGraphGenericDao)
-            .createNode(Mockito.any(), Mockito.eq(DataTypeData.class));
+            .createNode(Mockito.any(), eq(DataTypeData.class));
         
         Mockito.doReturn(Either.left(new DataTypeData(dataTypeDefinition))).when(janusGraphGenericDao)
             .getNode(GraphPropertiesDictionary.NAME.getProperty(), dataTypeName, DataTypeData.class, null);
         
         Mockito.doReturn(Either.left(Collections.EMPTY_LIST)).when(janusGraphGenericDao)
-            .getChildrenNodes(Mockito.anyString(), Mockito.anyString(), Mockito.eq(GraphEdgeLabels.PROPERTY), Mockito.eq(NodeTypeEnum.Property), Mockito.eq(PropertyData.class));
+            .getChildrenNodes(Mockito.anyString(), Mockito.anyString(), eq(GraphEdgeLabels.PROPERTY), eq(NodeTypeEnum.Property), eq(PropertyData.class));
 
 		result = propertyOperation.addDataType(dataTypeDefinition);
         assertTrue(result.isLeft());
         
         Mockito.doReturn(Either.right(JanusGraphOperationStatus.NOT_FOUND)).when(janusGraphGenericDao)
-            .getChild(Mockito.anyString(), Mockito.anyString(), Mockito.eq(GraphEdgeLabels.DERIVED_FROM), Mockito.eq(NodeTypeEnum.DataType), Mockito.eq(DataTypeData.class));
+            .getChild(Mockito.anyString(), Mockito.anyString(), eq(GraphEdgeLabels.DERIVED_FROM), eq(NodeTypeEnum.DataType), eq(DataTypeData.class));
 		
 	    result = propertyOperation.getDataTypeByName(dataTypeName, null, false);
 	    assertTrue(result.isLeft());
@@ -916,10 +982,10 @@
 	        Either<DataTypeDefinition, StorageOperationStatus> result;
 
 	        Mockito.doReturn(Either.left(new DataTypeData(dataTypeDefinition))).when(janusGraphGenericDao)
-                .createNode(Mockito.any(), Mockito.eq(DataTypeData.class));
+                .createNode(Mockito.any(), eq(DataTypeData.class));
 	        
 	        Mockito.doReturn(Either.left(new GraphRelation())).when(janusGraphGenericDao)
-                .createRelation(Mockito.any(), Mockito.any(), Mockito.eq(GraphEdgeLabels.MODEL_ELEMENT), Mockito.any());
+                .createRelation(Mockito.any(), Mockito.any(), eq(GraphEdgeLabels.MODEL_ELEMENT), Mockito.any());
 
 	        result = propertyOperation.addDataType(dataTypeDefinition);
 	        assertTrue(result.isLeft());
@@ -928,10 +994,10 @@
 	            .getNode(GraphPropertiesDictionary.UNIQUE_ID.getProperty(), "testModel.testName.datatype", DataTypeData.class);
 	        
 	        Mockito.doReturn(Either.left(Collections.EMPTY_LIST)).when(janusGraphGenericDao)
-	            .getChildrenNodes(Mockito.anyString(), Mockito.anyString(), Mockito.eq(GraphEdgeLabels.PROPERTY), Mockito.eq(NodeTypeEnum.Property), Mockito.eq(PropertyData.class));
+	            .getChildrenNodes(Mockito.anyString(), Mockito.anyString(), eq(GraphEdgeLabels.PROPERTY), eq(NodeTypeEnum.Property), eq(PropertyData.class));
 	        
 	        Mockito.doReturn(Either.right(JanusGraphOperationStatus.NOT_FOUND)).when(janusGraphGenericDao)
-	            .getChild(Mockito.anyString(), Mockito.anyString(), Mockito.eq(GraphEdgeLabels.DERIVED_FROM), Mockito.eq(NodeTypeEnum.DataType), Mockito.eq(DataTypeData.class));
+	            .getChild(Mockito.anyString(), Mockito.anyString(), eq(GraphEdgeLabels.DERIVED_FROM), eq(NodeTypeEnum.DataType), eq(DataTypeData.class));
 	        
 	        Either<DataTypeDefinition, JanusGraphOperationStatus> resultGetByUid = propertyOperation.getDataTypeByUid("testModel.testName.datatype");
 	        assertTrue(resultGetByUid.isLeft());
diff --git a/catalog-model/src/test/resources/application-context-test.xml b/catalog-model/src/test/resources/application-context-test.xml
index 7f4ada2..206435b 100644
--- a/catalog-model/src/test/resources/application-context-test.xml
+++ b/catalog-model/src/test/resources/application-context-test.xml
@@ -11,10 +11,11 @@
     	org.openecomp.sdc.be.dao.jsongraph,
     	org.openecomp.sdc.be.model.cache,
     	org.openecomp.sdc.be.client,
-		org.openecomp.sdc.be.dao.janusgraph,
-		org.openecomp.sdc.be.dao.cassandra,
-		org.openecomp.sdc.be.model.jsonjanusgraph.utils,
-    org.openecomp.sdc.be.model.jsonjanusgraph.config">
+		  org.openecomp.sdc.be.dao.janusgraph,
+		  org.openecomp.sdc.be.dao.cassandra,
+		  org.openecomp.sdc.be.model.jsonjanusgraph.utils,
+      org.openecomp.sdc.be.model.jsonjanusgraph.config,
+      org.openecomp.sdc.be.model.converter">
 
    
   </context:component-scan>
diff --git a/common-app-api/src/main/java/org/openecomp/sdc/common/util/JsonUtils.java b/common-app-api/src/main/java/org/openecomp/sdc/common/util/JsonUtils.java
index 6ee4984..3a445d1 100644
--- a/common-app-api/src/main/java/org/openecomp/sdc/common/util/JsonUtils.java
+++ b/common-app-api/src/main/java/org/openecomp/sdc/common/util/JsonUtils.java
@@ -19,6 +19,7 @@
  */
 package org.openecomp.sdc.common.util;
 
+import com.google.gson.JsonArray;
 import com.google.gson.JsonElement;
 import com.google.gson.JsonObject;
 
@@ -47,8 +48,18 @@
         return json.entrySet().isEmpty();
     }
 
-    public static boolean isEmptyJson(JsonElement json) {
-        return json.isJsonPrimitive() ? false : JsonUtils.isEmptyJson(json.getAsJsonObject());
+    public static boolean isEmptyJson(final JsonArray json) {
+        return json.size() == 0;
+    }
+
+    public static boolean isEmptyJson(final JsonElement json) {
+        if (json.isJsonObject()) {
+            return isEmptyJson(json.getAsJsonObject());
+        } else if (json.isJsonArray()) {
+            return isEmptyJson(json.getAsJsonArray());
+        }
+
+        return false;
     }
 
     public static boolean isJsonNullOrEmpty(JsonObject json) {
diff --git a/common-be/src/main/java/org/openecomp/sdc/be/datatypes/enums/JsonPresentationFields.java b/common-be/src/main/java/org/openecomp/sdc/be/datatypes/enums/JsonPresentationFields.java
index 8fce664..74fe467 100644
--- a/common-be/src/main/java/org/openecomp/sdc/be/datatypes/enums/JsonPresentationFields.java
+++ b/common-be/src/main/java/org/openecomp/sdc/be/datatypes/enums/JsonPresentationFields.java
@@ -119,6 +119,16 @@
     ENTRY_SCHEMA("entry_schema", null),
     VALUE("value", null),
     PARENT_UNIQUE_ID("parentUniqueId", null),
+    LABEL("label", null),
+    IMMUTABLE("immutable", null),
+    HIDDEN("hidden", null),
+    INPUT_PATH("inputPath", null),
+    INPUT_ID("inputId", null),
+    INSTANCE_UNIQUE_ID("instanceUniqueId", null),
+    PROPERTY_CONSTRAINTS("propertyConstraints", null),
+    PROPERTY_ID("propertyId", null),
+    PARENT_PROPERTY_TYPE("parentPropertyType", null),
+    SUB_PROPERTY_INPUT_PATH("subPropertyInputPath", null),
 
     COMPONENT_INSTANCES("componentInstances", null),
     RELATIONS("relations", null),