Add robustness to type creation on service import 02/133902/4
authorMichaelMorris <michael.morris@est.tech>
Tue, 21 Mar 2023 16:31:56 +0000 (16:31 +0000)
committerFrancisco Javier Paradela Vila <javier.paradela.vila@est.tech>
Mon, 3 Apr 2023 12:46:35 +0000 (12:46 +0000)
Change-Id: I2c6bf2a13f8972c3c336ee032d4d0fda22f90938
Issue-ID: SDC-4355
Signed-off-by: MichaelMorris <michael.morris@est.tech>
catalog-be/src/main/java/org/openecomp/sdc/be/components/csar/CsarBusinessLogic.java
catalog-be/src/main/java/org/openecomp/sdc/be/components/csar/ServiceCsarInfo.java
catalog-be/src/test/java/org/openecomp/sdc/be/components/ResourceImportManagerTest.java
catalog-be/src/test/java/org/openecomp/sdc/be/components/csar/CsarBusinessLogicTest.java
catalog-be/src/test/java/org/openecomp/sdc/be/components/csar/ServiceCsarInfoTest.java
catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/ServiceImportBusinessLogicTest.java
catalog-be/src/test/java/org/openecomp/sdc/be/components/impl/ServiceImportParseLogicTest.java
catalog-model/src/main/java/org/openecomp/sdc/be/model/operations/impl/ModelOperation.java

index 0df8555..36c16be 100644 (file)
@@ -50,6 +50,7 @@ import org.openecomp.sdc.be.model.operations.api.IGroupTypeOperation;
 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
 import org.openecomp.sdc.be.model.operations.impl.CsarOperation;
 import org.openecomp.sdc.be.model.operations.impl.InterfaceLifecycleOperation;
+import org.openecomp.sdc.be.model.operations.impl.ModelOperation;
 import org.openecomp.sdc.be.resources.data.auditing.AuditingActionEnum;
 import org.openecomp.sdc.common.log.enums.EcompLoggerErrorCode;
 import org.openecomp.sdc.common.log.wrappers.Logger;
@@ -64,15 +65,17 @@ public class CsarBusinessLogic extends BaseBusinessLogic {
     private static final String FAILED = " failed";
     private final YamlTemplateParsingHandler yamlHandler;
     private CsarOperation csarOperation;
+    private ModelOperation modelOperation;
 
     @Autowired
     public CsarBusinessLogic(IElementOperation elementDao, IGroupOperation groupOperation, IGroupInstanceOperation groupInstanceOperation,
                              IGroupTypeOperation groupTypeOperation, InterfaceOperation interfaceOperation,
                              InterfaceLifecycleOperation interfaceLifecycleTypeOperation, YamlTemplateParsingHandler yamlHandler,
-                             ArtifactsOperations artifactToscaOperation) {
+                             ArtifactsOperations artifactToscaOperation, ModelOperation modelOperation) {
         super(elementDao, groupOperation, groupInstanceOperation, groupTypeOperation, interfaceOperation, interfaceLifecycleTypeOperation,
             artifactToscaOperation);
         this.yamlHandler = yamlHandler;
+        this.modelOperation = modelOperation;
     }
 
     @Autowired
@@ -160,7 +163,7 @@ public class CsarBusinessLogic extends BaseBusinessLogic {
             oldResource.getComponentMetadataDefinition().getMetadataDataDefinition().setImportedToscaChecksum(checksum);
         }
         return new ServiceCsarInfo(user, csarUUID, csar, service.getName(), service.getModel(), toscaYamlCsarStatus.getKey(),
-            toscaYamlCsarStatus.getValue(), true);
+            toscaYamlCsarStatus.getValue(), true, modelOperation);
     }
 
     public ParsedToscaYamlInfo getParsedToscaYamlInfo(String topologyTemplateYaml, String yamlName, Map<String, NodeTypeInfo> nodeTypesInfo,
index dc77c60..cd73f70 100644 (file)
@@ -35,13 +35,13 @@ import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
 import java.util.Set;
+
 import org.apache.commons.collections.CollectionUtils;
 import org.apache.commons.collections.MapUtils;
 import org.openecomp.sdc.be.components.impl.ImportUtils;
 import org.openecomp.sdc.be.components.impl.ImportUtils.ResultStatusEnum;
 import org.openecomp.sdc.be.components.impl.ImportUtils.ToscaElementTypeEnum;
 import org.openecomp.sdc.be.datatypes.enums.ResourceTypeEnum;
-import org.openecomp.sdc.be.model.InterfaceDefinition;
 import org.openecomp.sdc.be.model.NodeTypeDefinition;
 import org.openecomp.sdc.be.model.NodeTypeInfo;
 import org.openecomp.sdc.be.model.NodeTypeMetadata;
@@ -49,8 +49,10 @@ import org.openecomp.sdc.be.model.NullNodeTypeMetadata;
 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.operations.impl.ModelOperation;
 import org.openecomp.sdc.be.utils.TypeUtils;
 import org.openecomp.sdc.be.utils.TypeUtils.ToscaTagNamesEnum;
+import org.openecomp.sdc.common.api.Constants;
 import org.openecomp.sdc.common.log.wrappers.Logger;
 import org.yaml.snakeyaml.Yaml;
 
@@ -63,12 +65,14 @@ public class ServiceCsarInfo extends CsarInfo {
     private final Map<String, Map<String, Object>> mainTemplateImports;
     private List<NodeTypeDefinition> nodeTypeDefinitions;
     private final String model;
+    private final ModelOperation modelOperation;
 
     public ServiceCsarInfo(final User modifier, final String csarUUID, final Map<String, byte[]> csar,
                            final String vfResourceName, final String model,
-                           final String mainTemplateName, final String mainTemplateContent, final boolean isUpdate) {
+                           final String mainTemplateName, final String mainTemplateContent, final boolean isUpdate, final ModelOperation modelOperation) {
         super(modifier, csarUUID, csar, vfResourceName, mainTemplateName, mainTemplateContent, isUpdate);
         this.model = model;
+        this.modelOperation = modelOperation;
         final Path mainTemplateDir = Paths.get(getMainTemplateName().substring(0, getMainTemplateName().lastIndexOf('/') + 1));
         final Collection<Path> filesHandled = new HashSet<>();
         filesHandled.add(Paths.get(mainTemplateName));
@@ -190,7 +194,7 @@ public class ServiceCsarInfo extends CsarInfo {
         if (nodeTypeDefinitions == null) {
             nodeTypeDefinitions = new ArrayList<>();
             final Set<String> nodeTypesUsed = getNodeTypesUsedInToscaTemplate(getMappedToscaMainTemplate());
-            nodeTypeDefinitions.addAll(getNodeTypeDefinitions(nodeTypesUsed));
+            nodeTypeDefinitions.addAll(getNodeTypeDefinitions(nodeTypesUsed).values());
         }
         nodeTypeDefinitions = sortNodeTypesByDependencyOrder(nodeTypeDefinitions);
         return nodeTypeDefinitions;
@@ -226,11 +230,11 @@ public class ServiceCsarInfo extends CsarInfo {
         return dependencies;
     }
 
-    private Set<NodeTypeDefinition> getNodeTypeDefinitions(final Set<String> nodeTypesToGet) {
-        final Set<NodeTypeDefinition> foundNodeTypes = getTypes(nodeTypesToGet);
-        final Set<NodeTypeDefinition> nodeTypesToReturn = new HashSet<>(foundNodeTypes);
+    private Map<String, NodeTypeDefinition> getNodeTypeDefinitions(final Set<String> nodeTypesToGet) {
+        final Map<String, NodeTypeDefinition> foundNodeTypes = getTypes(nodeTypesToGet);
+        final Map<String, NodeTypeDefinition> nodeTypesToReturn = new HashMap<>(foundNodeTypes);
         final Set<String> recursiveNodeTypesToGet = new HashSet<>();
-        foundNodeTypes.forEach(nodeTypeDef -> {
+        foundNodeTypes.values().forEach(nodeTypeDef -> {
             Either<Object, ResultStatusEnum> derivedFromTypeEither =
                 findToscaElement((Map<String, Object>) nodeTypeDef.getMappedNodeType().getValue(), TypeUtils.ToscaTagNamesEnum.DERIVED_FROM,
                     ToscaElementTypeEnum.STRING);
@@ -240,25 +244,46 @@ public class ServiceCsarInfo extends CsarInfo {
         });
         recursiveNodeTypesToGet.removeAll(nodeTypesToGet);
         if (CollectionUtils.isNotEmpty(recursiveNodeTypesToGet)) {
-            nodeTypesToReturn.addAll(getNodeTypeDefinitions(recursiveNodeTypesToGet));
+            nodeTypesToReturn.putAll(getNodeTypeDefinitions(recursiveNodeTypesToGet));
         }
         return nodeTypesToReturn;
     }
 
 
-    private Set<NodeTypeDefinition> getTypes(final Set<String> nodeTypes) {
-        Set<NodeTypeDefinition> nodeTypeDefinitionsLocal = new HashSet<>();
-        mainTemplateImports.values().forEach(template -> {
-            final Map<String, Object> types = getTypesFromTemplate(template, ToscaTagNamesEnum.NODE_TYPES, nodeTypes);
-            if (MapUtils.isNotEmpty(types)) {
-                types.entrySet().forEach(typesEntry -> {
-                    final NodeTypeMetadata metadata =
-                        getMetaDataFromTemplate(template, typesEntry.getKey());
-                    nodeTypeDefinitionsLocal.add(new NodeTypeDefinition(typesEntry, metadata));
-                });
-            }
-        });
-        return nodeTypeDefinitionsLocal;
+    private Map<String, NodeTypeDefinition> getTypes(final Set<String> nodeTypes) {
+        final Map<String, NodeTypeDefinition> nodeTypeDefinitionsMap = new HashMap<>();
+        final Set<String> lowerPrecedenceImports = new HashSet<>();
+
+        if (model != null && !model.equals(Constants.DEFAULT_MODEL_NAME)) {
+            final Set<String> modelImports = new HashSet<>();
+            modelOperation.findAllModelImports(model, true).forEach(modelImport -> modelImports.add("Definitions/" + modelImport.getFullPath()));
+
+            lowerPrecedenceImports.add("Definitions/" + ModelOperation.ADDITIONAL_TYPE_DEFINITIONS_PATH);
+            lowerPrecedenceImports.addAll(modelImports);
+
+            mainTemplateImports.entrySet().stream().filter(entry -> modelImports.contains(entry.getKey()))
+                    .forEach(template -> addTypesFromTemplate(nodeTypeDefinitionsMap, template.getValue(), nodeTypes));
+
+            mainTemplateImports.entrySet().stream().filter(entry -> entry.getKey().equals(ModelOperation.ADDITIONAL_TYPE_DEFINITIONS_PATH.toString()))
+                    .forEach(template -> addTypesFromTemplate(nodeTypeDefinitionsMap, template.getValue(), nodeTypes));
+        }
+
+        mainTemplateImports.entrySet().stream().filter(entry -> !lowerPrecedenceImports.contains(entry.getKey()))
+                .forEach(template -> addTypesFromTemplate(nodeTypeDefinitionsMap, template.getValue(), nodeTypes));
+
+        return nodeTypeDefinitionsMap;
+    }
+
+    
+    private void addTypesFromTemplate(final Map<String, NodeTypeDefinition> nodeTypeDefinitionsMap, final Map<String, Object> mappedTemplate,
+            final Set<String> nodeTypes) {
+        final Map<String, Object> types = getTypesFromTemplate(mappedTemplate, ToscaTagNamesEnum.NODE_TYPES, nodeTypes);
+        if (MapUtils.isNotEmpty(types)) {
+            types.entrySet().forEach(typesEntry -> {
+                final NodeTypeMetadata metadata = getMetaDataFromTemplate(mappedTemplate, typesEntry.getKey());
+                nodeTypeDefinitionsMap.put(typesEntry.getKey(), new NodeTypeDefinition(typesEntry, metadata));
+            });
+        }
     }
 
     @SuppressWarnings("unchecked")
index 5c981e3..7822bd8 100644 (file)
@@ -100,6 +100,7 @@ import org.openecomp.sdc.be.model.User;
 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;
+import org.openecomp.sdc.be.model.operations.impl.ModelOperation;
 import org.openecomp.sdc.be.model.tosca.constraints.GreaterOrEqualConstraint;
 import org.openecomp.sdc.be.resources.data.auditing.AuditingActionEnum;
 import org.openecomp.sdc.be.user.UserBusinessLogic;
@@ -770,7 +771,7 @@ class ResourceImportManagerTest {
             assertNotNull(mainTemplateService);
             final String mainTemplateContent = new String(mainTemplateService);
 
-            return new ServiceCsarInfo(user, csarUuid, csar, vfReousrceName, null, mainTemplateName, mainTemplateContent, false);
+            return new ServiceCsarInfo(user, csarUuid, csar, vfReousrceName, null, mainTemplateName, mainTemplateContent, false, mock(ModelOperation.class));
         } catch (URISyntaxException | ZipException e) {
             fail(e);
         }
index 66c8a51..fec288a 100644 (file)
@@ -60,6 +60,7 @@ import org.openecomp.sdc.be.model.VendorSoftwareProduct;
 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.CsarOperation;
+import org.openecomp.sdc.be.model.operations.impl.ModelOperation;
 import org.openecomp.sdc.be.resources.data.auditing.AuditingActionEnum;
 import org.openecomp.sdc.common.zip.ZipUtils;
 import org.openecomp.sdc.common.zip.exception.ZipException;
@@ -73,9 +74,10 @@ class CsarBusinessLogicTest extends BaseBusinessLogicMock {
     private final ComponentsUtils componentsUtils = Mockito.mock(ComponentsUtils.class);
     private final User user = Mockito.mock(User.class);
     private final YamlTemplateParsingHandler yamlHandler = Mockito.mock(YamlTemplateParsingHandler.class);
+    private final ModelOperation modelOperation = Mockito.mock(ModelOperation.class);
 
     private final CsarBusinessLogic csarBusinessLogic = new CsarBusinessLogic(elementDao, groupOperation, groupInstanceOperation, groupTypeOperation,
-        interfaceOperation, interfaceLifecycleTypeOperation, yamlHandler, artifactToscaOperation);
+        interfaceOperation, interfaceLifecycleTypeOperation, yamlHandler, artifactToscaOperation, modelOperation);
 
     private static final String CSAR_UUID = "csarUUID";
     private static final String CSAR_ENTRY = "Definitions/tosca_mock_vf.yaml";
index a51c406..5260aea 100644 (file)
@@ -23,6 +23,8 @@ package org.openecomp.sdc.be.components.csar;
 
 import static org.junit.jupiter.api.Assertions.assertEquals;
 import static org.junit.jupiter.api.Assertions.assertNotNull;
+import static org.mockito.Mockito.mock;
+
 import java.io.File;
 import java.net.URISyntaxException;
 import java.util.Map;
@@ -33,6 +35,7 @@ import org.mockito.Mock;
 import org.mockito.junit.jupiter.MockitoExtension;
 import org.openecomp.sdc.be.config.ConfigurationManager;
 import org.openecomp.sdc.be.model.User;
+import org.openecomp.sdc.be.model.operations.impl.ModelOperation;
 import org.openecomp.sdc.common.impl.ExternalConfiguration;
 import org.openecomp.sdc.common.impl.FSConfigurationSource;
 import org.openecomp.sdc.common.zip.ZipUtils;
@@ -62,7 +65,7 @@ class ServiceCsarInfoTest {
         final File csarFile = new File(ServiceCsarInfoTest.class.getClassLoader().getResource(csarFileName).toURI());
         final Map<String, byte[]> payload = ZipUtils.readZip(csarFile, false);
         String mainTemplateContent = new String(payload.get(mainTemplateName));
-        return new ServiceCsarInfo(user, CSAR_UUID, payload, SERVICE_NAME, null, mainTemplateName, mainTemplateContent, true);
+        return new ServiceCsarInfo(user, CSAR_UUID, payload, SERVICE_NAME, null, mainTemplateName, mainTemplateContent, true, mock(ModelOperation.class));
     }
 
     @SuppressWarnings("unchecked")
index dc8e617..bd61fdb 100644 (file)
@@ -117,6 +117,7 @@ import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
 import org.openecomp.sdc.be.model.operations.impl.ArtifactTypeOperation;
 import org.openecomp.sdc.be.model.operations.impl.CapabilityTypeOperation;
 import org.openecomp.sdc.be.model.operations.impl.GroupTypeOperation;
+import org.openecomp.sdc.be.model.operations.impl.ModelOperation;
 import org.openecomp.sdc.be.resources.data.auditing.AuditingActionEnum;
 import org.openecomp.sdc.be.servlets.AbstractValidationsServlet;
 import org.openecomp.sdc.be.tosca.CsarUtils;
@@ -2500,7 +2501,7 @@ class ServiceImportBusinessLogicTest extends ServiceImportBussinessLogicBaseTest
             assertNotNull(mainTemplateService);
             final String mainTemplateContent = new String(mainTemplateService);
 
-            return new ServiceCsarInfo(user, csarUuid, csar, vfReousrceName, null, mainTemplateName, mainTemplateContent, false);
+            return new ServiceCsarInfo(user, csarUuid, csar, vfReousrceName, null, mainTemplateName, mainTemplateContent, false, mock(ModelOperation.class));
         } catch (URISyntaxException | ZipException e) {
             fail(e);
         }
index 66ba214..4f90947 100644 (file)
@@ -105,6 +105,7 @@ import org.openecomp.sdc.be.model.operations.api.ICapabilityTypeOperation;
 import org.openecomp.sdc.be.model.operations.api.IElementOperation;
 import org.openecomp.sdc.be.model.operations.api.IInterfaceLifecycleOperation;
 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
+import org.openecomp.sdc.be.model.operations.impl.ModelOperation;
 import org.openecomp.sdc.be.resources.data.auditing.AuditingActionEnum;
 import org.openecomp.sdc.be.user.Role;
 import org.openecomp.sdc.common.api.Constants;
@@ -2091,7 +2092,7 @@ class ServiceImportParseLogicTest extends ServiceImportBussinessLogicBaseTestSet
             assertNotNull(mainTemplateService);
             final String mainTemplateContent = new String(mainTemplateService);
             
-            return new ServiceCsarInfo(user, csarUuid, csar, vfReousrceName, null, mainTemplateName, mainTemplateContent, false);
+            return new ServiceCsarInfo(user, csarUuid, csar, vfReousrceName, null, mainTemplateName, mainTemplateContent, false, mock(ModelOperation.class));
         } catch (URISyntaxException | ZipException e) {
             fail(e);
         }
index 785ca41..3ff3fb0 100644 (file)
@@ -75,7 +75,7 @@ import org.yaml.snakeyaml.Yaml;
 @Component("model-operation")
 public class ModelOperation {
 
-    static final Path ADDITIONAL_TYPE_DEFINITIONS_PATH = Path.of(ADDITIONAL_TYPE_DEFINITIONS);
+    public static final Path ADDITIONAL_TYPE_DEFINITIONS_PATH = Path.of(ADDITIONAL_TYPE_DEFINITIONS);
     private static final Logger log = Logger.getLogger(ModelOperation.class);
     private final JanusGraphGenericDao janusGraphGenericDao;
     private final JanusGraphDao janusGraphDao;