Reformat catalog-be
[sdc.git] / catalog-be / src / main / java / org / openecomp / sdc / be / components / impl / ComponentBusinessLogic.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * SDC
4  * ================================================================================
5  * Copyright (C) 2017 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  * Modifications copyright (c) 2019 Nokia
20  * ================================================================================
21  */
22 package org.openecomp.sdc.be.components.impl;
23
24 import fj.data.Either;
25 import java.util.ArrayList;
26 import java.util.HashMap;
27 import java.util.List;
28 import java.util.Map;
29 import java.util.Map.Entry;
30 import java.util.Optional;
31 import java.util.function.BiFunction;
32 import java.util.function.BooleanSupplier;
33 import java.util.stream.Collectors;
34 import org.apache.commons.collections.CollectionUtils;
35 import org.apache.commons.lang3.StringUtils;
36 import org.apache.commons.lang3.tuple.ImmutablePair;
37 import org.openecomp.sdc.be.catalog.enums.ChangeTypeEnum;
38 import org.openecomp.sdc.be.components.impl.exceptions.ByActionStatusComponentException;
39 import org.openecomp.sdc.be.components.impl.exceptions.ByResponseFormatComponentException;
40 import org.openecomp.sdc.be.components.impl.exceptions.ComponentException;
41 import org.openecomp.sdc.be.components.impl.generic.GenericTypeBusinessLogic;
42 import org.openecomp.sdc.be.components.validation.component.ComponentContactIdValidator;
43 import org.openecomp.sdc.be.components.validation.component.ComponentDescriptionValidator;
44 import org.openecomp.sdc.be.components.validation.component.ComponentIconValidator;
45 import org.openecomp.sdc.be.components.validation.component.ComponentNameValidator;
46 import org.openecomp.sdc.be.components.validation.component.ComponentProjectCodeValidator;
47 import org.openecomp.sdc.be.components.validation.component.ComponentTagsValidator;
48 import org.openecomp.sdc.be.components.validation.component.ComponentValidator;
49 import org.openecomp.sdc.be.config.BeEcompErrorManager;
50 import org.openecomp.sdc.be.config.ConfigurationManager;
51 import org.openecomp.sdc.be.dao.api.ActionStatus;
52 import org.openecomp.sdc.be.dao.jsongraph.types.JsonParseFlagEnum;
53 import org.openecomp.sdc.be.dao.utils.MapUtil;
54 import org.openecomp.sdc.be.datamodel.api.HighestFilterEnum;
55 import org.openecomp.sdc.be.datatypes.components.ServiceMetadataDataDefinition;
56 import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
57 import org.openecomp.sdc.be.datatypes.enums.ComponentTypeEnum;
58 import org.openecomp.sdc.be.datatypes.enums.FilterKeyEnum;
59 import org.openecomp.sdc.be.datatypes.enums.NodeTypeEnum;
60 import org.openecomp.sdc.be.datatypes.enums.OriginTypeEnum;
61 import org.openecomp.sdc.be.datatypes.tosca.ToscaDataDefinition;
62 import org.openecomp.sdc.be.facade.operations.CatalogOperation;
63 import org.openecomp.sdc.be.impl.ComponentsUtils;
64 import org.openecomp.sdc.be.model.ArtifactDefinition;
65 import org.openecomp.sdc.be.model.AttributeDefinition;
66 import org.openecomp.sdc.be.model.CapReqDef;
67 import org.openecomp.sdc.be.model.Component;
68 import org.openecomp.sdc.be.model.ComponentInstance;
69 import org.openecomp.sdc.be.model.ComponentInstanceInput;
70 import org.openecomp.sdc.be.model.ComponentInstanceProperty;
71 import org.openecomp.sdc.be.model.ComponentParametersView;
72 import org.openecomp.sdc.be.model.DataTypeDefinition;
73 import org.openecomp.sdc.be.model.GroupDefinition;
74 import org.openecomp.sdc.be.model.IComponentInstanceConnectedElement;
75 import org.openecomp.sdc.be.model.InputDefinition;
76 import org.openecomp.sdc.be.model.LifecycleStateEnum;
77 import org.openecomp.sdc.be.model.Operation;
78 import org.openecomp.sdc.be.model.PropertyDefinition;
79 import org.openecomp.sdc.be.model.Resource;
80 import org.openecomp.sdc.be.model.User;
81 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ArtifactsOperations;
82 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.InterfaceOperation;
83 import org.openecomp.sdc.be.model.operations.api.IElementOperation;
84 import org.openecomp.sdc.be.model.operations.api.IGroupInstanceOperation;
85 import org.openecomp.sdc.be.model.operations.api.IGroupOperation;
86 import org.openecomp.sdc.be.model.operations.api.IGroupTypeOperation;
87 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
88 import org.openecomp.sdc.be.model.operations.impl.InterfaceLifecycleOperation;
89 import org.openecomp.sdc.be.model.tosca.ToscaPropertyType;
90 import org.openecomp.sdc.be.resources.data.ComponentMetadataData;
91 import org.openecomp.sdc.be.resources.data.auditing.AuditingActionEnum;
92 import org.openecomp.sdc.be.resources.data.auditing.model.ResourceCommonInfo;
93 import org.openecomp.sdc.be.resources.data.auditing.model.ResourceVersionInfo;
94 import org.openecomp.sdc.be.ui.model.UiComponentDataTransfer;
95 import org.openecomp.sdc.be.user.Role;
96 import org.openecomp.sdc.be.utils.CommonBeUtils;
97 import org.openecomp.sdc.common.api.ArtifactGroupTypeEnum;
98 import org.openecomp.sdc.common.api.ArtifactTypeEnum;
99 import org.openecomp.sdc.common.log.wrappers.Logger;
100 import org.openecomp.sdc.common.util.ValidationUtils;
101 import org.openecomp.sdc.exception.ResponseFormat;
102 import org.springframework.beans.factory.annotation.Autowired;
103
104 public abstract class ComponentBusinessLogic extends BaseBusinessLogic {
105
106     private static final Logger log = Logger.getLogger(ComponentBusinessLogic.class.getName());
107     protected final GroupBusinessLogic groupBusinessLogic;
108     protected ArtifactsBusinessLogic artifactsBusinessLogic;
109     protected GenericTypeBusinessLogic genericTypeBusinessLogic;
110     protected ComponentDescriptionValidator componentDescriptionValidator;
111     protected ComponentProjectCodeValidator componentProjectCodeValidator;
112     protected CatalogOperation catalogOperations;
113     protected ComponentIconValidator componentIconValidator;
114     protected ComponentValidator componentValidator;
115     protected ComponentTagsValidator componentTagsValidator;
116     protected ComponentNameValidator componentNameValidator;
117     protected ComponentContactIdValidator componentContactIdValidator;
118
119     public ComponentBusinessLogic(IElementOperation elementDao, IGroupOperation groupOperation, IGroupInstanceOperation groupInstanceOperation,
120                                   IGroupTypeOperation groupTypeOperation, GroupBusinessLogic groupBusinessLogic,
121                                   InterfaceOperation interfaceOperation, InterfaceLifecycleOperation interfaceLifecycleTypeOperation,
122                                   ArtifactsBusinessLogic artifactsBusinessLogic, ArtifactsOperations artifactToscaOperation,
123                                   ComponentContactIdValidator componentContactIdValidator, ComponentNameValidator componentNameValidator,
124                                   ComponentTagsValidator componentTagsValidator, ComponentValidator componentValidator,
125                                   ComponentIconValidator componentIconValidator, ComponentProjectCodeValidator componentProjectCodeValidator,
126                                   ComponentDescriptionValidator componentDescriptionValidator) {
127         super(elementDao, groupOperation, groupInstanceOperation, groupTypeOperation, interfaceOperation, interfaceLifecycleTypeOperation,
128             artifactToscaOperation);
129         this.artifactsBusinessLogic = artifactsBusinessLogic;
130         this.groupBusinessLogic = groupBusinessLogic;
131         this.componentContactIdValidator = componentContactIdValidator;
132         this.componentNameValidator = componentNameValidator;
133         this.componentTagsValidator = componentTagsValidator;
134         this.componentValidator = componentValidator;
135         this.componentIconValidator = componentIconValidator;
136         this.componentProjectCodeValidator = componentProjectCodeValidator;
137         this.componentDescriptionValidator = componentDescriptionValidator;
138     }
139
140     private static Either<ArtifactDefinition, Operation> saveToscaArtifactAndPopulateToscaArtifactsWithResult(Component component,
141                                                                                                               final ComponentsUtils componentsUtils,
142                                                                                                               final ArtifactTypeEnum artifactEnum,
143                                                                                                               final BiFunction<Component, ArtifactDefinition, Either<ArtifactDefinition, Operation>> saveToscaArtifactPayloadFunction) {
144         ArtifactDefinition artifactDefinition = getToscaArtifactByTypeOrThrowException(component, artifactEnum, componentsUtils);
145         Either<ArtifactDefinition, Operation> result = saveToscaArtifactPayloadFunction.apply(component, artifactDefinition);
146         if (result.isLeft()) {
147             ArtifactDefinition def = result.left().value();
148             component.getToscaArtifacts().put(def.getArtifactLabel(), def);
149         }
150         return result;
151     }
152
153     private static Optional<ArtifactDefinition> getToscaArtifactByType(final Map<String, ArtifactDefinition> toscaArtifacts,
154                                                                        final ArtifactTypeEnum typeEnum) {
155         return toscaArtifacts.values().stream().filter(p -> p.getArtifactType().equals(typeEnum.getType())).findAny();
156     }
157
158     private static ArtifactDefinition getToscaArtifactByTypeOrThrowException(final Component component, final ArtifactTypeEnum typeEnum,
159                                                                              final ComponentsUtils componentsUtils) {
160         return Optional.ofNullable(component.getToscaArtifacts()).flatMap(toscaArtifacts -> getToscaArtifactByType(toscaArtifacts, typeEnum))
161             .orElseThrow(() -> {
162                 log.debug("Impossible to find a ToscaArtifact with type '{}' for {}", typeEnum.getType(), component);
163                 return new ByResponseFormatComponentException(componentsUtils.getResponseFormat(ActionStatus.ARTIFACT_NOT_FOUND, typeEnum.name()));
164             });
165     }
166
167     public void setComponentDescriptionValidator(ComponentDescriptionValidator componentDescriptionValidator) {
168         this.componentDescriptionValidator = componentDescriptionValidator;
169     }
170
171     public void setComponentProjectCodeValidator(ComponentProjectCodeValidator componentProjectCodeValidator) {
172         this.componentProjectCodeValidator = componentProjectCodeValidator;
173     }
174
175     public void setComponentIconValidator(ComponentIconValidator componentIconValidator) {
176         this.componentIconValidator = componentIconValidator;
177     }
178
179     public void setComponentContactIdValidator(ComponentContactIdValidator componentContactIdValidator) {
180         this.componentContactIdValidator = componentContactIdValidator;
181     }
182
183     public void setComponentTagsValidator(ComponentTagsValidator componentTagsValidator) {
184         this.componentTagsValidator = componentTagsValidator;
185     }
186
187     public void setComponentNameValidator(ComponentNameValidator componentNameValidator) {
188         this.componentNameValidator = componentNameValidator;
189     }
190
191     @Autowired
192     public void setGenericTypeBusinessLogic(GenericTypeBusinessLogic genericTypeBusinessLogic) {
193         this.genericTypeBusinessLogic = genericTypeBusinessLogic;
194     }
195
196     public abstract Either<List<String>, ResponseFormat> deleteMarkedComponents();
197
198     public abstract ComponentInstanceBusinessLogic getComponentInstanceBL();
199
200     public abstract Either<List<ComponentInstance>, ResponseFormat> getComponentInstancesFilteredByPropertiesAndInputs(String componentId,
201                                                                                                                        String userId);
202
203     /**
204      * @param componentId
205      * @param dataParamsToReturn
206      * @return
207      */
208     public abstract Either<UiComponentDataTransfer, ResponseFormat> getUiComponentDataTransferByComponentId(String componentId,
209                                                                                                             List<String> dataParamsToReturn);
210
211     User validateUser(User user, String ecompErrorContext, Component component, AuditingActionEnum auditAction, boolean inTransaction) {
212         User validatedUser;
213         ResponseFormat responseFormat;
214         try {
215             validateUserNotEmpty(user, ecompErrorContext);
216             validatedUser = validateUserExists(user);
217         } catch (ByActionStatusComponentException e) {
218             if (e.getActionStatus() == ActionStatus.MISSING_INFORMATION) {
219                 user.setUserId("UNKNOWN");
220             }
221             responseFormat = componentsUtils.getResponseFormat(e.getActionStatus(), e.getParams());
222             componentsUtils.auditComponentAdmin(responseFormat, user, component, auditAction, component.getComponentType());
223             throw e;
224         } catch (ByResponseFormatComponentException e) {
225             responseFormat = e.getResponseFormat();
226             componentsUtils.auditComponentAdmin(responseFormat, user, component, auditAction, component.getComponentType());
227             throw e;
228         }
229         return validatedUser;
230     }
231
232     protected void validateUserRole(User user, Component component, List<Role> roles, AuditingActionEnum auditAction, String comment) {
233         if (roles != null && roles.isEmpty()) {
234             roles.add(Role.ADMIN);
235             roles.add(Role.DESIGNER);
236         }
237         try {
238             validateUserRole(user, roles);
239         } catch (ByActionStatusComponentException e) {
240             ResponseFormat responseFormat = componentsUtils.getResponseFormat(e.getActionStatus(), e.getParams());
241             handleComponentException(component, comment, responseFormat, user, auditAction);
242             throw e;
243         } catch (ByResponseFormatComponentException e) {
244             ResponseFormat responseFormat = e.getResponseFormat();
245             handleComponentException(component, comment, responseFormat, user, auditAction);
246             throw e;
247         }
248     }
249
250     private void handleComponentException(Component component, String comment, ResponseFormat responseFormat, User user,
251                                           AuditingActionEnum auditAction) {
252         String commentStr = null;
253         String distrStatus = null;
254         ComponentTypeEnum componentType = component.getComponentType();
255         if (componentType == ComponentTypeEnum.SERVICE) {
256             distrStatus = ((ServiceMetadataDataDefinition) component.getComponentMetadataDefinition().getMetadataDataDefinition())
257                 .getDistributionStatus();
258             commentStr = comment;
259         }
260         componentsUtils.auditComponent(responseFormat, user, component, auditAction, new ResourceCommonInfo(componentType.getValue()),
261             ResourceVersionInfo.newBuilder().distributionStatus(distrStatus).build(),
262             ResourceVersionInfo.newBuilder().distributionStatus(distrStatus).build(), commentStr, null, null);
263     }
264
265     public Either<Boolean, ResponseFormat> validateConformanceLevel(String componentUuid, ComponentTypeEnum componentTypeEnum, String userId) {
266         log.trace("validate conformance level");
267         if (componentTypeEnum != ComponentTypeEnum.SERVICE) {
268             log.error("conformance level validation for non service component, id {}", componentUuid);
269             ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.INVALID_CONTENT);
270             return Either.right(errorResponse);
271         }
272         validateUserExists(userId);
273         Either<ComponentMetadataData, StorageOperationStatus> eitherComponent = toscaOperationFacade
274             .getLatestComponentMetadataByUuid(componentUuid, JsonParseFlagEnum.ParseMetadata, null);
275         if (eitherComponent.isRight()) {
276             log.error("can't validate conformance level, component not found, uuid {}", componentUuid);
277             BeEcompErrorManager.getInstance().logBeComponentMissingError("validateConformanceLevel", componentTypeEnum.getValue(), componentUuid);
278             StorageOperationStatus status = eitherComponent.right().value();
279             ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(status, componentTypeEnum);
280             ResponseFormat responseFormat = componentsUtils.getResponseFormat(actionStatus);
281             return Either.right(responseFormat);
282         }
283         String componentConformanceLevel = eitherComponent.left().value().getMetadataDataDefinition().getConformanceLevel();
284         if (StringUtils.isBlank(componentConformanceLevel)) {
285             log.error("component conformance level property is null or empty, uuid {}", componentUuid);
286             ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR);
287             return Either.right(errorResponse);
288         }
289         String configConformanceLevel = ConfigurationManager.getConfigurationManager().getConfiguration().getMinToscaConformanceLevel();
290         Boolean result = true;
291         if (CommonBeUtils.conformanceLevelCompare(componentConformanceLevel, configConformanceLevel) < 0) {
292             log.error("invalid asset conformance level, uuid {}, asset conformanceLevel {}, config conformanceLevel {}", componentUuid,
293                 componentConformanceLevel, configConformanceLevel);
294             result = false;
295         }
296         log.trace("conformance level validation finished");
297         return Either.left(result);
298     }
299
300     protected void validateIcon(User user, Component component, AuditingActionEnum actionEnum) {
301         log.debug("validate Icon");
302         ComponentTypeEnum type = component.getComponentType();
303         String icon = component.getIcon();
304         if (!ValidationUtils.validateStringNotEmpty(icon)) {
305             log.info("icon is missing.");
306             ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.COMPONENT_MISSING_ICON, type.getValue());
307             componentsUtils.auditComponentAdmin(errorResponse, user, component, actionEnum, type);
308             throw new ComponentException(ActionStatus.COMPONENT_MISSING_ICON, type.getValue());
309         }
310         try {
311             validateIcon(icon, type);
312         } catch (ComponentException e) {
313             ResponseFormat responseFormat =
314                 e.getResponseFormat() != null ? e.getResponseFormat() : componentsUtils.getResponseFormat(e.getActionStatus(), e.getParams());
315             componentsUtils.auditComponentAdmin(responseFormat, user, component, actionEnum, type);
316             throw e;
317         }
318     }
319
320     private void validateIcon(String icon, ComponentTypeEnum type) {
321         if (icon != null) {
322             if (!ValidationUtils.validateIconLength(icon)) {
323                 log.debug("icon exceeds max length");
324                 throw new ComponentException(ActionStatus.COMPONENT_ICON_EXCEEDS_LIMIT, type.getValue(), "" + ValidationUtils.ICON_MAX_LENGTH);
325             }
326             if (!ValidationUtils.validateIcon(icon)) {
327                 log.info("icon is invalid.");
328                 throw new ComponentException(ActionStatus.COMPONENT_INVALID_ICON, type.getValue());
329             }
330         }
331     }
332
333     protected void checkComponentFieldsForOverrideAttempt(Component component) {
334         if (component.getLifecycleState() != null) {
335             log.info("LifecycleState cannot be defined by user. This field will be overridden by the application");
336         }
337         if (component.getVersion() != null) {
338             log.info("Version cannot be defined by user. This field will be overridden by the application");
339         }
340         if (component.getCreatorUserId() != null || component.getCreatorFullName() != null) {
341             log.info("Creator cannot be defined by user. This field will be overridden by the application");
342         }
343         if (component.getLastUpdaterUserId() != null || component.getLastUpdaterFullName() != null) {
344             log.info("Last Updater cannot be defined by user. This field will be overridden by the application");
345         }
346         if (component.getCreationDate() != null) {
347             log.info("Creation Date cannot be defined by user. This field will be overridden by the application");
348         }
349         if (component.isHighestVersion() != null) {
350             log.info("Is Highest Version cannot be defined by user. This field will be overridden by the application");
351         }
352         if (component.getUUID() != null) {
353             log.info("UUID cannot be defined by user. This field will be overridden by the application");
354         }
355         if (component.getLastUpdateDate() != null) {
356             log.info("Last Update Date cannot be defined by user. This field will be overridden by the application");
357         }
358         if (component.getUniqueId() != null) {
359             log.info("uid cannot be defined by user. This field will be overridden by the application.");
360             component.setUniqueId(null);
361         }
362         if (component.getInvariantUUID() != null) {
363             log.info("Invariant UUID cannot be defined by user. This field will be overridden by the application.");
364         }
365     }
366
367     protected void validateComponentFieldsBeforeCreate(User user, Component component, AuditingActionEnum actionEnum) {
368         // validate component name uniqueness
369         log.debug("validate component name ");
370         componentNameValidator.validateAndCorrectField(user, component, actionEnum);
371         // validate description
372         log.debug("validate description");
373         componentDescriptionValidator.validateAndCorrectField(user, component, actionEnum);
374         // validate tags
375         log.debug("validate tags");
376         componentTagsValidator.validateAndCorrectField(user, component, actionEnum);
377         // validate contact info
378         log.debug("validate contact info");
379         componentContactIdValidator.validateAndCorrectField(user, component, actionEnum);
380         // validate icon
381         log.debug("validate icon");
382         validateIcon(user, component, actionEnum);
383     }
384
385     public CapReqDef getRequirementsAndCapabilities(String componentId, ComponentTypeEnum componentTypeEnum, String userId) {
386         validateUserExists(userId);
387         ComponentParametersView filter = new ComponentParametersView(true);
388         filter.setIgnoreCapabilities(false);
389         filter.setIgnoreRequirements(false);
390         filter.setIgnoreComponentInstances(false);
391         try {
392             Component component = validateComponentExists(componentId, componentTypeEnum, filter);
393             return new CapReqDef(component.getRequirements(), component.getCapabilities());
394         } catch (ComponentException e) {
395             BeEcompErrorManager.getInstance().logBeComponentMissingError("getRequirementsAndCapabilities", componentTypeEnum.getValue(), componentId);
396             throwComponentException(e.getResponseFormat());
397         }
398         return null;
399     }
400
401     public Either<List<Component>, ResponseFormat> getLatestVersionNotAbstractComponents(boolean isAbstractAbstract,
402                                                                                          ComponentTypeEnum componentTypeEnum,
403                                                                                          String internalComponentType, List<String> componentUids,
404                                                                                          String userId) {
405         try {
406             validateUserExists(userId);
407             List<Component> result = new ArrayList<>();
408             List<String> componentsUidToFetch = new ArrayList<>();
409             componentsUidToFetch.addAll(componentUids);
410             if (!componentsUidToFetch.isEmpty()) {
411                 log.debug("Number of Components to fetch from graph is {}", componentsUidToFetch.size());
412                 Either<List<Component>, StorageOperationStatus> nonCheckoutCompResponse = toscaOperationFacade
413                     .getLatestVersionNotAbstractComponents(isAbstractAbstract, componentTypeEnum, internalComponentType, componentsUidToFetch);
414                 if (nonCheckoutCompResponse.isLeft()) {
415                     log.debug("Retrived Resource successfully.");
416                     result.addAll(nonCheckoutCompResponse.left().value());
417                 } else {
418                     return Either.right(
419                         componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(nonCheckoutCompResponse.right().value())));
420                 }
421             }
422             return Either.left(result);
423         } finally {
424             janusGraphDao.commit();
425         }
426     }
427
428     public Either<List<Component>, ResponseFormat> getLatestVersionNotAbstractComponentsMetadata(boolean isAbstractAbstract,
429                                                                                                  HighestFilterEnum highestFilter,
430                                                                                                  ComponentTypeEnum componentTypeEnum,
431                                                                                                  String internalComponentType, String userId) {
432         try {
433             validateUserExists(userId);
434             Either<List<Component>, StorageOperationStatus> nonCheckoutCompResponse = toscaOperationFacade
435                 .getLatestVersionNotAbstractMetadataOnly(isAbstractAbstract, componentTypeEnum, internalComponentType);
436             if (nonCheckoutCompResponse.isLeft()) {
437                 log.debug("Retrieved Resource successfully.");
438                 return Either.left(nonCheckoutCompResponse.left().value());
439             }
440             return Either
441                 .right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(nonCheckoutCompResponse.right().value())));
442         } finally {
443             janusGraphDao.commit();
444         }
445     }
446
447     public void setDeploymentArtifactsPlaceHolder(Component component, User user) {
448     }
449
450     @SuppressWarnings("unchecked")
451     public void setToscaArtifactsPlaceHolders(Component component, User user) {
452         Map<String, ArtifactDefinition> artifactMap = component.getToscaArtifacts();
453         if (artifactMap == null) {
454             artifactMap = new HashMap<>();
455         }
456         String componentUniqueId = component.getUniqueId();
457         String componentSystemName = component.getSystemName();
458         String componentType = component.getComponentType().getValue().toLowerCase();
459         Map<String, Object> toscaArtifacts = ConfigurationManager.getConfigurationManager().getConfiguration().getToscaArtifacts();
460         if (toscaArtifacts != null) {
461             for (Entry<String, Object> artifactInfoMap : toscaArtifacts.entrySet()) {
462                 Map<String, Object> artifactInfo = (Map<String, Object>) artifactInfoMap.getValue();
463                 ArtifactDefinition artifactDefinition = artifactsBusinessLogic
464                     .createArtifactPlaceHolderInfo(componentUniqueId, artifactInfoMap.getKey(), artifactInfo, user, ArtifactGroupTypeEnum.TOSCA);
465                 artifactDefinition
466                     .setArtifactName(ValidationUtils.normalizeFileName(componentType + "-" + componentSystemName + artifactInfo.get("artifactName")));
467                 artifactMap.put(artifactDefinition.getArtifactLabel(), artifactDefinition);
468             }
469         }
470         component.setToscaArtifacts(artifactMap);
471     }
472
473     public Either<ArtifactDefinition, Operation> populateToscaArtifacts(Component component, User user, boolean isInCertificationRequest,
474                                                                         boolean inTransaction, boolean shouldLock) {
475         return populateToscaArtifacts(component, user, isInCertificationRequest, inTransaction, shouldLock, true, true);
476     }
477
478     public Either<ArtifactDefinition, Operation> populateToscaArtifacts(Component component, User user, boolean isInCertificationRequest,
479                                                                         boolean inTransaction, boolean shouldLock, boolean retrieveResource) {
480         return populateToscaArtifacts(component, user, isInCertificationRequest, inTransaction, shouldLock, true, retrieveResource);
481     }
482
483     private Either<ArtifactDefinition, Operation> populateToscaArtifacts(Component component, User user, boolean isInCertificationRequest,
484                                                                          boolean inTransaction, boolean shouldLock, boolean fetchTemplatesFromDB,
485                                                                          boolean retrieveResource) {
486         if (retrieveResource) {
487             Either<Component, StorageOperationStatus> toscaElement = toscaOperationFacade.getToscaFullElement(component.getUniqueId());
488             if (toscaElement.isRight()) {
489                 throw new ByActionStatusComponentException(
490                     componentsUtils.convertFromStorageResponse(toscaElement.right().value(), component.getComponentType()));
491             }
492             component = toscaElement.left().value();
493         }
494         Either<ArtifactDefinition, Operation> generateToscaRes = saveToscaArtifactAndPopulateToscaArtifactsWithResult(component, componentsUtils,
495             ArtifactTypeEnum.TOSCA_TEMPLATE,
496             (comp, toscaArtifact) -> saveToscaArtifactPayload(toscaArtifact, comp, user, isInCertificationRequest, shouldLock, inTransaction,
497                 fetchTemplatesFromDB));
498         if (!isAbstractResource(component)) {
499             generateToscaRes = saveToscaArtifactAndPopulateToscaArtifactsWithResult(component, componentsUtils, ArtifactTypeEnum.TOSCA_CSAR,
500                 (comp, toscaArtifactArg) -> saveToscaArtifactPayload(toscaArtifactArg, comp, user, isInCertificationRequest, shouldLock,
501                     inTransaction, true));
502         }
503         return generateToscaRes;
504     }
505
506     private boolean isAbstractResource(Component component) {
507         return component.getComponentType() == ComponentTypeEnum.RESOURCE && ((Resource) component).isAbstract();
508     }
509
510     private Either<ArtifactDefinition, Operation> saveToscaArtifactPayload(ArtifactDefinition artifactDefinition,
511                                                                            org.openecomp.sdc.be.model.Component component, User user,
512                                                                            boolean isInCertificationRequest, boolean shouldLock,
513                                                                            boolean inTransaction, boolean fetchTemplatesFromDB) {
514         return artifactsBusinessLogic
515             .generateAndSaveToscaArtifact(artifactDefinition, component, user, isInCertificationRequest, shouldLock, inTransaction,
516                 fetchTemplatesFromDB);
517     }
518
519     public ImmutablePair<String, byte[]> getToscaModelByComponentUuid(ComponentTypeEnum componentType, String uuid,
520                                                                       ResourceCommonInfo resourceCommonInfo) {
521         Either<List<Component>, StorageOperationStatus> latestVersionEither = toscaOperationFacade.getComponentListByUuid(uuid, null);
522         if (latestVersionEither.isRight()) {
523             throw new ByActionStatusComponentException(
524                 componentsUtils.convertFromStorageResponse(latestVersionEither.right().value(), componentType));
525         }
526         List<Component> components = latestVersionEither.left().value();
527         Component component = components.stream().filter(Component::isHighestVersion).findFirst().orElse(null);
528         if (component == null) {
529             component = components.stream().filter(c -> c.getLifecycleState() == LifecycleStateEnum.CERTIFIED).findFirst().orElse(null);
530         }
531         if (component == null) {
532             throw new ByResponseFormatComponentException(
533                 componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(StorageOperationStatus.NOT_FOUND, componentType)));
534         }
535         resourceCommonInfo.setResourceName(component.getName());
536         // TODO remove after migration - handle artifact not found(no
537
538         // placeholder)
539         if (null == component.getToscaArtifacts() || component.getToscaArtifacts().isEmpty()) {
540             throw new ByResponseFormatComponentException(
541                 componentsUtils.getResponseFormat(ActionStatus.ARTIFACT_NOT_FOUND, ArtifactTypeEnum.TOSCA_CSAR.name()));
542         }
543         ArtifactDefinition csarArtifact = component.getToscaArtifacts().values().stream()
544             .filter(p -> p.getArtifactType().equals(ArtifactTypeEnum.TOSCA_CSAR.getType())).findAny().get();
545         return artifactsBusinessLogic.handleDownloadToscaModelRequest(component, csarArtifact);
546     }
547
548     protected StorageOperationStatus markComponentToDelete(Component component) {
549         ComponentTypeEnum componentType = component.getComponentType();
550         String uniqueId = component.getUniqueId();
551         if (Boolean.TRUE.equals(component.getIsDeleted())) {
552             log.info("component {} already marked as deleted. id= {}, type={}", component.getName(), uniqueId, componentType);
553             return StorageOperationStatus.NOT_FOUND;
554         }
555         StorageOperationStatus markResourceToDelete = toscaOperationFacade.markComponentToDelete(component);
556         if (StorageOperationStatus.OK != markResourceToDelete) {
557             log.debug("failed to mark component {} of type {} for delete. error = {}", uniqueId, componentType, markResourceToDelete);
558             return markResourceToDelete;
559         } else {
560             log.debug("Component {}  of type {} was marked as deleted", uniqueId, componentType);
561             updateCatalog(component, ChangeTypeEnum.DELETE);
562             return StorageOperationStatus.OK;
563         }
564     }
565
566     public Either<Boolean, ResponseFormat> validateAndUpdateDescription(User user, Component currentComponent, Component updatedComponent,
567                                                                         AuditingActionEnum auditingAction) {
568         String descriptionUpdated = updatedComponent.getDescription();
569         String descriptionCurrent = currentComponent.getDescription();
570         if (descriptionUpdated != null && !descriptionCurrent.equals(descriptionUpdated)) {
571             componentDescriptionValidator.validateAndCorrectField(user, updatedComponent, auditingAction);
572             currentComponent.setDescription(updatedComponent.getDescription());
573         }
574         return Either.left(true);
575     }
576
577     public Either<Boolean, ResponseFormat> validateAndUpdateProjectCode(User user, Component currentComponent, Component updatedComponent) {
578         String projectCodeUpdated = updatedComponent.getProjectCode();
579         String projectCodeCurrent = currentComponent.getProjectCode();
580         if (projectCodeUpdated != null && !projectCodeCurrent.equals(projectCodeUpdated)) {
581             try {
582                 componentProjectCodeValidator.validateAndCorrectField(user, updatedComponent, null);
583             } catch (ComponentException exp) {
584                 ResponseFormat errorRespons = exp.getResponseFormat();
585                 return Either.right(errorRespons);
586             }
587             currentComponent.setProjectCode(updatedComponent.getProjectCode());
588         }
589         return Either.left(true);
590     }
591
592     public Either<Boolean, ResponseFormat> validateAndUpdateIcon(User user, Component currentComponent, Component updatedComponent,
593                                                                  boolean hasBeenCertified) {
594         String iconUpdated = updatedComponent.getIcon();
595         String iconCurrent = currentComponent.getIcon();
596         if (iconUpdated != null && !iconCurrent.equals(iconUpdated)) {
597             if (!hasBeenCertified) {
598                 componentIconValidator.validateAndCorrectField(user, updatedComponent, null);
599                 currentComponent.setIcon(updatedComponent.getIcon());
600             } else {
601                 log.info("icon {} cannot be updated once the component has been certified once.", iconUpdated);
602                 ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.COMPONENT_PARAMETER_CANNOT_BE_CHANGED, "Icon",
603                     currentComponent.getComponentType().name().toLowerCase());
604                 return Either.right(errorResponse);
605             }
606         }
607         return Either.left(true);
608     }
609
610     protected Either<List<String>, ResponseFormat> deleteMarkedComponents(ComponentTypeEnum componentType) {
611         log.trace("start deleteMarkedComponents");
612         Either<List<String>, StorageOperationStatus> deleteMarkedElements = toscaOperationFacade.deleteMarkedElements(componentType);
613         if (deleteMarkedElements.isRight()) {
614             janusGraphDao.rollback();
615             ResponseFormat responseFormat = componentsUtils
616                 .getResponseFormat(componentsUtils.convertFromStorageResponse(deleteMarkedElements.right().value(), componentType));
617             return Either.right(responseFormat);
618         }
619         log.trace("end deleteMarkedComponents");
620         janusGraphDao.commit();
621         return Either.left(deleteMarkedElements.left().value());
622     }
623
624     public Either<List<ArtifactDefinition>, StorageOperationStatus> getComponentArtifactsForDelete(String parentId, NodeTypeEnum parentType) {
625         List<ArtifactDefinition> artifacts = new ArrayList<>();
626         Either<Map<String, ArtifactDefinition>, StorageOperationStatus> artifactsResponse = artifactToscaOperation.getArtifacts(parentId);
627         if (artifactsResponse.isRight()) {
628             if (artifactsResponse.right().value() != StorageOperationStatus.NOT_FOUND) {
629                 log.debug("failed to retrieve artifacts for {} {}", parentType, parentId);
630                 return Either.right(artifactsResponse.right().value());
631             }
632         } else {
633             artifacts.addAll(artifactsResponse.left().value().values());
634         }
635         return Either.left(artifacts);
636     }
637
638     /**
639      * @param componentId
640      * @param user
641      * @param dataParamsToReturn - ui list of params to return
642      * @return
643      */
644     public Either<UiComponentDataTransfer, ResponseFormat> getComponentDataFilteredByParams(String componentId, User user,
645                                                                                             List<String> dataParamsToReturn) {
646         if (user != null) {
647             validateUserExists(user);
648         }
649         UiComponentDataTransfer result = new UiComponentDataTransfer();
650         if (dataParamsToReturn == null || dataParamsToReturn.isEmpty()) {
651             Either.left(result);
652         } else {
653             Either<UiComponentDataTransfer, ResponseFormat> uiDataTransferEither = getUiComponentDataTransferByComponentId(componentId,
654                 dataParamsToReturn);
655             if (uiDataTransferEither.isRight()) {
656                 return Either.right(uiDataTransferEither.right().value());
657             }
658             result = uiDataTransferEither.left().value();
659         }
660         return Either.left(result);
661     }
662
663     protected <T extends Component> void generateAndAddInputsFromGenericTypeProperties(T component, Resource genericType) {
664         List<InputDefinition> genericAndComponentInputs = new ArrayList<>();
665         List<InputDefinition> genericInputs = genericTypeBusinessLogic.generateInputsFromGenericTypeProperties(genericType);
666         genericAndComponentInputs.addAll(genericInputs);
667         if (null != component.getInputs()) {
668             List<InputDefinition> nonGenericInputsFromComponent = getAllNonGenericInputsFromComponent(genericInputs, component.getInputs());
669             genericAndComponentInputs.addAll(nonGenericInputsFromComponent);
670         }
671         component.setInputs(genericAndComponentInputs);
672     }
673
674     private List<InputDefinition> getAllNonGenericInputsFromComponent(List<InputDefinition> genericInputs, List<InputDefinition> componentInputs) {
675         if (genericInputs == null) {
676             return componentInputs;
677         }
678         Map<String, InputDefinition> inputByNameMap = MapUtil.toMap(genericInputs, InputDefinition::getName);
679         List<InputDefinition> componentNonGenericInputs = new ArrayList<>();
680         componentInputs.stream().forEach(input -> {
681             if (!inputByNameMap.containsKey(input.getName())) {
682                 componentNonGenericInputs.add(input);
683             }
684         });
685         return componentNonGenericInputs;
686     }
687
688     protected <T extends Component> Resource fetchAndSetDerivedFromGenericType(T component) {
689         Either<Resource, ResponseFormat> genericTypeEither = this.genericTypeBusinessLogic.fetchDerivedFromGenericType(component);
690         if (genericTypeEither.isRight()) {
691             log.debug("Failed to fetch latest generic type for component {} of type", component.getName(), component.assetType());
692             throw new ByActionStatusComponentException(ActionStatus.GENERIC_TYPE_NOT_FOUND, component.assetType());
693         }
694         Resource genericTypeResource = genericTypeEither.left().value();
695         component.setDerivedFromGenericInfo(genericTypeResource);
696         return genericTypeResource;
697     }
698
699     public Either<Map<String, List<IComponentInstanceConnectedElement>>, ResponseFormat> getFilteredComponentInstanceProperties(String componentId,
700                                                                                                                                 Map<FilterKeyEnum, List<String>> filters,
701                                                                                                                                 String userId) {
702         Either<Map<String, List<IComponentInstanceConnectedElement>>, ResponseFormat> response = null;
703         Either<Component, StorageOperationStatus> getResourceRes = null;
704         try {
705             if (!filters.containsKey(FilterKeyEnum.NAME_FRAGMENT) && StringUtils.isEmpty(filters.get(FilterKeyEnum.NAME_FRAGMENT).get(0))) {
706                 response = Either.right(componentsUtils.getResponseFormat(ActionStatus.INVALID_CONTENT));
707             }
708             if (userId != null && response == null) {
709                 validateUserExists(userId);
710             }
711             if (response == null) {
712                 getResourceRes = toscaOperationFacade.getToscaElement(componentId);
713                 if (getResourceRes.isRight()) {
714                     response = Either
715                         .right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(getResourceRes.right().value())));
716                 }
717             }
718             if (response == null) {
719                 response = getFilteredComponentInstancesProperties(getResourceRes.left().value(), filters);
720             }
721         } catch (Exception e) {
722             log.debug("The exception {} occured during filtered instance properties fetching. the  containing component is {}. ", e, componentId);
723             response = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
724         } finally {
725             if (response != null && response.isLeft()) {
726                 toscaOperationFacade.commit();
727             } else {
728                 toscaOperationFacade.rollback();
729             }
730         }
731         return response;
732     }
733
734     private Either<Map<String, List<IComponentInstanceConnectedElement>>, ResponseFormat> getFilteredComponentInstancesProperties(Component component,
735                                                                                                                                   Map<FilterKeyEnum, List<String>> filters) {
736         Map<String, List<IComponentInstanceConnectedElement>> filteredProperties = new HashMap<>();
737         Either<Map<String, List<IComponentInstanceConnectedElement>>, ResponseFormat> result = Either.left(filteredProperties);
738         List<ComponentInstance> filteredInstances = getFilteredInstances(component, filters.get(FilterKeyEnum.RESOURCE_TYPE));
739         String propertyNameFragment = filters.get(FilterKeyEnum.NAME_FRAGMENT).get(0);
740         boolean searchByFragment = propertyNameFragment.length() > 3;
741         if (CollectionUtils.isNotEmpty(filteredInstances)) {
742             for (ComponentInstance instance : filteredInstances) {
743                 if (component.getComponentInstancesProperties() != null && component.getComponentInstancesProperties()
744                     .containsKey(instance.getUniqueId())) {
745                     List<IComponentInstanceConnectedElement> currProperties = getFilteredComponentInstanceProperties(
746                         component.getComponentInstancesProperties().get(instance.getUniqueId()), propertyNameFragment, searchByFragment);
747                     setFilteredProperties(filteredProperties, instance, currProperties);
748                 }
749                 if (component.getComponentInstancesInputs() != null && component.getComponentInstancesInputs().containsKey(instance.getUniqueId())) {
750                     List<IComponentInstanceConnectedElement> currInputs = getFilteredComponentInstanceInputs(
751                         component.getComponentInstancesInputs().get(instance.getUniqueId()), propertyNameFragment, searchByFragment);
752                     if (CollectionUtils.isNotEmpty(currInputs)) {
753                         checkFilteredProperties(filteredProperties, instance, currInputs);
754                     }
755                 }
756             }
757         }
758         return result;
759     }
760
761     private void setFilteredProperties(Map<String, List<IComponentInstanceConnectedElement>> filteredProperties, ComponentInstance instance,
762                                        List<IComponentInstanceConnectedElement> currProperties) {
763         if (CollectionUtils.isNotEmpty(currProperties)) {
764             filteredProperties.put(instance.getUniqueId(), currProperties);
765         }
766     }
767
768     private void checkFilteredProperties(Map<String, List<IComponentInstanceConnectedElement>> filteredProperties, ComponentInstance instance,
769                                          List<IComponentInstanceConnectedElement> currInputs) {
770         if (filteredProperties.get(instance.getUniqueId()) != null) {
771             filteredProperties.get(instance.getUniqueId()).addAll(currInputs);
772         } else {
773             filteredProperties.put(instance.getUniqueId(), currInputs);
774         }
775     }
776
777     private List<IComponentInstanceConnectedElement> getFilteredComponentInstanceInputs(List<ComponentInstanceInput> inputs,
778                                                                                         String propertyNameFragment, boolean searchByFragment) {
779         return inputs.stream().filter(i -> isMatchingInput(i, propertyNameFragment, searchByFragment)).collect(Collectors.toList());
780     }
781
782     private List<IComponentInstanceConnectedElement> getFilteredComponentInstanceProperties(List<ComponentInstanceProperty> instanceProperties,
783                                                                                             String propertyNameFragment, boolean searchByFragment) {
784         return instanceProperties.stream().filter(p -> isMatchingProperty(p, propertyNameFragment, searchByFragment)).collect(Collectors.toList());
785     }
786
787     private boolean isMatchingInput(ComponentInstanceInput input, String propertyNameFragment, boolean searchByFragment) {
788         boolean isMatching = false;
789         if (searchByFragment && input.getName().toLowerCase().contains(propertyNameFragment)) {
790             isMatching = true;
791         }
792         if (!searchByFragment && input.getName().equalsIgnoreCase(propertyNameFragment)) {
793             isMatching = true;
794         }
795         return isMatching;
796     }
797
798     private boolean isMatchingProperty(ComponentInstanceProperty property, String propertyNameFragment, boolean searchByFragment) {
799         boolean isMatching = false;
800         if (searchByFragment && property.getName().toLowerCase().contains(propertyNameFragment)) {
801             isMatching = true;
802         }
803         if (!searchByFragment && property.getName().equalsIgnoreCase(propertyNameFragment)) {
804             isMatching = true;
805         }
806         if (!isMatching && !ToscaPropertyType.isPrimitiveType(property.getType())) {
807             isMatching = isMatchingComplexPropertyByRecursively(property, propertyNameFragment, searchByFragment);
808         }
809         return isMatching;
810     }
811
812     private boolean isMatchingComplexPropertyByRecursively(PropertyDataDefinition property, String propertyNameFragment, boolean searchByFragment) {
813         String propertyType;
814         List<PropertyDefinition> dataTypeProperties;
815         DataTypeDefinition currentProperty;
816         if (searchByFragment && property.getName().toLowerCase().contains(propertyNameFragment.toLowerCase())) {
817             return true;
818         }
819         if (!searchByFragment && property.getName().equalsIgnoreCase(propertyNameFragment)) {
820             return true;
821         }
822         propertyType = isEmptyInnerType(property) ? property.getType() : property.getSchema().getProperty().getType();
823         if (ToscaPropertyType.isScalarType(propertyType)) {
824             return false;
825         }
826         Either<DataTypeDefinition, StorageOperationStatus> getDataTypeByNameRes = propertyOperation.getDataTypeByName(propertyType);
827         if (getDataTypeByNameRes.isRight()) {
828             return false;
829         }
830         currentProperty = getDataTypeByNameRes.left().value();
831         dataTypeProperties = currentProperty.getProperties();
832         boolean dataPropertiesNotNull = CollectionUtils.isNotEmpty(dataTypeProperties);
833         BooleanSupplier dataMatchesComplexProperty = () -> isMatchingComplexProperty(propertyNameFragment, searchByFragment, dataTypeProperties);
834         BooleanSupplier parentPropertiesNotNull = () -> CollectionUtils.isNotEmpty(currentProperty.getDerivedFrom().getProperties());
835         BooleanSupplier parentDataMatchesComplexProperty = () -> isMatchingComplexProperty(propertyNameFragment, searchByFragment,
836             currentProperty.getDerivedFrom().getProperties());
837         return ((dataPropertiesNotNull && dataMatchesComplexProperty.getAsBoolean()) || (parentPropertiesNotNull.getAsBoolean()
838             && parentDataMatchesComplexProperty.getAsBoolean()));
839     }
840
841     private boolean isMatchingComplexProperty(String propertyNameFragment, boolean searchByFragment, List<PropertyDefinition> dataTypeProperties) {
842         for (PropertyDefinition prop : dataTypeProperties) {
843             if (isMatchingComplexPropertyByRecursively(prop, propertyNameFragment, searchByFragment)) {
844                 return true;
845             }
846         }
847         return false;
848     }
849
850     private boolean isEmptyInnerType(PropertyDataDefinition property) {
851         return property == null || property.getSchema() == null || property.getSchema().getProperty() == null
852             || property.getSchema().getProperty().getType() == null;
853     }
854
855     public Either<Boolean, ResponseFormat> shouldUpgradeToLatestGeneric(Component clonedComponent) {
856         if (!clonedComponent.deriveFromGeneric()) {
857             return Either.left(false);
858         }
859         Boolean shouldUpgrade = false;
860         String currentGenericType = clonedComponent.getDerivedFromGenericType();
861         String currentGenericVersion = clonedComponent.getDerivedFromGenericVersion();
862         Resource genericTypeResource = fetchAndSetDerivedFromGenericType(clonedComponent);
863         if (null == currentGenericType || !currentGenericType.equals(genericTypeResource.getToscaResourceName()) || !currentGenericVersion
864             .equals(genericTypeResource.getVersion())) {
865             shouldUpgrade = upgradeToLatestGeneric(clonedComponent, genericTypeResource);
866             if (!shouldUpgrade) {
867                 reverntUpdateOfGenericVersion(clonedComponent, currentGenericType, currentGenericVersion);
868             }
869         }
870         return Either.left(shouldUpgrade);
871     }
872
873     private void reverntUpdateOfGenericVersion(Component clonedComponent, String currentGenericType, String currentGenericVersion) {
874         clonedComponent.setDerivedFromGenericType(currentGenericType);
875         clonedComponent.setDerivedFromGenericVersion(currentGenericVersion);
876     }
877
878     private <T extends ToscaDataDefinition> Either<Map<String, T>, String> validateNoConflictingProperties(List<T> currentList,
879                                                                                                            List<T> upgradedList) {
880         Map<String, T> currentMap = ToscaDataDefinition.listToMapByName(currentList);
881         Map<String, T> upgradedMap = ToscaDataDefinition.listToMapByName(upgradedList);
882         return ToscaDataDefinition.mergeDataMaps(upgradedMap, currentMap, true);
883     }
884
885     private boolean shouldUpgradeNodeType(Component componentToCheckOut, Resource latestGeneric) {
886         List<PropertyDefinition> genericTypeProps = latestGeneric.getProperties();
887         Either<Map<String, PropertyDefinition>, String> validPropertiesMerge = validateNoConflictingProperties(genericTypeProps,
888             ((Resource) componentToCheckOut).getProperties());
889         if (validPropertiesMerge.isRight()) {
890             log.debug("property {} cannot be overriden, check out performed without upgrading to latest generic",
891                 validPropertiesMerge.right().value());
892             return false;
893         }
894         List<AttributeDefinition> genericTypeAttributes = latestGeneric.getAttributes();
895         final Either<Map<String, AttributeDefinition>, String> validAttributesMerge = validateNoConflictingProperties(genericTypeAttributes,
896             ((Resource) componentToCheckOut).getAttributes());
897         if (validAttributesMerge.isRight()) {
898             log.debug("attribute {} cannot be overriden, check out performed without upgrading to latest generic",
899                 validAttributesMerge.right().value());
900             return false;
901         }
902         return true;
903     }
904
905     private boolean upgradeToLatestGeneric(Component componentToCheckOut, Resource latestGeneric) {
906         if (!componentToCheckOut.shouldGenerateInputs()) {
907             //node type - validate properties and attributes
908             return shouldUpgradeNodeType(componentToCheckOut, latestGeneric);
909         }
910         List<PropertyDefinition> genericTypeProps = latestGeneric.getProperties();
911         List<InputDefinition> genericTypeInputs = null == genericTypeProps ? null
912             : genericTypeBusinessLogic.convertGenericTypePropertiesToInputsDefintion(genericTypeProps, latestGeneric.getUniqueId());
913         List<InputDefinition> currentList = new ArrayList<>();
914         // nullify existing ownerId from existing list and merge into updated list
915         if (null != componentToCheckOut.getInputs()) {
916             for (InputDefinition input : componentToCheckOut.getInputs()) {
917                 InputDefinition copy = new InputDefinition(input);
918                 copy.setOwnerId(null);
919                 currentList.add(copy);
920             }
921         }
922         if (null == genericTypeInputs) {
923             componentToCheckOut.setInputs(currentList);
924             return true;
925         }
926         Either<Map<String, InputDefinition>, String> eitherMerged = validateNoConflictingProperties(genericTypeInputs, currentList);
927         if (eitherMerged.isRight()) {
928             log.debug("input {} cannot be overriden, check out performed without upgrading to latest generic", eitherMerged.right().value());
929             return false;
930         }
931         componentToCheckOut.setInputs(new ArrayList<>(eitherMerged.left().value().values()));
932         return true;
933     }
934
935     private List<ComponentInstance> getFilteredInstances(Component component, List<String> resourceTypes) {
936         List<ComponentInstance> filteredInstances = null;
937         if (CollectionUtils.isEmpty(resourceTypes)) {
938             filteredInstances = component.getComponentInstances();
939         } else if (CollectionUtils.isNotEmpty(component.getComponentInstances())) {
940             filteredInstances = component.getComponentInstances().stream().filter(i -> isMatchingType(i.getOriginType(), resourceTypes))
941                 .collect(Collectors.toList());
942         }
943         if (filteredInstances == null) {
944             filteredInstances = new ArrayList<>();
945         }
946         return filteredInstances;
947     }
948
949     private boolean isMatchingType(OriginTypeEnum originType, List<String> resourceTypes) {
950         boolean isMatchingType = false;
951         for (String resourceType : resourceTypes) {
952             if (originType == OriginTypeEnum.findByValue(resourceType.toUpperCase())) {
953                 isMatchingType = true;
954                 break;
955             }
956         }
957         return isMatchingType;
958     }
959
960     public Either<Component, ActionStatus> shouldUpgradeToLatestDerived(Component clonedComponent) {
961         //general implementation. Must be error for service, VF . In ResourceBuisnessLogic exist override
962         return Either.right(ActionStatus.GENERAL_ERROR);
963     }
964
965     protected Either<Component, ResponseFormat> updateCatalog(Component component, ChangeTypeEnum changeStatus) {
966         log.debug("update Catalog start with Component Type {} And Componet Name {} with change status {}", component.getComponentType().name(),
967             component.getName(), changeStatus.name());
968         ActionStatus status = catalogOperations.updateCatalog(changeStatus, component);
969         if (status != ActionStatus.OK) {
970             return Either.right(componentsUtils.getResponseFormat(status));
971         }
972         return Either.left(component);
973     }
974
975     public CatalogOperation getCatalogOperations() {
976         return catalogOperations;
977     }
978
979     @Autowired
980     public void setCatalogOperations(CatalogOperation catalogOperations) {
981         this.catalogOperations = catalogOperations;
982     }
983
984     public List<GroupDefinition> throwComponentException(ResponseFormat responseFormat) {
985         throw new ByResponseFormatComponentException(responseFormat);
986     }
987 }