Reformat catalog-model
[sdc.git] / catalog-model / src / main / java / org / openecomp / sdc / be / model / jsonjanusgraph / operations / ToscaOperationFacade.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * SDC
4  * ================================================================================
5  * Copyright (C) 2017 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  */
20 package org.openecomp.sdc.be.model.jsonjanusgraph.operations;
21
22 import static java.util.Objects.requireNonNull;
23 import static org.apache.commons.collections.CollectionUtils.isEmpty;
24 import static org.apache.commons.collections.CollectionUtils.isNotEmpty;
25 import static org.janusgraph.core.attribute.Text.REGEX;
26
27 import com.vdurmont.semver4j.Semver;
28 import com.vdurmont.semver4j.Semver.SemverType;
29 import fj.data.Either;
30 import java.util.ArrayList;
31 import java.util.Arrays;
32 import java.util.Collection;
33 import java.util.Collections;
34 import java.util.EnumMap;
35 import java.util.HashMap;
36 import java.util.HashSet;
37 import java.util.Iterator;
38 import java.util.LinkedList;
39 import java.util.List;
40 import java.util.Map;
41 import java.util.Map.Entry;
42 import java.util.Optional;
43 import java.util.Set;
44 import java.util.function.BiPredicate;
45 import java.util.stream.Collectors;
46 import org.apache.commons.collections.CollectionUtils;
47 import org.apache.commons.collections.MapUtils;
48 import org.apache.commons.lang3.StringUtils;
49 import org.apache.commons.lang3.tuple.ImmutablePair;
50 import org.apache.tinkerpop.gremlin.structure.Direction;
51 import org.apache.tinkerpop.gremlin.structure.Edge;
52 import org.janusgraph.graphdb.query.JanusGraphPredicate;
53 import org.openecomp.sdc.be.config.Configuration;
54 import org.openecomp.sdc.be.config.ConfigurationManager;
55 import org.openecomp.sdc.be.dao.janusgraph.JanusGraphOperationStatus;
56 import org.openecomp.sdc.be.dao.jsongraph.GraphVertex;
57 import org.openecomp.sdc.be.dao.jsongraph.HealingJanusGraphDao;
58 import org.openecomp.sdc.be.dao.jsongraph.types.EdgeLabelEnum;
59 import org.openecomp.sdc.be.dao.jsongraph.types.JsonParseFlagEnum;
60 import org.openecomp.sdc.be.dao.jsongraph.types.VertexTypeEnum;
61 import org.openecomp.sdc.be.datatypes.elements.ArtifactDataDefinition;
62 import org.openecomp.sdc.be.datatypes.elements.AttributeDataDefinition;
63 import org.openecomp.sdc.be.datatypes.elements.CapabilityDataDefinition;
64 import org.openecomp.sdc.be.datatypes.elements.ComponentInstanceDataDefinition;
65 import org.openecomp.sdc.be.datatypes.elements.DataTypeDataDefinition;
66 import org.openecomp.sdc.be.datatypes.elements.GroupDataDefinition;
67 import org.openecomp.sdc.be.datatypes.elements.ListCapabilityDataDefinition;
68 import org.openecomp.sdc.be.datatypes.elements.ListRequirementDataDefinition;
69 import org.openecomp.sdc.be.datatypes.elements.MapArtifactDataDefinition;
70 import org.openecomp.sdc.be.datatypes.elements.MapAttributesDataDefinition;
71 import org.openecomp.sdc.be.datatypes.elements.MapCapabilityProperty;
72 import org.openecomp.sdc.be.datatypes.elements.MapInterfaceDataDefinition;
73 import org.openecomp.sdc.be.datatypes.elements.MapListCapabilityDataDefinition;
74 import org.openecomp.sdc.be.datatypes.elements.MapListRequirementDataDefinition;
75 import org.openecomp.sdc.be.datatypes.elements.MapPropertiesDataDefinition;
76 import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
77 import org.openecomp.sdc.be.datatypes.elements.RequirementDataDefinition;
78 import org.openecomp.sdc.be.datatypes.enums.ComponentTypeEnum;
79 import org.openecomp.sdc.be.datatypes.enums.GraphPropertyEnum;
80 import org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields;
81 import org.openecomp.sdc.be.datatypes.enums.OriginTypeEnum;
82 import org.openecomp.sdc.be.datatypes.enums.PromoteVersionEnum;
83 import org.openecomp.sdc.be.datatypes.enums.ResourceTypeEnum;
84 import org.openecomp.sdc.be.model.ArtifactDefinition;
85 import org.openecomp.sdc.be.model.AttributeDefinition;
86 import org.openecomp.sdc.be.model.CapabilityDefinition;
87 import org.openecomp.sdc.be.model.CatalogUpdateTimestamp;
88 import org.openecomp.sdc.be.model.Component;
89 import org.openecomp.sdc.be.model.ComponentInstance;
90 import org.openecomp.sdc.be.model.ComponentInstanceAttribute;
91 import org.openecomp.sdc.be.model.ComponentInstanceInput;
92 import org.openecomp.sdc.be.model.ComponentInstanceInterface;
93 import org.openecomp.sdc.be.model.ComponentInstanceOutput;
94 import org.openecomp.sdc.be.model.ComponentInstanceProperty;
95 import org.openecomp.sdc.be.model.ComponentParametersView;
96 import org.openecomp.sdc.be.model.DataTypeDefinition;
97 import org.openecomp.sdc.be.model.DistributionStatusEnum;
98 import org.openecomp.sdc.be.model.GroupDefinition;
99 import org.openecomp.sdc.be.model.GroupInstance;
100 import org.openecomp.sdc.be.model.InputDefinition;
101 import org.openecomp.sdc.be.model.LifecycleStateEnum;
102 import org.openecomp.sdc.be.model.OutputDefinition;
103 import org.openecomp.sdc.be.model.PolicyDefinition;
104 import org.openecomp.sdc.be.model.PropertyDefinition;
105 import org.openecomp.sdc.be.model.RelationshipInfo;
106 import org.openecomp.sdc.be.model.RequirementCapabilityRelDef;
107 import org.openecomp.sdc.be.model.RequirementDefinition;
108 import org.openecomp.sdc.be.model.Resource;
109 import org.openecomp.sdc.be.model.Service;
110 import org.openecomp.sdc.be.model.User;
111 import org.openecomp.sdc.be.model.catalog.CatalogComponent;
112 import org.openecomp.sdc.be.model.jsonjanusgraph.config.ContainerInstanceTypesData;
113 import org.openecomp.sdc.be.model.jsonjanusgraph.datamodel.TopologyTemplate;
114 import org.openecomp.sdc.be.model.jsonjanusgraph.datamodel.ToscaElement;
115 import org.openecomp.sdc.be.model.jsonjanusgraph.utils.ModelConverter;
116 import org.openecomp.sdc.be.model.operations.StorageException;
117 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
118 import org.openecomp.sdc.be.model.operations.impl.DaoStatusConverter;
119 import org.openecomp.sdc.be.model.operations.impl.UniqueIdBuilder;
120 import org.openecomp.sdc.be.model.utils.GroupUtils;
121 import org.openecomp.sdc.be.resources.data.ComponentMetadataData;
122 import org.openecomp.sdc.common.jsongraph.util.CommonUtility;
123 import org.openecomp.sdc.common.jsongraph.util.CommonUtility.LogLevelEnum;
124 import org.openecomp.sdc.common.log.wrappers.Logger;
125 import org.openecomp.sdc.common.util.ValidationUtils;
126 import org.springframework.beans.factory.annotation.Autowired;
127
128 @org.springframework.stereotype.Component("tosca-operation-facade")
129 public class ToscaOperationFacade {
130
131     // region - ToscaElement - GetById
132     public static final String PROXY_SUFFIX = "_proxy";
133     // region - Fields
134     private static final String COULDNT_FETCH_A_COMPONENT_WITH_AND_UNIQUE_ID_ERROR = "Couldn't fetch a component with and UniqueId {}, error: {}";
135     private static final String FAILED_TO_FIND_RECENTLY_ADDED_PROPERTY_ON_THE_RESOURCE_STATUS_IS = "Failed to find recently added property {} on the resource {}. Status is {}. ";
136     private static final String FAILED_TO_GET_UPDATED_RESOURCE_STATUS_IS = "Failed to get updated resource {}. Status is {}. ";
137     private static final String FAILED_TO_ADD_THE_PROPERTY_TO_THE_RESOURCE_STATUS_IS = "Failed to add the property {} to the resource {}. Status is {}. ";
138     private static final String SERVICE = "service";
139     private static final String NOT_SUPPORTED_COMPONENT_TYPE = "Not supported component type {}";
140     private static final String COMPONENT_CREATED_SUCCESSFULLY = "Component created successfully!!!";
141     private static final String COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR = "Couldn't fetch component with and unique id {}, error: {}";
142     private static final Logger log = Logger.getLogger(ToscaOperationFacade.class.getName());
143     @Autowired
144     private NodeTypeOperation nodeTypeOperation;
145     @Autowired
146     private TopologyTemplateOperation topologyTemplateOperation;
147     @Autowired
148     private NodeTemplateOperation nodeTemplateOperation;
149     @Autowired
150     private GroupsOperation groupsOperation;
151     @Autowired
152     private HealingJanusGraphDao janusGraphDao;
153     // endregion
154     @Autowired
155     private ContainerInstanceTypesData containerInstanceTypesData;
156
157     private static Optional<CapabilityDefinition> getPropertyCapability(String propertyParentUniqueId, Component containerComponent) {
158         Map<String, List<CapabilityDefinition>> componentCapabilities = containerComponent.getCapabilities();
159         if (MapUtils.isEmpty(componentCapabilities)) {
160             return Optional.empty();
161         }
162         List<CapabilityDefinition> capabilityDefinitionList = componentCapabilities.values().stream().flatMap(Collection::stream)
163             .collect(Collectors.toList());
164         if (CollectionUtils.isEmpty(capabilityDefinitionList)) {
165             return Optional.empty();
166         }
167         return capabilityDefinitionList.stream().filter(capabilityDefinition -> capabilityDefinition.getUniqueId().equals(propertyParentUniqueId))
168             .findAny();
169     }
170
171     public <T extends Component> Either<T, StorageOperationStatus> getToscaFullElement(String componentId) {
172         ComponentParametersView filters = new ComponentParametersView();
173         filters.setIgnoreCapabiltyProperties(false);
174         filters.setIgnoreServicePath(false);
175         return getToscaElement(componentId, filters);
176     }
177
178     public <T extends Component> Either<T, StorageOperationStatus> getToscaElement(String componentId) {
179         return getToscaElement(componentId, JsonParseFlagEnum.ParseAll);
180     }
181
182     public <T extends Component> Either<T, StorageOperationStatus> getToscaElement(String componentId, ComponentParametersView filters) {
183         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, filters.detectParseFlag());
184         if (getVertexEither.isRight()) {
185             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
186             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
187         }
188         return getToscaElementByOperation(getVertexEither.left().value(), filters);
189     }
190
191     public <T extends Component> Either<T, StorageOperationStatus> getToscaElement(String componentId, JsonParseFlagEnum parseFlag) {
192         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, parseFlag);
193         if (getVertexEither.isRight()) {
194             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
195             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
196         }
197         return getToscaElementByOperation(getVertexEither.left().value());
198     }
199
200     public <T extends Component> Either<T, StorageOperationStatus> getToscaElement(GraphVertex componentVertex) {
201         return getToscaElementByOperation(componentVertex);
202     }
203
204     public Either<Boolean, StorageOperationStatus> validateComponentExists(String componentId) {
205         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
206         if (getVertexEither.isRight()) {
207             JanusGraphOperationStatus status = getVertexEither.right().value();
208             if (status == JanusGraphOperationStatus.NOT_FOUND) {
209                 return Either.left(false);
210             } else {
211                 log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
212                 return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
213             }
214         }
215         return Either.left(true);
216     }
217     // endregion
218
219     public <T extends Component> Either<T, StorageOperationStatus> findLastCertifiedToscaElementByUUID(T component) {
220         Map<GraphPropertyEnum, Object> props = new EnumMap<>(GraphPropertyEnum.class);
221         props.put(GraphPropertyEnum.UUID, component.getUUID());
222         props.put(GraphPropertyEnum.STATE, LifecycleStateEnum.CERTIFIED.name());
223         props.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
224         Either<List<GraphVertex>, JanusGraphOperationStatus> getVertexEither = janusGraphDao
225             .getByCriteria(ModelConverter.getVertexType(component), props);
226         if (getVertexEither.isRight()) {
227             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, component.getUniqueId(), getVertexEither.right().value());
228             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
229         }
230         return getToscaElementByOperation(getVertexEither.left().value().get(0));
231     }
232
233     // region - ToscaElement - GetByOperation
234     private <T extends Component> Either<T, StorageOperationStatus> getToscaElementByOperation(GraphVertex componentV) {
235         return getToscaElementByOperation(componentV, new ComponentParametersView());
236     }
237
238     private <T extends Component> Either<T, StorageOperationStatus> getToscaElementByOperation(GraphVertex componentV,
239                                                                                                ComponentParametersView filters) {
240         if (componentV == null) {
241             log.debug("Unexpected null value for `componentV`");
242             return Either.right(StorageOperationStatus.GENERAL_ERROR);
243         } else {
244             VertexTypeEnum label = componentV.getLabel();
245             ToscaElementOperation toscaOperation = getToscaElementOperation(componentV);
246             if (toscaOperation != null) {
247                 log.debug("getToscaElementByOperation: toscaOperation={}", toscaOperation.getClass());
248             }
249             Either<ToscaElement, StorageOperationStatus> toscaElement;
250             String componentId = componentV.getUniqueId();
251             if (toscaOperation != null) {
252                 log.debug("Need to fetch tosca element for id {}", componentId);
253                 toscaElement = toscaOperation.getToscaElement(componentV, filters);
254             } else {
255                 log.debug("not supported tosca type {} for id {}", label, componentId);
256                 toscaElement = Either.right(StorageOperationStatus.BAD_REQUEST);
257             }
258             return toscaElement.left().map(ModelConverter::convertFromToscaElement);
259         }
260     }
261
262     // endregion
263     private ToscaElementOperation getToscaElementOperation(GraphVertex componentV) {
264         VertexTypeEnum label = componentV.getLabel();
265         switch (label) {
266             case NODE_TYPE:
267                 return nodeTypeOperation;
268             case TOPOLOGY_TEMPLATE:
269                 return topologyTemplateOperation;
270             default:
271                 return null;
272         }
273     }
274
275     public <T extends Component> Either<T, StorageOperationStatus> createToscaComponent(T resource) {
276         ToscaElement toscaElement = ModelConverter.convertToToscaElement(resource);
277         ToscaElementOperation toscaElementOperation = getToscaElementOperation(resource);
278         Either<ToscaElement, StorageOperationStatus> createToscaElement = toscaElementOperation.createToscaElement(toscaElement);
279         if (createToscaElement.isLeft()) {
280             log.debug(COMPONENT_CREATED_SUCCESSFULLY);
281             T dataModel = ModelConverter.convertFromToscaElement(createToscaElement.left().value());
282             return Either.left(dataModel);
283         }
284         return Either.right(createToscaElement.right().value());
285     }
286
287     // region - ToscaElement Delete
288     public StorageOperationStatus markComponentToDelete(Component componentToDelete) {
289         if (Boolean.TRUE.equals(componentToDelete.getIsDeleted()) && Boolean.FALSE.equals(componentToDelete.isHighestVersion())) {
290             // component already marked for delete
291             return StorageOperationStatus.OK;
292         } else {
293             Either<GraphVertex, JanusGraphOperationStatus> getResponse = janusGraphDao
294                 .getVertexById(componentToDelete.getUniqueId(), JsonParseFlagEnum.ParseAll);
295             if (getResponse.isRight()) {
296                 log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentToDelete.getUniqueId(), getResponse.right().value());
297                 return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getResponse.right().value());
298             }
299             GraphVertex componentV = getResponse.left().value();
300             // same operation for node type and topology template operations
301             Either<GraphVertex, StorageOperationStatus> result = nodeTypeOperation.markComponentToDelete(componentV);
302             if (result.isRight()) {
303                 return result.right().value();
304             }
305             return StorageOperationStatus.OK;
306         }
307     }
308
309     public <T extends Component> Either<T, StorageOperationStatus> deleteToscaComponent(String componentId) {
310         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.ParseAll);
311         if (getVertexEither.isRight()) {
312             log.debug("Couldn't fetch component vertex with and unique id {}, error: {}", componentId, getVertexEither.right().value());
313             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
314         }
315         Either<ToscaElement, StorageOperationStatus> deleteElement = deleteToscaElement(getVertexEither.left().value());
316         if (deleteElement.isRight()) {
317             log.debug("Failed to delete component with and unique id {}, error: {}", componentId, deleteElement.right().value());
318             return Either.right(deleteElement.right().value());
319         }
320         T dataModel = ModelConverter.convertFromToscaElement(deleteElement.left().value());
321         return Either.left(dataModel);
322     }
323
324     private Either<ToscaElement, StorageOperationStatus> deleteToscaElement(GraphVertex componentV) {
325         VertexTypeEnum label = componentV.getLabel();
326         Either<ToscaElement, StorageOperationStatus> toscaElement;
327         Object componentId = componentV.getUniqueId();
328         switch (label) {
329             case NODE_TYPE:
330                 log.debug("Need to fetch node type for id {}", componentId);
331                 toscaElement = nodeTypeOperation.deleteToscaElement(componentV);
332                 break;
333             case TOPOLOGY_TEMPLATE:
334                 log.debug("Need to fetch topology template for id {}", componentId);
335                 toscaElement = topologyTemplateOperation.deleteToscaElement(componentV);
336                 break;
337             default:
338                 log.debug("not supported tosca type {} for id {}", label, componentId);
339                 toscaElement = Either.right(StorageOperationStatus.BAD_REQUEST);
340                 break;
341         }
342         return toscaElement;
343     }
344
345     // endregion
346     private ToscaElementOperation getToscaElementOperation(Component component) {
347         return ModelConverter.isAtomicComponent(component) ? nodeTypeOperation : topologyTemplateOperation;
348     }
349
350     public <T extends Component> Either<T, StorageOperationStatus> getLatestByToscaResourceName(String toscaResourceName) {
351         return getLatestByName(GraphPropertyEnum.TOSCA_RESOURCE_NAME, toscaResourceName);
352     }
353
354     public <T extends Component> Either<T, StorageOperationStatus> getFullLatestComponentByToscaResourceName(String toscaResourceName) {
355         ComponentParametersView fetchAllFilter = new ComponentParametersView();
356         fetchAllFilter.setIgnoreServicePath(true);
357         fetchAllFilter.setIgnoreCapabiltyProperties(false);
358         return getLatestByName(GraphPropertyEnum.TOSCA_RESOURCE_NAME, toscaResourceName, JsonParseFlagEnum.ParseAll, fetchAllFilter);
359     }
360
361     public <T extends Component> Either<T, StorageOperationStatus> getLatestByName(String resourceName) {
362         return getLatestByName(GraphPropertyEnum.NAME, resourceName);
363     }
364
365     public StorageOperationStatus validateCsarUuidUniqueness(String csarUUID) {
366         Map<GraphPropertyEnum, Object> properties = new EnumMap<>(GraphPropertyEnum.class);
367         properties.put(GraphPropertyEnum.CSAR_UUID, csarUUID);
368         Either<List<GraphVertex>, JanusGraphOperationStatus> resources = janusGraphDao
369             .getByCriteria(null, properties, JsonParseFlagEnum.ParseMetadata);
370         if (resources.isRight()) {
371             if (resources.right().value() == JanusGraphOperationStatus.NOT_FOUND) {
372                 return StorageOperationStatus.OK;
373             } else {
374                 log.debug("failed to get resources from graph with property name: {}", csarUUID);
375                 return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(resources.right().value());
376             }
377         }
378         return StorageOperationStatus.ENTITY_ALREADY_EXISTS;
379     }
380
381     public <T extends Component> Either<Set<T>, StorageOperationStatus> getFollowed(String userId, Set<LifecycleStateEnum> lifecycleStates,
382                                                                                     Set<LifecycleStateEnum> lastStateStates,
383                                                                                     ComponentTypeEnum componentType) {
384         Either<List<ToscaElement>, StorageOperationStatus> followedResources;
385         if (componentType == ComponentTypeEnum.RESOURCE) {
386             followedResources = nodeTypeOperation.getFollowedComponent(userId, lifecycleStates, lastStateStates, componentType);
387         } else {
388             followedResources = topologyTemplateOperation.getFollowedComponent(userId, lifecycleStates, lastStateStates, componentType);
389         }
390         Set<T> components = new HashSet<>();
391         if (followedResources.isRight() && followedResources.right().value() != StorageOperationStatus.NOT_FOUND) {
392             return Either.right(followedResources.right().value());
393         }
394         if (followedResources.isLeft()) {
395             List<ToscaElement> toscaElements = followedResources.left().value();
396             toscaElements.forEach(te -> {
397                 T component = ModelConverter.convertFromToscaElement(te);
398                 components.add(component);
399             });
400         }
401         return Either.left(components);
402     }
403
404     public Either<Resource, StorageOperationStatus> getLatestCertifiedNodeTypeByToscaResourceName(String toscaResourceName) {
405         return getLatestCertifiedByToscaResourceName(toscaResourceName, VertexTypeEnum.NODE_TYPE, JsonParseFlagEnum.ParseMetadata);
406     }
407
408     public Either<Resource, StorageOperationStatus> getByToscaResourceNameMatchingVendorRelease(final String toscaResourceName,
409                                                                                                 final String vendorVersion) {
410         return getByToscaResourceNameMatchingVendorRelease(toscaResourceName, VertexTypeEnum.NODE_TYPE, JsonParseFlagEnum.ParseMetadata,
411             vendorVersion);
412     }
413
414     public Either<Resource, StorageOperationStatus> getByToscaResourceNameMatchingVendorRelease(String toscaResourceName, VertexTypeEnum vertexType,
415                                                                                                 JsonParseFlagEnum parseFlag, String vendorRelease) {
416         Map<GraphPropertyEnum, Object> props = new EnumMap<>(GraphPropertyEnum.class);
417         props.put(GraphPropertyEnum.TOSCA_RESOURCE_NAME, toscaResourceName);
418         props.put(GraphPropertyEnum.STATE, LifecycleStateEnum.CERTIFIED.name());
419         Map<String, Entry<JanusGraphPredicate, Object>> predicateCriteria = getVendorVersionPredicate(vendorRelease);
420         Either<List<GraphVertex>, JanusGraphOperationStatus> getLatestRes = janusGraphDao
421             .getByCriteria(vertexType, props, null, predicateCriteria, parseFlag);
422         if (getLatestRes.isRight() || CollectionUtils.isEmpty(getLatestRes.left().value())) {
423             getLatestRes = janusGraphDao.getByCriteria(vertexType, props, parseFlag);
424         }
425         return getLatestRes.right().map(status -> {
426             CommonUtility
427                 .addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to fetch {} with name {}. status={} ", vertexType, toscaResourceName, status);
428             return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status);
429         }).left().bind(resources -> {
430             double version = 0.0;
431             GraphVertex highestResource = null;
432             for (GraphVertex resource : resources) {
433                 double resourceVersion = Double.parseDouble((String) resource.getJsonMetadataField(JsonPresentationFields.VERSION));
434                 if (resourceVersion > version && isValidForVendorRelease(resource, vendorRelease)) {
435                     version = resourceVersion;
436                     highestResource = resource;
437                 }
438             }
439             if (highestResource != null) {
440                 return getToscaFullElement(highestResource.getUniqueId());
441             } else {
442                 log.debug("The vertex with the highest version could not be found for {}", toscaResourceName);
443                 return Either.right(StorageOperationStatus.GENERAL_ERROR);
444             }
445         });
446     }
447
448     private Map<String, Entry<JanusGraphPredicate, Object>> getVendorVersionPredicate(final String vendorRelease) {
449         Map<String, Entry<JanusGraphPredicate, Object>> predicateCriteria = new HashMap<>();
450         if (!"1.0".equals(vendorRelease)) {
451             String[] vendorReleaseElements = vendorRelease.split("\\.");
452             if (vendorReleaseElements.length > 0) {
453                 String regex = ".*\"vendorRelease\":\"";
454                 for (int i = 0; i < vendorReleaseElements.length; i++) {
455                     regex += vendorReleaseElements[i];
456                     regex += i < vendorReleaseElements.length - 1 ? "\\." : "\".*";
457                 }
458                 predicateCriteria.put("metadata", new HashMap.SimpleEntry<>(REGEX, regex));
459             }
460         }
461         return predicateCriteria;
462     }
463
464     private boolean isValidForVendorRelease(final GraphVertex resource, final String vendorRelease) {
465         if (!vendorRelease.equals("1.0")) {
466             try {
467                 Semver resourceSemVer = new Semver((String) resource.getJsonMetadataField(JsonPresentationFields.VENDOR_RELEASE), SemverType.NPM);
468                 Semver packageSemVer = new Semver(vendorRelease, SemverType.NPM);
469                 return !resourceSemVer.isGreaterThan(packageSemVer);
470             } catch (Exception exception) {
471                 log.debug("Error in comparing vendor release", exception);
472                 return true;
473             }
474         }
475         return true;
476     }
477
478     public Either<Resource, StorageOperationStatus> getLatestCertifiedByToscaResourceName(String toscaResourceName, VertexTypeEnum vertexType,
479                                                                                           JsonParseFlagEnum parseFlag) {
480         Map<GraphPropertyEnum, Object> props = new EnumMap<>(GraphPropertyEnum.class);
481         props.put(GraphPropertyEnum.TOSCA_RESOURCE_NAME, toscaResourceName);
482         props.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
483         props.put(GraphPropertyEnum.STATE, LifecycleStateEnum.CERTIFIED.name());
484         Either<List<GraphVertex>, JanusGraphOperationStatus> getLatestRes = janusGraphDao.getByCriteria(vertexType, props, parseFlag);
485         return getLatestRes.right().map(status -> {
486             CommonUtility
487                 .addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to fetch {} with name {}. status={} ", vertexType, toscaResourceName, status);
488             return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status);
489         }).left().bind(resources -> {
490             double version = 0.0;
491             GraphVertex highestResource = null;
492             for (GraphVertex resource : resources) {
493                 double resourceVersion = Double.parseDouble((String) resource.getJsonMetadataField(JsonPresentationFields.VERSION));
494                 if (resourceVersion > version) {
495                     version = resourceVersion;
496                     highestResource = resource;
497                 }
498             }
499             if (highestResource != null) {
500                 return getToscaFullElement(highestResource.getUniqueId());
501             } else {
502                 log.debug("The vertex with the highest version could not be found for {}", toscaResourceName);
503                 return Either.right(StorageOperationStatus.GENERAL_ERROR);
504             }
505         });
506     }
507
508     public Either<Resource, StorageOperationStatus> getLatestResourceByToscaResourceName(String toscaResourceName) {
509         if (toscaResourceName != null && toscaResourceName.contains("org.openecomp.resource.vf")) {
510             return getLatestResourceByToscaResourceName(toscaResourceName, VertexTypeEnum.TOPOLOGY_TEMPLATE, JsonParseFlagEnum.ParseMetadata);
511         } else {
512             return getLatestResourceByToscaResourceName(toscaResourceName, VertexTypeEnum.NODE_TYPE, JsonParseFlagEnum.ParseMetadata);
513         }
514     }
515
516     public Either<Resource, StorageOperationStatus> getLatestResourceByToscaResourceName(String toscaResourceName, VertexTypeEnum vertexType,
517                                                                                          JsonParseFlagEnum parseFlag) {
518         Either<Resource, StorageOperationStatus> result = null;
519         Map<GraphPropertyEnum, Object> props = new EnumMap<>(GraphPropertyEnum.class);
520         props.put(GraphPropertyEnum.TOSCA_RESOURCE_NAME, toscaResourceName);
521         props.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
522         if (!toscaResourceName.contains("org.openecomp.resource.vf")) {
523             props.put(GraphPropertyEnum.STATE, LifecycleStateEnum.CERTIFIED.name());
524         }
525         Either<List<GraphVertex>, JanusGraphOperationStatus> getLatestRes = janusGraphDao.getByCriteria(vertexType, props, parseFlag);
526         if (getLatestRes.isRight()) {
527             JanusGraphOperationStatus status = getLatestRes.right().value();
528             CommonUtility
529                 .addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to fetch {} with name {}. status={} ", vertexType, toscaResourceName, status);
530             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
531         }
532         if (result == null) {
533             List<GraphVertex> resources = getLatestRes.left().value();
534             double version = 0.0;
535             GraphVertex highestResource = null;
536             for (GraphVertex resource : resources) {
537                 double resourceVersion = Double.parseDouble((String) resource.getJsonMetadataField(JsonPresentationFields.VERSION));
538                 if (resourceVersion > version) {
539                     version = resourceVersion;
540                     highestResource = resource;
541                 }
542             }
543             if (highestResource != null) {
544                 result = getToscaFullElement(highestResource.getUniqueId());
545             } else {
546                 log.debug("The vertex with the highest version could not be found for {}", toscaResourceName);
547                 result = Either.right(StorageOperationStatus.GENERAL_ERROR);
548             }
549         }
550         return result;
551     }
552
553     public Either<Boolean, StorageOperationStatus> validateToscaResourceNameExists(String templateName) {
554         Either<Boolean, StorageOperationStatus> validateUniquenessRes = validateToscaResourceNameUniqueness(templateName);
555         if (validateUniquenessRes.isLeft()) {
556             return Either.left(!validateUniquenessRes.left().value());
557         }
558         return validateUniquenessRes;
559     }
560
561     public Either<RequirementCapabilityRelDef, StorageOperationStatus> dissociateResourceInstances(String componentId,
562                                                                                                    RequirementCapabilityRelDef requirementDef) {
563         return nodeTemplateOperation.dissociateResourceInstances(componentId, requirementDef);
564     }
565
566     /**
567      * Allows to get fulfilled requirement by relation and received predicate
568      */
569     public Either<RequirementDataDefinition, StorageOperationStatus> getFulfilledRequirementByRelation(String componentId, String instanceId,
570                                                                                                        RequirementCapabilityRelDef relation,
571                                                                                                        BiPredicate<RelationshipInfo, RequirementDataDefinition> predicate) {
572         return nodeTemplateOperation.getFulfilledRequirementByRelation(componentId, instanceId, relation, predicate);
573     }
574
575     /**
576      * Allows to get fulfilled capability by relation and received predicate
577      */
578     public Either<CapabilityDataDefinition, StorageOperationStatus> getFulfilledCapabilityByRelation(String componentId, String instanceId,
579                                                                                                      RequirementCapabilityRelDef relation,
580                                                                                                      BiPredicate<RelationshipInfo, CapabilityDataDefinition> predicate) {
581         return nodeTemplateOperation.getFulfilledCapabilityByRelation(componentId, instanceId, relation, predicate);
582     }
583
584     public Either<List<RequirementCapabilityRelDef>, StorageOperationStatus> associateResourceInstances(Component component, String componentId,
585                                                                                                         List<RequirementCapabilityRelDef> relations) {
586         Either<List<RequirementCapabilityRelDef>, StorageOperationStatus> reqAndCapListEither = nodeTemplateOperation
587             .associateResourceInstances(component, componentId, relations);
588         if (component != null) {
589             updateInstancesCapAndReqOnComponentFromDB(component);
590         }
591         return reqAndCapListEither;
592     }
593
594     protected Either<Boolean, StorageOperationStatus> validateToscaResourceNameUniqueness(String name) {
595         Map<GraphPropertyEnum, Object> properties = new EnumMap<>(GraphPropertyEnum.class);
596         properties.put(GraphPropertyEnum.TOSCA_RESOURCE_NAME, name);
597         Either<List<GraphVertex>, JanusGraphOperationStatus> resources = janusGraphDao
598             .getByCriteria(null, properties, JsonParseFlagEnum.ParseMetadata);
599         if (resources.isRight() && resources.right().value() != JanusGraphOperationStatus.NOT_FOUND) {
600             log.debug("failed to get resources from graph with property name: {}", name);
601             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(resources.right().value()));
602         }
603         List<GraphVertex> resourceList = (resources.isLeft() ? resources.left().value() : null);
604         if (isNotEmpty(resourceList)) {
605             if (log.isDebugEnabled()) {
606                 StringBuilder builder = new StringBuilder();
607                 for (GraphVertex resourceData : resourceList) {
608                     builder.append(resourceData.getUniqueId() + "|");
609                 }
610                 log.debug("resources  with property name:{} exists in graph. found {}", name, builder);
611             }
612             return Either.left(false);
613         } else {
614             log.debug("resources  with property name:{} does not exists in graph", name);
615             return Either.left(true);
616         }
617     }
618
619     // region - Component Update
620     public Either<Resource, StorageOperationStatus> overrideComponent(Resource newComponent, Resource oldComponent) {
621         copyArtifactsToNewComponent(newComponent, oldComponent);
622         Either<GraphVertex, JanusGraphOperationStatus> componentVEither = janusGraphDao
623             .getVertexById(oldComponent.getUniqueId(), JsonParseFlagEnum.NoParse);
624         if (componentVEither.isRight()) {
625             log.debug("Failed to fetch component {} error {}", oldComponent.getUniqueId(), componentVEither.right().value());
626             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(componentVEither.right().value()));
627         }
628         GraphVertex componentv = componentVEither.left().value();
629         Either<GraphVertex, JanusGraphOperationStatus> parentVertexEither = janusGraphDao
630             .getParentVertex(componentv, EdgeLabelEnum.VERSION, JsonParseFlagEnum.NoParse);
631         if (parentVertexEither.isRight() && parentVertexEither.right().value() != JanusGraphOperationStatus.NOT_FOUND) {
632             log.debug("Failed to fetch parent version for component {} error {}", oldComponent.getUniqueId(), parentVertexEither.right().value());
633             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(parentVertexEither.right().value()));
634         }
635         Either<ToscaElement, StorageOperationStatus> deleteToscaComponent = deleteToscaElement(componentv);
636         if (deleteToscaComponent.isRight()) {
637             log.debug("Failed to remove old component {} error {}", oldComponent.getUniqueId(), deleteToscaComponent.right().value());
638             return Either.right(deleteToscaComponent.right().value());
639         }
640         Either<Resource, StorageOperationStatus> createToscaComponent = createToscaComponent(newComponent);
641         if (createToscaComponent.isRight()) {
642             log.debug("Failed to create tosca element component {} error {}", newComponent.getUniqueId(), createToscaComponent.right().value());
643             return Either.right(createToscaComponent.right().value());
644         }
645         Resource newElement = createToscaComponent.left().value();
646         Either<GraphVertex, JanusGraphOperationStatus> newVersionEither = janusGraphDao
647             .getVertexById(newElement.getUniqueId(), JsonParseFlagEnum.NoParse);
648         if (newVersionEither.isRight()) {
649             log.debug("Failed to fetch new tosca element component {} error {}", newComponent.getUniqueId(), newVersionEither.right().value());
650             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(newVersionEither.right().value()));
651         }
652         if (parentVertexEither.isLeft()) {
653             GraphVertex previousVersionV = parentVertexEither.left().value();
654             JanusGraphOperationStatus createEdge = janusGraphDao
655                 .createEdge(previousVersionV, newVersionEither.left().value(), EdgeLabelEnum.VERSION, null);
656             if (createEdge != JanusGraphOperationStatus.OK) {
657                 log.debug("Failed to associate to previous version {} new version {} error {}", previousVersionV.getUniqueId(),
658                     newVersionEither.right().value(), createEdge);
659                 return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(createEdge));
660             }
661         }
662         return Either.left(newElement);
663     }
664
665     void copyArtifactsToNewComponent(Resource newComponent, Resource oldComponent) {
666         // TODO - check if required
667         Map<String, ArtifactDefinition> toscaArtifacts = oldComponent.getToscaArtifacts();
668         if (toscaArtifacts != null && !toscaArtifacts.isEmpty()) {
669             toscaArtifacts.values().stream().forEach(a -> a.setDuplicated(Boolean.TRUE));
670         }
671         newComponent.setToscaArtifacts(toscaArtifacts);
672         Map<String, ArtifactDefinition> artifacts = oldComponent.getArtifacts();
673         if (artifacts != null && !artifacts.isEmpty()) {
674             artifacts.values().stream().forEach(a -> a.setDuplicated(Boolean.TRUE));
675         }
676         newComponent.setArtifacts(artifacts);
677         Map<String, ArtifactDefinition> depArtifacts = oldComponent.getDeploymentArtifacts();
678         if (depArtifacts != null && !depArtifacts.isEmpty()) {
679             depArtifacts.values().stream().forEach(a -> a.setDuplicated(Boolean.TRUE));
680         }
681         newComponent.setDeploymentArtifacts(depArtifacts);
682         newComponent.setLastUpdateDate(null);
683         newComponent.setHighestVersion(true);
684     }
685
686     public <T extends Component> Either<T, StorageOperationStatus> updateToscaElement(T componentToUpdate) {
687         return updateToscaElement(componentToUpdate, new ComponentParametersView());
688     }
689
690     public <T extends Component> Either<T, StorageOperationStatus> updateToscaElement(T componentToUpdate, ComponentParametersView filterResult) {
691         String componentId = componentToUpdate.getUniqueId();
692         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.ParseAll);
693         if (getVertexEither.isRight()) {
694             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
695             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
696         }
697         GraphVertex elementV = getVertexEither.left().value();
698         ToscaElementOperation toscaElementOperation = getToscaElementOperation(elementV);
699         ToscaElement toscaElementToUpdate = ModelConverter.convertToToscaElement(componentToUpdate);
700         Either<ToscaElement, StorageOperationStatus> updateToscaElement = null;
701         if (toscaElementOperation != null) {
702             updateToscaElement = toscaElementOperation.updateToscaElement(toscaElementToUpdate, elementV, filterResult);
703         } else {
704             log.debug("Null value returned by `getToscaElementOperation` with value {}", elementV);
705             updateToscaElement = Either.right(StorageOperationStatus.GENERAL_ERROR);
706         }
707         return updateToscaElement.bimap(ModelConverter::convertFromToscaElement, status -> {
708             log.debug("Failed to update tosca element {} error {}", componentId, status);
709             return status;
710         });
711     }
712
713     private <T extends Component> Either<T, StorageOperationStatus> getLatestByName(GraphPropertyEnum property, String nodeName,
714                                                                                     JsonParseFlagEnum parseFlag) {
715         return getLatestByName(property, nodeName, parseFlag, new ComponentParametersView());
716     }
717     // endregion
718
719     private <T extends Component> Either<T, StorageOperationStatus> getLatestByName(GraphPropertyEnum property, String nodeName,
720                                                                                     JsonParseFlagEnum parseFlag, ComponentParametersView filter) {
721         Either<T, StorageOperationStatus> result;
722         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
723         Map<GraphPropertyEnum, Object> propertiesNotToMatch = new EnumMap<>(GraphPropertyEnum.class);
724         propertiesToMatch.put(property, nodeName);
725         propertiesToMatch.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
726         propertiesNotToMatch.put(GraphPropertyEnum.IS_DELETED, true);
727         Either<List<GraphVertex>, JanusGraphOperationStatus> highestResources = janusGraphDao
728             .getByCriteria(null, propertiesToMatch, propertiesNotToMatch, parseFlag);
729         if (highestResources.isRight()) {
730             JanusGraphOperationStatus status = highestResources.right().value();
731             log.debug("failed to find resource with name {}. status={} ", nodeName, status);
732             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
733             return result;
734         }
735         List<GraphVertex> resources = highestResources.left().value();
736         double version = 0.0;
737         GraphVertex highestResource = null;
738         for (GraphVertex vertex : resources) {
739             Object versionObj = vertex.getMetadataProperty(GraphPropertyEnum.VERSION);
740             double resourceVersion = Double.parseDouble((String) versionObj);
741             if (resourceVersion > version) {
742                 version = resourceVersion;
743                 highestResource = vertex;
744             }
745         }
746         return getToscaElementByOperation(highestResource, filter);
747     }
748
749     // region - Component Get By ..
750     private <T extends Component> Either<T, StorageOperationStatus> getLatestByName(GraphPropertyEnum property, String nodeName) {
751         return getLatestByName(property, nodeName, JsonParseFlagEnum.ParseMetadata);
752     }
753
754     public <T extends Component> Either<List<T>, StorageOperationStatus> getBySystemName(ComponentTypeEnum componentType, String systemName) {
755         Either<List<T>, StorageOperationStatus> result = null;
756         Either<T, StorageOperationStatus> getComponentRes;
757         List<T> components = new ArrayList<>();
758         List<GraphVertex> componentVertices;
759         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
760         Map<GraphPropertyEnum, Object> propertiesNotToMatch = new EnumMap<>(GraphPropertyEnum.class);
761         propertiesToMatch.put(GraphPropertyEnum.SYSTEM_NAME, systemName);
762         if (componentType != null) {
763             propertiesToMatch.put(GraphPropertyEnum.COMPONENT_TYPE, componentType.name());
764         }
765         propertiesNotToMatch.put(GraphPropertyEnum.IS_DELETED, true);
766         Either<List<GraphVertex>, JanusGraphOperationStatus> getComponentsRes = janusGraphDao
767             .getByCriteria(null, propertiesToMatch, propertiesNotToMatch, JsonParseFlagEnum.ParseAll);
768         if (getComponentsRes.isRight()) {
769             JanusGraphOperationStatus status = getComponentsRes.right().value();
770             log.debug("Failed to fetch the component with system name {}. Status is {} ", systemName, status);
771             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
772         }
773         if (result == null) {
774             componentVertices = getComponentsRes.left().value();
775             for (GraphVertex componentVertex : componentVertices) {
776                 getComponentRes = getToscaElementByOperation(componentVertex);
777                 if (getComponentRes.isRight()) {
778                     log.debug("Failed to get the component {}. Status is {} ", componentVertex.getJsonMetadataField(JsonPresentationFields.NAME),
779                         getComponentRes.right().value());
780                     result = Either.right(getComponentRes.right().value());
781                     break;
782                 }
783                 T componentBySystemName = getComponentRes.left().value();
784                 log.debug("Found component, id: {}", componentBySystemName.getUniqueId());
785                 components.add(componentBySystemName);
786             }
787         }
788         if (result == null) {
789             result = Either.left(components);
790         }
791         return result;
792     }
793
794     public <T extends Component> Either<T, StorageOperationStatus> getComponentByNameAndVersion(ComponentTypeEnum componentType, String name,
795                                                                                                 String version) {
796         return getComponentByNameAndVersion(componentType, name, version, JsonParseFlagEnum.ParseAll);
797     }
798
799     public <T extends Component> Either<T, StorageOperationStatus> getComponentByNameAndVersion(ComponentTypeEnum componentType, String name,
800                                                                                                 String version, JsonParseFlagEnum parseFlag) {
801         Either<T, StorageOperationStatus> result;
802         Map<GraphPropertyEnum, Object> hasProperties = new EnumMap<>(GraphPropertyEnum.class);
803         Map<GraphPropertyEnum, Object> hasNotProperties = new EnumMap<>(GraphPropertyEnum.class);
804         hasProperties.put(GraphPropertyEnum.NAME, name);
805         hasProperties.put(GraphPropertyEnum.VERSION, version);
806         hasNotProperties.put(GraphPropertyEnum.IS_DELETED, true);
807         if (componentType != null) {
808             hasProperties.put(GraphPropertyEnum.COMPONENT_TYPE, componentType.name());
809         }
810         Either<List<GraphVertex>, JanusGraphOperationStatus> getResourceRes = janusGraphDao
811             .getByCriteria(null, hasProperties, hasNotProperties, parseFlag);
812         if (getResourceRes.isRight()) {
813             JanusGraphOperationStatus status = getResourceRes.right().value();
814             log.debug("failed to find resource with name {}, version {}. Status is {} ", name, version, status);
815             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
816             return result;
817         }
818         return getToscaElementByOperation(getResourceRes.left().value().get(0));
819     }
820
821     public <T extends Component> Either<T, StorageOperationStatus> getComponentByNameAndVendorRelease(final ComponentTypeEnum componentType,
822                                                                                                       final String name, final String vendorRelease,
823                                                                                                       final JsonParseFlagEnum parseFlag) {
824         Map<GraphPropertyEnum, Object> hasProperties = new EnumMap<>(GraphPropertyEnum.class);
825         Map<GraphPropertyEnum, Object> hasNotProperties = new EnumMap<>(GraphPropertyEnum.class);
826         hasProperties.put(GraphPropertyEnum.NAME, name);
827         hasNotProperties.put(GraphPropertyEnum.IS_DELETED, true);
828         if (componentType != null) {
829             hasProperties.put(GraphPropertyEnum.COMPONENT_TYPE, componentType.name());
830         }
831         Map<String, Entry<JanusGraphPredicate, Object>> predicateCriteria = getVendorVersionPredicate(vendorRelease);
832         Either<List<GraphVertex>, JanusGraphOperationStatus> getResourceRes = janusGraphDao
833             .getByCriteria(null, hasProperties, hasNotProperties, predicateCriteria, parseFlag);
834         if (getResourceRes.isRight()) {
835             JanusGraphOperationStatus status = getResourceRes.right().value();
836             log.debug("failed to find resource with name {}, version {}. Status is {} ", name, predicateCriteria, status);
837             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
838         }
839         return getToscaElementByOperation(getResourceRes.left().value().get(0));
840     }
841
842     public Either<List<CatalogComponent>, StorageOperationStatus> getCatalogOrArchiveComponents(boolean isCatalog,
843                                                                                                 List<OriginTypeEnum> excludeTypes) {
844         List<ResourceTypeEnum> excludedResourceTypes = Optional.ofNullable(excludeTypes).orElse(Collections.emptyList()).stream()
845             .filter(type -> !type.equals(OriginTypeEnum.SERVICE)).map(type -> ResourceTypeEnum.getTypeByName(type.name()))
846             .collect(Collectors.toList());
847         return topologyTemplateOperation.getElementCatalogData(isCatalog, excludedResourceTypes);
848     }
849
850     // endregion
851     public <T extends Component> Either<List<T>, StorageOperationStatus> getCatalogComponents(ComponentTypeEnum componentType,
852                                                                                               List<OriginTypeEnum> excludeTypes,
853                                                                                               boolean isHighestVersions) {
854         List<T> components = new ArrayList<>();
855         Either<List<ToscaElement>, StorageOperationStatus> catalogDataResult;
856         List<ToscaElement> toscaElements = new ArrayList<>();
857         List<ResourceTypeEnum> excludedResourceTypes = Optional.ofNullable(excludeTypes).orElse(Collections.emptyList()).stream()
858             .filter(type -> !type.equals(OriginTypeEnum.SERVICE)).map(type -> ResourceTypeEnum.getTypeByName(type.name()))
859             .collect(Collectors.toList());
860         switch (componentType) {
861             case RESOURCE:
862                 catalogDataResult = nodeTypeOperation.getElementCatalogData(ComponentTypeEnum.RESOURCE, excludedResourceTypes, isHighestVersions);
863                 if (catalogDataResult.isRight()) {
864                     return Either.right(catalogDataResult.right().value());
865                 }
866                 toscaElements = catalogDataResult.left().value();
867                 break;
868             case SERVICE:
869                 if (excludeTypes != null && excludeTypes.contains(OriginTypeEnum.SERVICE)) {
870                     break;
871                 }
872                 catalogDataResult = topologyTemplateOperation.getElementCatalogData(ComponentTypeEnum.SERVICE, null, isHighestVersions);
873                 if (catalogDataResult.isRight()) {
874                     return Either.right(catalogDataResult.right().value());
875                 }
876                 toscaElements = catalogDataResult.left().value();
877                 break;
878             default:
879                 log.debug(NOT_SUPPORTED_COMPONENT_TYPE, componentType);
880                 return Either.right(StorageOperationStatus.BAD_REQUEST);
881         }
882         toscaElements.forEach(te -> {
883             T component = ModelConverter.convertFromToscaElement(te);
884             components.add(component);
885         });
886         return Either.left(components);
887     }
888
889     public Either<List<String>, StorageOperationStatus> deleteMarkedElements(ComponentTypeEnum componentType) {
890         Either<List<GraphVertex>, StorageOperationStatus> allComponentsMarkedForDeletion;
891         switch (componentType) {
892             case RESOURCE:
893                 allComponentsMarkedForDeletion = nodeTypeOperation.getAllComponentsMarkedForDeletion(componentType);
894                 break;
895             case SERVICE:
896             case PRODUCT:
897                 allComponentsMarkedForDeletion = topologyTemplateOperation.getAllComponentsMarkedForDeletion(componentType);
898                 break;
899             default:
900                 log.debug(NOT_SUPPORTED_COMPONENT_TYPE, componentType);
901                 return Either.right(StorageOperationStatus.BAD_REQUEST);
902         }
903         if (allComponentsMarkedForDeletion.isRight()) {
904             return Either.right(allComponentsMarkedForDeletion.right().value());
905         }
906         List<GraphVertex> allMarked = allComponentsMarkedForDeletion.left().value();
907         return Either.left(checkIfInUseAndDelete(allMarked));
908     }
909
910     private List<String> checkIfInUseAndDelete(List<GraphVertex> allMarked) {
911         final List<EdgeLabelEnum> forbiddenEdgeLabelEnums = Arrays
912             .asList(EdgeLabelEnum.INSTANCE_OF, EdgeLabelEnum.PROXY_OF, EdgeLabelEnum.ALLOTTED_OF);
913         List<String> deleted = new ArrayList<>();
914         for (GraphVertex elementV : allMarked) {
915             boolean isAllowedToDelete = true;
916             for (EdgeLabelEnum edgeLabelEnum : forbiddenEdgeLabelEnums) {
917                 Either<Edge, JanusGraphOperationStatus> belongingEdgeByCriteria = janusGraphDao
918                     .getBelongingEdgeByCriteria(elementV, edgeLabelEnum, null);
919                 if (belongingEdgeByCriteria.isLeft()) {
920                     log.debug("Marked element {} in use. don't delete it", elementV.getUniqueId());
921                     isAllowedToDelete = false;
922                     break;
923                 }
924             }
925             if (isAllowedToDelete) {
926                 Either<ToscaElement, StorageOperationStatus> deleteToscaElement = deleteToscaElement(elementV);
927                 if (deleteToscaElement.isRight()) {
928                     log.debug("Failed to delete marked element UniqueID {}, Name {}, error {}", elementV.getUniqueId(),
929                         elementV.getMetadataProperties().get(GraphPropertyEnum.NAME), deleteToscaElement.right().value());
930                     continue;
931                 }
932                 deleted.add(elementV.getUniqueId());
933             }
934         }
935         return deleted;
936     }
937
938     public Either<List<String>, StorageOperationStatus> getAllComponentsMarkedForDeletion(ComponentTypeEnum componentType) {
939         Either<List<GraphVertex>, StorageOperationStatus> allComponentsMarkedForDeletion;
940         switch (componentType) {
941             case RESOURCE:
942                 allComponentsMarkedForDeletion = nodeTypeOperation.getAllComponentsMarkedForDeletion(componentType);
943                 break;
944             case SERVICE:
945             case PRODUCT:
946                 allComponentsMarkedForDeletion = topologyTemplateOperation.getAllComponentsMarkedForDeletion(componentType);
947                 break;
948             default:
949                 log.debug(NOT_SUPPORTED_COMPONENT_TYPE, componentType);
950                 return Either.right(StorageOperationStatus.BAD_REQUEST);
951         }
952         if (allComponentsMarkedForDeletion.isRight()) {
953             return Either.right(allComponentsMarkedForDeletion.right().value());
954         }
955         return Either.left(allComponentsMarkedForDeletion.left().value().stream().map(GraphVertex::getUniqueId).collect(Collectors.toList()));
956     }
957
958     // region - Component Update
959     public Either<ImmutablePair<Component, String>, StorageOperationStatus> addComponentInstanceToTopologyTemplate(Component containerComponent,
960                                                                                                                    Component origComponent,
961                                                                                                                    ComponentInstance componentInstance,
962                                                                                                                    boolean allowDeleted, User user) {
963         Either<ImmutablePair<Component, String>, StorageOperationStatus> result = null;
964         Either<ToscaElement, StorageOperationStatus> updateContainerComponentRes = null;
965         if (StringUtils.isEmpty(componentInstance.getIcon())) {
966             componentInstance.setIcon(origComponent.getIcon());
967         }
968         String nameToFindForCounter;
969         switch (componentInstance.getOriginType()) {
970             case ServiceProxy:
971                 nameToFindForCounter = ValidationUtils.normaliseComponentName(componentInstance.getSourceModelName()) + PROXY_SUFFIX;
972                 break;
973             case ServiceSubstitution:
974                 nameToFindForCounter = ValidationUtils.normaliseComponentName(componentInstance.getSourceModelName());
975                 break;
976             default:
977                 nameToFindForCounter = origComponent.getName();
978         }
979         String nextComponentInstanceCounter = getNextComponentInstanceCounter(containerComponent, nameToFindForCounter);
980         Either<ImmutablePair<TopologyTemplate, String>, StorageOperationStatus> addResult = nodeTemplateOperation
981             .addComponentInstanceToTopologyTemplate(ModelConverter.convertToToscaElement(containerComponent),
982                 ModelConverter.convertToToscaElement(origComponent), nextComponentInstanceCounter, componentInstance, allowDeleted, user);
983         if (addResult.isRight()) {
984             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to add the component instance {} to container component {}. ",
985                 componentInstance.getName(), containerComponent.getName());
986             result = Either.right(addResult.right().value());
987         }
988         if (result == null) {
989             updateContainerComponentRes = topologyTemplateOperation.getToscaElement(containerComponent.getUniqueId());
990             if (updateContainerComponentRes.isRight()) {
991                 CommonUtility
992                     .addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to fetch updated topology template {} with updated component instance {}. ",
993                         containerComponent.getName(), componentInstance.getName());
994                 result = Either.right(updateContainerComponentRes.right().value());
995             }
996         }
997         if (result == null) {
998             Component updatedComponent = ModelConverter.convertFromToscaElement(updateContainerComponentRes.left().value());
999             String createdInstanceId = addResult.left().value().getRight();
1000             CommonUtility
1001                 .addRecordToLog(log, LogLevelEnum.TRACE, "The component instance {} has been added to container component {}. ", createdInstanceId,
1002                     updatedComponent.getName());
1003             result = Either.left(new ImmutablePair<>(updatedComponent, createdInstanceId));
1004         }
1005         return result;
1006     }
1007
1008     public void associateComponentInstancesToComponent(Component containerComponent, Map<ComponentInstance, Resource> resourcesInstancesMap,
1009                                                        boolean allowDeleted, boolean isUpdateCsar) {
1010         CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Going to add component instances to component {}", containerComponent.getUniqueId());
1011         Either<GraphVertex, JanusGraphOperationStatus> metadataVertex = janusGraphDao
1012             .getVertexById(containerComponent.getUniqueId(), JsonParseFlagEnum.ParseAll);
1013         if (metadataVertex.isRight()) {
1014             JanusGraphOperationStatus status = metadataVertex.right().value();
1015             if (status == JanusGraphOperationStatus.NOT_FOUND) {
1016                 status = JanusGraphOperationStatus.INVALID_ID;
1017             }
1018             throw new StorageException(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
1019         }
1020         Map<String, ComponentInstanceDataDefinition> compnentInstancesMap = nodeTemplateOperation
1021             .associateComponentInstancesToComponent(containerComponent, resourcesInstancesMap, metadataVertex.left().value(), allowDeleted,
1022                 isUpdateCsar);
1023         containerComponent.setComponentInstances(ModelConverter.getComponentInstancesFromMapObject(compnentInstancesMap, containerComponent));
1024     }
1025
1026     public Either<ImmutablePair<Component, String>, StorageOperationStatus> updateComponentInstanceMetadataOfTopologyTemplate(
1027         Component containerComponent, Component origComponent, ComponentInstance componentInstance) {
1028         Either<ImmutablePair<Component, String>, StorageOperationStatus> result = null;
1029         CommonUtility.addRecordToLog(log, LogLevelEnum.TRACE,
1030             "Going to update the metadata of the component instance {} belonging to container component {}. ", componentInstance.getName(),
1031             containerComponent.getName());
1032         componentInstance.setIcon(origComponent.getIcon());
1033         Either<ImmutablePair<TopologyTemplate, String>, StorageOperationStatus> updateResult = nodeTemplateOperation
1034             .updateComponentInstanceMetadataOfTopologyTemplate(ModelConverter.convertToToscaElement(containerComponent),
1035                 ModelConverter.convertToToscaElement(origComponent), componentInstance);
1036         if (updateResult.isRight()) {
1037             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG,
1038                 "Failed to update the metadata of the component instance {} belonging to container component {}. ", componentInstance.getName(),
1039                 containerComponent.getName());
1040             result = Either.right(updateResult.right().value());
1041         }
1042         if (result == null) {
1043             Component updatedComponent = ModelConverter.convertFromToscaElement(updateResult.left().value().getLeft());
1044             String createdInstanceId = updateResult.left().value().getRight();
1045             CommonUtility
1046                 .addRecordToLog(log, LogLevelEnum.TRACE, "The metadata of the component instance {} has been updated to container component {}. ",
1047                     createdInstanceId, updatedComponent.getName());
1048             result = Either.left(new ImmutablePair<>(updatedComponent, createdInstanceId));
1049         }
1050         return result;
1051     }
1052
1053     public Either<Component, StorageOperationStatus> updateComponentInstanceMetadataOfTopologyTemplate(Component containerComponent) {
1054         return updateComponentInstanceMetadataOfTopologyTemplate(containerComponent, new ComponentParametersView());
1055     }
1056
1057     public Either<Component, StorageOperationStatus> updateComponentInstanceMetadataOfTopologyTemplate(Component containerComponent,
1058                                                                                                        ComponentParametersView filter) {
1059         Either<Component, StorageOperationStatus> result = null;
1060         CommonUtility.addRecordToLog(log, LogLevelEnum.TRACE, "Going to update the metadata  belonging to container component {}. ",
1061             containerComponent.getName());
1062         Either<TopologyTemplate, StorageOperationStatus> updateResult = nodeTemplateOperation
1063             .updateComponentInstanceMetadataOfTopologyTemplate(ModelConverter.convertToToscaElement(containerComponent), filter);
1064         if (updateResult.isRight()) {
1065             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to update the metadata  belonging to container component {}. ",
1066                 containerComponent.getName());
1067             result = Either.right(updateResult.right().value());
1068         }
1069         if (result == null) {
1070             Component updatedComponent = ModelConverter.convertFromToscaElement(updateResult.left().value());
1071             CommonUtility
1072                 .addRecordToLog(log, LogLevelEnum.TRACE, "The metadata has been updated to container component {}. ", updatedComponent.getName());
1073             result = Either.left(updatedComponent);
1074         }
1075         return result;
1076     }
1077
1078     // endregion
1079     public Either<ImmutablePair<Component, String>, StorageOperationStatus> deleteComponentInstanceFromTopologyTemplate(Component containerComponent,
1080                                                                                                                         String resourceInstanceId) {
1081         Either<ImmutablePair<Component, String>, StorageOperationStatus> result = null;
1082         CommonUtility.addRecordToLog(log, LogLevelEnum.TRACE, "Going to delete the component instance {} belonging to container component {}. ",
1083             resourceInstanceId, containerComponent.getName());
1084         Either<ImmutablePair<TopologyTemplate, String>, StorageOperationStatus> updateResult = nodeTemplateOperation
1085             .deleteComponentInstanceFromTopologyTemplate(ModelConverter.convertToToscaElement(containerComponent), resourceInstanceId);
1086         if (updateResult.isRight()) {
1087             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to delete the component instance {} belonging to container component {}. ",
1088                 resourceInstanceId, containerComponent.getName());
1089             result = Either.right(updateResult.right().value());
1090         }
1091         if (result == null) {
1092             Component updatedComponent = ModelConverter.convertFromToscaElement(updateResult.left().value().getLeft());
1093             String deletedInstanceId = updateResult.left().value().getRight();
1094             CommonUtility.addRecordToLog(log, LogLevelEnum.TRACE, "The component instance {} has been deleted from container component {}. ",
1095                 deletedInstanceId, updatedComponent.getName());
1096             result = Either.left(new ImmutablePair<>(updatedComponent, deletedInstanceId));
1097         }
1098         return result;
1099     }
1100
1101     private String getNextComponentInstanceCounter(Component containerComponent, String originResourceName) {
1102         Integer nextCounter = 0;
1103         if (CollectionUtils.isNotEmpty(containerComponent.getComponentInstances())) {
1104             String normalizedName = ValidationUtils.normalizeComponentInstanceName(originResourceName);
1105             Integer maxCounter = getMaxCounterFromNamesAndIds(containerComponent, normalizedName);
1106             if (maxCounter != null) {
1107                 nextCounter = maxCounter + 1;
1108             }
1109         }
1110         return nextCounter.toString();
1111     }
1112
1113     /**
1114      * @return max counter of component instance Id's, null if not found
1115      */
1116     private Integer getMaxCounterFromNamesAndIds(Component containerComponent, String normalizedName) {
1117         List<String> countersInNames = containerComponent.getComponentInstances().stream()
1118             .filter(ci -> ci.getNormalizedName() != null && ci.getNormalizedName().startsWith(normalizedName))
1119             .map(ci -> ci.getNormalizedName().split(normalizedName)[1]).collect(Collectors.toList());
1120         List<String> countersInIds = containerComponent.getComponentInstances().stream()
1121             .filter(ci -> ci.getUniqueId() != null && ci.getUniqueId().contains(normalizedName)).map(ci -> ci.getUniqueId().split(normalizedName)[1])
1122             .collect(Collectors.toList());
1123         List<String> namesAndIdsList = new ArrayList<>(countersInNames);
1124         namesAndIdsList.addAll(countersInIds);
1125         return getMaxInteger(namesAndIdsList);
1126     }
1127
1128     private Integer getMaxInteger(List<String> counters) {
1129         Integer maxCounter = 0;
1130         Integer currCounter = null;
1131         for (String counter : counters) {
1132             try {
1133                 currCounter = Integer.parseInt(counter);
1134                 if (maxCounter < currCounter) {
1135                     maxCounter = currCounter;
1136                 }
1137             } catch (NumberFormatException e) {
1138                 continue;
1139             }
1140         }
1141         return currCounter == null ? null : maxCounter;
1142     }
1143
1144     public Either<RequirementCapabilityRelDef, StorageOperationStatus> associateResourceInstances(Component component, String componentId,
1145                                                                                                   RequirementCapabilityRelDef requirementDef) {
1146         return nodeTemplateOperation.associateResourceInstances(component, componentId, requirementDef);
1147     }
1148
1149     public Either<List<InputDefinition>, StorageOperationStatus> createAndAssociateInputs(Map<String, InputDefinition> inputs, String componentId) {
1150         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1151         if (getVertexEither.isRight()) {
1152             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1153             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
1154         }
1155         GraphVertex vertex = getVertexEither.left().value();
1156         Map<String, PropertyDataDefinition> inputsMap = inputs.entrySet().stream()
1157             .collect(Collectors.toMap(Map.Entry::getKey, e -> new PropertyDataDefinition(e.getValue())));
1158         StorageOperationStatus status = topologyTemplateOperation.associateInputsToComponent(vertex, inputsMap, componentId);
1159         if (StorageOperationStatus.OK == status) {
1160             log.debug(COMPONENT_CREATED_SUCCESSFULLY);
1161             List<InputDefinition> inputsResList = null;
1162             if (inputsMap != null && !inputsMap.isEmpty()) {
1163                 inputsResList = inputsMap.values().stream().map(InputDefinition::new).collect(Collectors.toList());
1164             }
1165             return Either.left(inputsResList);
1166         }
1167         return Either.right(status);
1168     }
1169
1170     public Either<List<InputDefinition>, StorageOperationStatus> addInputsToComponent(Map<String, InputDefinition> inputs, String componentId) {
1171         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1172         if (getVertexEither.isRight()) {
1173             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1174             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
1175         }
1176         GraphVertex vertex = getVertexEither.left().value();
1177         Map<String, PropertyDefinition> inputsMap = inputs.entrySet().stream()
1178             .collect(Collectors.toMap(Map.Entry::getKey, e -> new PropertyDefinition(e.getValue())));
1179         StorageOperationStatus status = topologyTemplateOperation
1180             .addToscaDataToToscaElement(vertex, EdgeLabelEnum.INPUTS, VertexTypeEnum.INPUTS, inputsMap, JsonPresentationFields.NAME);
1181         if (StorageOperationStatus.OK == status) {
1182             log.debug(COMPONENT_CREATED_SUCCESSFULLY);
1183             List<InputDefinition> inputsResList = null;
1184             if (inputsMap != null && !inputsMap.isEmpty()) {
1185                 inputsResList = inputsMap.values().stream().map(InputDefinition::new).collect(Collectors.toList());
1186             }
1187             return Either.left(inputsResList);
1188         }
1189         return Either.right(status);
1190     }
1191
1192     public Either<List<OutputDefinition>, StorageOperationStatus> addOutputsToComponent(Map<String, OutputDefinition> outputs, String componentId) {
1193         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1194         if (getVertexEither.isRight()) {
1195             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1196             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
1197         }
1198         GraphVertex vertex = getVertexEither.left().value();
1199         Map<String, AttributeDefinition> outputsMap = outputs.entrySet().stream()
1200             .collect(Collectors.toMap(Map.Entry::getKey, e -> new AttributeDefinition(e.getValue())));
1201         StorageOperationStatus status = topologyTemplateOperation
1202             .addToscaDataToToscaElement(vertex, EdgeLabelEnum.OUTPUTS, VertexTypeEnum.OUTPUTS, outputsMap, JsonPresentationFields.NAME);
1203         if (StorageOperationStatus.OK == status) {
1204             log.debug(COMPONENT_CREATED_SUCCESSFULLY);
1205             List<OutputDefinition> outputsResList = null;
1206             if (outputsMap != null && !outputsMap.isEmpty()) {
1207                 outputsResList = outputsMap.values().stream().map(OutputDefinition::new).collect(Collectors.toList());
1208             }
1209             return Either.left(outputsResList);
1210         }
1211         return Either.right(status);
1212     }
1213
1214     /**
1215      * Add data types into a Component.
1216      *
1217      * @param dataTypes   datatypes to be added. the key should be each name of data type.
1218      * @param componentId unique ID of Component.
1219      * @return list of data types.
1220      */
1221     public Either<List<DataTypeDefinition>, StorageOperationStatus> addDataTypesToComponent(Map<String, DataTypeDefinition> dataTypes,
1222                                                                                             String componentId) {
1223         log.trace("#addDataTypesToComponent - enter, componentId={}", componentId);
1224         /* get component vertex */
1225         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao
1226             .getVertexById(componentId, JsonParseFlagEnum.NoParse);
1227         if (getVertexEither.isRight()) {
1228             /* not found / error */
1229             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1230             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
1231         }
1232         GraphVertex vertex = getVertexEither.left().value();
1233         log.trace("#addDataTypesToComponent - get vertex ok");
1234         // convert DataTypeDefinition to DataTypeDataDefinition
1235         Map<String, DataTypeDataDefinition> dataTypeDataMap = dataTypes.entrySet().stream()
1236             .collect(Collectors.toMap(Map.Entry::getKey, e -> convertDataTypeToDataTypeData(e.getValue())));
1237         // add datatype(s) to the Component.
1238
1239         // if child vertex does not exist, it will be created.
1240         StorageOperationStatus status = topologyTemplateOperation
1241             .addToscaDataToToscaElement(vertex, EdgeLabelEnum.DATA_TYPES, VertexTypeEnum.DATA_TYPES, dataTypeDataMap, JsonPresentationFields.NAME);
1242         if (StorageOperationStatus.OK == status) {
1243             log.debug(COMPONENT_CREATED_SUCCESSFULLY);
1244             List<DataTypeDefinition> inputsResList = null;
1245             if (!dataTypes.isEmpty()) {
1246                 inputsResList = new ArrayList<>(dataTypes.values());
1247             }
1248             return Either.left(inputsResList);
1249         }
1250         log.trace("#addDataTypesToComponent - leave");
1251         return Either.right(status);
1252     }
1253
1254     private DataTypeDataDefinition convertDataTypeToDataTypeData(DataTypeDefinition dataType) {
1255         DataTypeDataDefinition dataTypeData = new DataTypeDataDefinition(dataType);
1256         if (CollectionUtils.isNotEmpty(dataType.getProperties())) {
1257             List<PropertyDataDefinition> propertyDataList = dataType.getProperties().stream().map(PropertyDataDefinition::new)
1258                 .collect(Collectors.toList());
1259             dataTypeData.setPropertiesData(propertyDataList);
1260         }
1261         // if "derivedFrom" data_type exists, copy the name to "derivedFromName"
1262         if (dataType.getDerivedFrom() != null && StringUtils.isNotEmpty(dataType.getDerivedFrom().getName())) {
1263             // if names are different, log it
1264             if (!StringUtils.equals(dataTypeData.getDerivedFromName(), dataType.getDerivedFrom().getName())) {
1265                 log.debug("#convertDataTypeToDataTypeData - derivedFromName(={}) overwritten by derivedFrom.name(={})", dataType.getDerivedFromName(),
1266                     dataType.getDerivedFrom().getName());
1267             }
1268             dataTypeData.setDerivedFromName(dataType.getDerivedFrom().getName());
1269         }
1270         // supply "name" field to toscaPresentationValue in each datatype object for DAO operations
1271         dataTypeData.setToscaPresentationValue(JsonPresentationFields.NAME, dataType.getName());
1272         return dataTypeData;
1273     }
1274
1275     public Either<List<InputDefinition>, StorageOperationStatus> getComponentInputs(String componentId) {
1276         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1277         if (getVertexEither.isRight()) {
1278             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1279             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
1280         }
1281         Either<ToscaElement, StorageOperationStatus> toscaElement = topologyTemplateOperation.getToscaElement(componentId);
1282         if (toscaElement.isRight()) {
1283             return Either.right(toscaElement.right().value());
1284         }
1285         TopologyTemplate topologyTemplate = (TopologyTemplate) toscaElement.left().value();
1286         Map<String, PropertyDataDefinition> inputsMap = topologyTemplate.getInputs();
1287         List<InputDefinition> inputs = new ArrayList<>();
1288         if (MapUtils.isNotEmpty(inputsMap)) {
1289             inputs = inputsMap.values().stream().map(p -> new InputDefinition(p)).collect(Collectors.toList());
1290         }
1291         return Either.left(inputs);
1292     }
1293
1294     public Either<List<InputDefinition>, StorageOperationStatus> updateInputsToComponent(List<InputDefinition> inputs, String componentId) {
1295         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1296         if (getVertexEither.isRight()) {
1297             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1298             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
1299         }
1300         GraphVertex vertex = getVertexEither.left().value();
1301         List<PropertyDataDefinition> inputsAsDataDef = inputs.stream().map(PropertyDataDefinition::new).collect(Collectors.toList());
1302         StorageOperationStatus status = topologyTemplateOperation
1303             .updateToscaDataOfToscaElement(vertex, EdgeLabelEnum.INPUTS, VertexTypeEnum.INPUTS, inputsAsDataDef, JsonPresentationFields.NAME);
1304         if (StorageOperationStatus.OK == status) {
1305             log.debug(COMPONENT_CREATED_SUCCESSFULLY);
1306             List<InputDefinition> inputsResList = null;
1307             if (inputsAsDataDef != null && !inputsAsDataDef.isEmpty()) {
1308                 inputsResList = inputsAsDataDef.stream().map(InputDefinition::new).collect(Collectors.toList());
1309             }
1310             return Either.left(inputsResList);
1311         }
1312         return Either.right(status);
1313     }
1314
1315     // region - ComponentInstance
1316     public Either<Map<String, List<ComponentInstanceProperty>>, StorageOperationStatus> associateComponentInstancePropertiesToComponent(
1317         Map<String, List<ComponentInstanceProperty>> instProperties, String componentId) {
1318         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1319         if (getVertexEither.isRight()) {
1320             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1321             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
1322         }
1323         GraphVertex vertex = getVertexEither.left().value();
1324         Map<String, MapPropertiesDataDefinition> instPropsMap = new HashMap<>();
1325         if (instProperties != null) {
1326             MapPropertiesDataDefinition propertiesMap;
1327             for (Entry<String, List<ComponentInstanceProperty>> entry : instProperties.entrySet()) {
1328                 propertiesMap = new MapPropertiesDataDefinition();
1329                 propertiesMap.setMapToscaDataDefinition(
1330                     entry.getValue().stream().map(PropertyDataDefinition::new).collect(Collectors.toMap(PropertyDataDefinition::getName, e -> e)));
1331                 instPropsMap.put(entry.getKey(), propertiesMap);
1332             }
1333         }
1334         StorageOperationStatus status = topologyTemplateOperation.associateInstPropertiesToComponent(vertex, instPropsMap);
1335         if (StorageOperationStatus.OK == status) {
1336             log.debug(COMPONENT_CREATED_SUCCESSFULLY);
1337             return Either.left(instProperties);
1338         }
1339         return Either.right(status);
1340     }
1341
1342     /**
1343      * saves the instInputs as the updated instance inputs of the component container in DB
1344      */
1345     public Either<Map<String, List<ComponentInstanceInput>>, StorageOperationStatus> updateComponentInstanceInputsToComponent(
1346         Map<String, List<ComponentInstanceInput>> instInputs, String componentId) {
1347         if (instInputs == null || instInputs.isEmpty()) {
1348             return Either.left(instInputs);
1349         }
1350         StorageOperationStatus status;
1351         for (Entry<String, List<ComponentInstanceInput>> inputsPerIntance : instInputs.entrySet()) {
1352             List<ComponentInstanceInput> toscaDataListPerInst = inputsPerIntance.getValue();
1353             List<String> pathKeysPerInst = new ArrayList<>();
1354             pathKeysPerInst.add(inputsPerIntance.getKey());
1355             status = topologyTemplateOperation
1356                 .updateToscaDataDeepElementsOfToscaElement(componentId, EdgeLabelEnum.INST_INPUTS, VertexTypeEnum.INST_INPUTS, toscaDataListPerInst,
1357                     pathKeysPerInst, JsonPresentationFields.NAME);
1358             if (status != StorageOperationStatus.OK) {
1359                 log.debug("Failed to update component instance inputs for instance {} in component {} edge type {} error {}",
1360                     inputsPerIntance.getKey(), componentId, EdgeLabelEnum.INST_INPUTS, status);
1361                 return Either.right(status);
1362             }
1363         }
1364         return Either.left(instInputs);
1365     }
1366
1367     /**
1368      * saves the instProps as the updated instance properties of the component container in DB
1369      */
1370     public Either<Map<String, List<ComponentInstanceProperty>>, StorageOperationStatus> updateComponentInstancePropsToComponent(
1371         Map<String, List<ComponentInstanceProperty>> instProps, String componentId) {
1372         if (instProps == null || instProps.isEmpty()) {
1373             return Either.left(instProps);
1374         }
1375         StorageOperationStatus status;
1376         for (Entry<String, List<ComponentInstanceProperty>> propsPerIntance : instProps.entrySet()) {
1377             List<ComponentInstanceProperty> toscaDataListPerInst = propsPerIntance.getValue();
1378             List<String> pathKeysPerInst = new ArrayList<>();
1379             pathKeysPerInst.add(propsPerIntance.getKey());
1380             status = topologyTemplateOperation
1381                 .updateToscaDataDeepElementsOfToscaElement(componentId, EdgeLabelEnum.INST_PROPERTIES, VertexTypeEnum.INST_PROPERTIES,
1382                     toscaDataListPerInst, pathKeysPerInst, JsonPresentationFields.NAME);
1383             if (status != StorageOperationStatus.OK) {
1384                 log.debug("Failed to update component instance inputs for instance {} in component {} edge type {} error {}",
1385                     propsPerIntance.getKey(), componentId, EdgeLabelEnum.INST_PROPERTIES, status);
1386                 return Either.right(status);
1387             }
1388         }
1389         return Either.left(instProps);
1390     }
1391
1392     public Either<Map<String, List<ComponentInstanceInput>>, StorageOperationStatus> associateComponentInstanceInputsToComponent(
1393         Map<String, List<ComponentInstanceInput>> instInputs, String componentId) {
1394         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1395         if (getVertexEither.isRight()) {
1396             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1397             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
1398         }
1399         GraphVertex vertex = getVertexEither.left().value();
1400         Map<String, MapPropertiesDataDefinition> instPropsMap = new HashMap<>();
1401         if (instInputs != null) {
1402             MapPropertiesDataDefinition propertiesMap;
1403             for (Entry<String, List<ComponentInstanceInput>> entry : instInputs.entrySet()) {
1404                 propertiesMap = new MapPropertiesDataDefinition();
1405                 propertiesMap.setMapToscaDataDefinition(
1406                     entry.getValue().stream().map(PropertyDataDefinition::new).collect(Collectors.toMap(PropertyDataDefinition::getName, e -> e)));
1407                 instPropsMap.put(entry.getKey(), propertiesMap);
1408             }
1409         }
1410         StorageOperationStatus status = topologyTemplateOperation.associateInstInputsToComponent(vertex, instPropsMap);
1411         if (StorageOperationStatus.OK == status) {
1412             log.debug(COMPONENT_CREATED_SUCCESSFULLY);
1413             return Either.left(instInputs);
1414         }
1415         return Either.right(status);
1416     }
1417
1418     public Either<Map<String, List<ComponentInstanceInput>>, StorageOperationStatus> addComponentInstanceInputsToComponent(
1419         Component containerComponent, Map<String, List<ComponentInstanceInput>> instProperties) {
1420         requireNonNull(instProperties);
1421         StorageOperationStatus status;
1422         for (Entry<String, List<ComponentInstanceInput>> entry : instProperties.entrySet()) {
1423             List<ComponentInstanceInput> props = entry.getValue();
1424             String componentInstanceId = entry.getKey();
1425             if (!isEmpty(props)) {
1426                 for (ComponentInstanceInput property : props) {
1427                     List<ComponentInstanceInput> componentInstancesInputs = containerComponent.getComponentInstancesInputs().get(componentInstanceId);
1428                     Optional<ComponentInstanceInput> instanceProperty = componentInstancesInputs.stream()
1429                         .filter(p -> p.getName().equals(property.getName())).findAny();
1430                     if (instanceProperty.isPresent()) {
1431                         status = updateComponentInstanceInput(containerComponent, componentInstanceId, property);
1432                     } else {
1433                         status = addComponentInstanceInput(containerComponent, componentInstanceId, property);
1434                     }
1435                     if (status != StorageOperationStatus.OK) {
1436                         log.debug("Failed to update instance input {} for instance {} error {} ", property, componentInstanceId, status);
1437                         return Either.right(status);
1438                     } else {
1439                         log.trace("instance input {} for instance {} updated", property, componentInstanceId);
1440                     }
1441                 }
1442             }
1443         }
1444         return Either.left(instProperties);
1445     }
1446
1447     public Either<Map<String, List<ComponentInstanceOutput>>, StorageOperationStatus> addComponentInstanceOutputsToComponent(
1448         Component containerComponent, Map<String, List<ComponentInstanceOutput>> instProperties) {
1449         requireNonNull(instProperties);
1450         StorageOperationStatus status;
1451         for (final Entry<String, List<ComponentInstanceOutput>> entry : instProperties.entrySet()) {
1452             final List<ComponentInstanceOutput> props = entry.getValue();
1453             final String componentInstanceId = entry.getKey();
1454             if (!isEmpty(props)) {
1455                 for (final ComponentInstanceOutput property : props) {
1456                     final List<ComponentInstanceOutput> componentInstancesInputs = containerComponent.getComponentInstancesOutputs()
1457                         .get(componentInstanceId);
1458                     final Optional<ComponentInstanceOutput> instanceProperty = componentInstancesInputs.stream()
1459                         .filter(p -> p.getName().equals(property.getName())).findAny();
1460                     if (instanceProperty.isPresent()) {
1461                         status = updateComponentInstanceOutput(containerComponent, componentInstanceId, property);
1462                     } else {
1463                         status = addComponentInstanceOutput(containerComponent, componentInstanceId, property);
1464                     }
1465                     if (status != StorageOperationStatus.OK) {
1466                         log.debug("Failed to update instance input {} for instance {} error {} ", property, componentInstanceId, status);
1467                         return Either.right(status);
1468                     } else {
1469                         log.trace("instance input {} for instance {} updated", property, componentInstanceId);
1470                     }
1471                 }
1472             }
1473         }
1474         return Either.left(instProperties);
1475     }
1476
1477     public Either<Map<String, List<ComponentInstanceProperty>>, StorageOperationStatus> addComponentInstancePropertiesToComponent(
1478         Component containerComponent, Map<String, List<ComponentInstanceProperty>> instProperties) {
1479         requireNonNull(instProperties);
1480         for (Entry<String, List<ComponentInstanceProperty>> entry : instProperties.entrySet()) {
1481             List<ComponentInstanceProperty> props = entry.getValue();
1482             String componentInstanceId = entry.getKey();
1483             List<ComponentInstanceProperty> originalComponentInstProps = containerComponent.getComponentInstancesProperties()
1484                 .get(componentInstanceId);
1485             Map<String, List<CapabilityDefinition>> containerComponentCapabilities = containerComponent.getCapabilities();
1486             if (isEmpty(props)) {
1487                 continue;
1488             }
1489             for (ComponentInstanceProperty property : props) {
1490                 StorageOperationStatus status = null;
1491                 String propertyParentUniqueId = property.getParentUniqueId();
1492                 Optional<CapabilityDefinition> capPropDefinition = getPropertyCapability(propertyParentUniqueId, containerComponent);
1493                 if (capPropDefinition.isPresent() && MapUtils.isNotEmpty(containerComponentCapabilities)) {
1494                     status = populateAndUpdateInstanceCapProperty(containerComponent, componentInstanceId, containerComponentCapabilities, property,
1495                         capPropDefinition.get());
1496                 }
1497                 if (status == null) {
1498                     status = updateOrAddComponentInstanceProperty(containerComponent, componentInstanceId, originalComponentInstProps, property);
1499                 }
1500                 if (status != StorageOperationStatus.OK) {
1501                     return Either.right(status);
1502                 }
1503             }
1504         }
1505         return Either.left(instProperties);
1506     }
1507
1508     public Either<Map<String, List<ComponentInstanceAttribute>>, StorageOperationStatus> addComponentInstanceAttributesToComponent(
1509         final Component containerComponent, final Map<String, List<ComponentInstanceAttribute>> instProperties) {
1510         requireNonNull(instProperties);
1511         for (final Entry<String, List<ComponentInstanceAttribute>> entry : instProperties.entrySet()) {
1512             final List<ComponentInstanceAttribute> props = entry.getValue();
1513             if (isEmpty(props)) {
1514                 continue;
1515             }
1516             final String componentInstanceId = entry.getKey();
1517             final List<ComponentInstanceAttribute> originalComponentInstProps = containerComponent.getComponentInstancesAttributes()
1518                 .get(componentInstanceId);
1519             for (final ComponentInstanceAttribute property : props) {
1520                 final StorageOperationStatus status = updateOrAddComponentInstanceAttribute(containerComponent, componentInstanceId,
1521                     originalComponentInstProps, property);
1522                 if (status != StorageOperationStatus.OK) {
1523                     return Either.right(status);
1524                 }
1525             }
1526         }
1527         return Either.left(instProperties);
1528     }
1529
1530     private StorageOperationStatus populateAndUpdateInstanceCapProperty(Component containerComponent, String componentInstanceId,
1531                                                                         Map<String, List<CapabilityDefinition>> containerComponentCapabilities,
1532                                                                         ComponentInstanceProperty property,
1533                                                                         CapabilityDefinition capabilityDefinition) {
1534         List<CapabilityDefinition> capabilityDefinitions = containerComponentCapabilities.get(capabilityDefinition.getType());
1535         if (CollectionUtils.isEmpty(capabilityDefinitions)) {
1536             return null;
1537         }
1538         Optional<CapabilityDefinition> capDefToGetProp = capabilityDefinitions.stream()
1539             .filter(cap -> cap.getUniqueId().equals(capabilityDefinition.getUniqueId()) && cap.getPath().size() == 1).findAny();
1540         if (capDefToGetProp.isPresent()) {
1541             return updateInstanceCapabilityProperty(containerComponent, componentInstanceId, property, capDefToGetProp.get());
1542         }
1543         return null;
1544     }
1545
1546     private StorageOperationStatus updateOrAddComponentInstanceProperty(Component containerComponent, String componentInstanceId,
1547                                                                         List<ComponentInstanceProperty> originalComponentInstProps,
1548                                                                         ComponentInstanceProperty property) {
1549         StorageOperationStatus status;
1550         // check if the property already exists or not
1551         Optional<ComponentInstanceProperty> instanceProperty = originalComponentInstProps.stream()
1552             .filter(p -> p.getUniqueId().equals(property.getUniqueId())).findAny();
1553         if (instanceProperty.isPresent()) {
1554             status = updateComponentInstanceProperty(containerComponent, componentInstanceId, property);
1555         } else {
1556             status = addComponentInstanceProperty(containerComponent, componentInstanceId, property);
1557         }
1558         if (status != StorageOperationStatus.OK) {
1559             log.debug("Failed to update instance property {} for instance {} error {} ", property, componentInstanceId, status);
1560         }
1561         return status;
1562     }
1563
1564     private StorageOperationStatus updateOrAddComponentInstanceAttribute(Component containerComponent, String componentInstanceId,
1565                                                                          List<ComponentInstanceAttribute> originalComponentInstProps,
1566                                                                          ComponentInstanceAttribute property) {
1567         StorageOperationStatus status;
1568         // check if the property already exists or not
1569         Optional<ComponentInstanceAttribute> instanceProperty = originalComponentInstProps.stream()
1570             .filter(p -> p.getUniqueId().equals(property.getUniqueId())).findAny();
1571         if (instanceProperty.isPresent()) {
1572             status = updateComponentInstanceAttribute(containerComponent, componentInstanceId, property);
1573         } else {
1574             status = addComponentInstanceAttribute(containerComponent, componentInstanceId, property);
1575         }
1576         if (status != StorageOperationStatus.OK) {
1577             log.debug("Failed to update instance property {} for instance {} error {} ", property, componentInstanceId, status);
1578         }
1579         return status;
1580     }
1581
1582     public StorageOperationStatus updateInstanceCapabilityProperty(Component containerComponent, String componentInstanceId,
1583                                                                    ComponentInstanceProperty property, CapabilityDefinition capabilityDefinition) {
1584         Optional<ComponentInstance> fetchedCIOptional = containerComponent.getComponentInstanceById(componentInstanceId);
1585         if (!fetchedCIOptional.isPresent()) {
1586             return StorageOperationStatus.GENERAL_ERROR;
1587         }
1588         Either<Component, StorageOperationStatus> getComponentRes = getToscaFullElement(fetchedCIOptional.get().getComponentUid());
1589         if (getComponentRes.isRight()) {
1590             return StorageOperationStatus.GENERAL_ERROR;
1591         }
1592         Optional<Component> componentOptional = isNodeServiceProxy(getComponentRes.left().value());
1593         String propOwner;
1594         if (!componentOptional.isPresent()) {
1595             propOwner = componentInstanceId;
1596         } else {
1597             propOwner = fetchedCIOptional.get().getSourceModelUid();
1598         }
1599         StorageOperationStatus status;
1600         StringBuilder sb = new StringBuilder(componentInstanceId);
1601         sb.append(ModelConverter.CAP_PROP_DELIM).append(propOwner).append(ModelConverter.CAP_PROP_DELIM).append(capabilityDefinition.getType())
1602             .append(ModelConverter.CAP_PROP_DELIM).append(capabilityDefinition.getName());
1603         String capKey = sb.toString();
1604         status = updateComponentInstanceCapabiltyProperty(containerComponent, componentInstanceId, capKey, property);
1605         if (status != StorageOperationStatus.OK) {
1606             log.debug("Failed to update instance capability property {} for instance {} error {} ", property, componentInstanceId, status);
1607             return status;
1608         }
1609         return StorageOperationStatus.OK;
1610     }
1611
1612     private Optional<Component> isNodeServiceProxy(Component component) {
1613         if (component.getComponentType().equals(ComponentTypeEnum.SERVICE)) {
1614             return Optional.empty();
1615         }
1616         Resource resource = (Resource) component;
1617         ResourceTypeEnum resType = resource.getResourceType();
1618         if (resType.equals(ResourceTypeEnum.ServiceProxy)) {
1619             return Optional.of(component);
1620         }
1621         return Optional.empty();
1622     }
1623
1624     public StorageOperationStatus associateCapabilitiesToService(Map<String, ListCapabilityDataDefinition> capabilities, String componentId) {
1625         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1626         if (getVertexEither.isRight()) {
1627             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1628             return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value());
1629         }
1630         GraphVertex vertex = getVertexEither.left().value();
1631         if (MapUtils.isNotEmpty(capabilities)) {
1632             Either<GraphVertex, StorageOperationStatus> associateElementToData = topologyTemplateOperation
1633                 .associateElementToData(vertex, VertexTypeEnum.CAPABILITIES, EdgeLabelEnum.CAPABILITIES, capabilities);
1634             if (associateElementToData.isRight()) {
1635                 return associateElementToData.right().value();
1636             }
1637         }
1638         return StorageOperationStatus.OK;
1639     }
1640
1641     public StorageOperationStatus associateRequirementsToService(Map<String, ListRequirementDataDefinition> requirements, String componentId) {
1642         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
1643         if (getVertexEither.isRight()) {
1644             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
1645             return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value());
1646         }
1647         GraphVertex vertex = getVertexEither.left().value();
1648         if (MapUtils.isNotEmpty(requirements)) {
1649             Either<GraphVertex, StorageOperationStatus> associateElementToData = topologyTemplateOperation
1650                 .associateElementToData(vertex, VertexTypeEnum.REQUIREMENTS, EdgeLabelEnum.REQUIREMENTS, requirements);
1651             if (associateElementToData.isRight()) {
1652                 return associateElementToData.right().value();
1653             }
1654         }
1655         return StorageOperationStatus.OK;
1656     }
1657
1658     public StorageOperationStatus associateDeploymentArtifactsToInstances(Map<String, Map<String, ArtifactDefinition>> instDeploymentArtifacts,
1659                                                                           Component component, User user) {
1660         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao
1661             .getVertexById(component.getUniqueId(), JsonParseFlagEnum.NoParse);
1662         if (getVertexEither.isRight()) {
1663             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, component.getUniqueId(), getVertexEither.right().value());
1664             return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value());
1665         }
1666         GraphVertex vertex = getVertexEither.left().value();
1667         Map<String, MapArtifactDataDefinition> instArtMap = new HashMap<>();
1668         if (instDeploymentArtifacts != null) {
1669             MapArtifactDataDefinition artifactsMap;
1670             for (Entry<String, Map<String, ArtifactDefinition>> entry : instDeploymentArtifacts.entrySet()) {
1671                 Map<String, ArtifactDefinition> artList = entry.getValue();
1672                 Map<String, ArtifactDataDefinition> artifacts = artList.entrySet().stream()
1673                     .collect(Collectors.toMap(Map.Entry::getKey, e -> new ArtifactDataDefinition(e.getValue())));
1674                 artifactsMap = nodeTemplateOperation
1675                     .prepareInstDeploymentArtifactPerInstance(artifacts, entry.getKey(), user, NodeTemplateOperation.HEAT_VF_ENV_NAME);
1676                 instArtMap.put(entry.getKey(), artifactsMap);
1677             }
1678         }
1679         ModelConverter.setComponentInstancesDeploymentArtifactsToComponent(instArtMap, component);
1680         return topologyTemplateOperation.associateInstDeploymentArtifactsToComponent(vertex, instArtMap);
1681     }
1682
1683     public StorageOperationStatus associateArtifactsToInstances(Map<String, Map<String, ArtifactDefinition>> instArtifacts, Component component) {
1684         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao
1685             .getVertexById(component.getUniqueId(), JsonParseFlagEnum.NoParse);
1686         if (getVertexEither.isRight()) {
1687             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, component.getUniqueId(), getVertexEither.right().value());
1688             return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value());
1689         }
1690         GraphVertex vertex = getVertexEither.left().value();
1691         Map<String, MapArtifactDataDefinition> instArtMap = new HashMap<>();
1692         if (instArtifacts != null) {
1693             MapArtifactDataDefinition artifactsMap;
1694             for (Entry<String, Map<String, ArtifactDefinition>> entry : instArtifacts.entrySet()) {
1695                 Map<String, ArtifactDefinition> artList = entry.getValue();
1696                 Map<String, ArtifactDataDefinition> artifacts = artList.entrySet().stream()
1697                     .collect(Collectors.toMap(Map.Entry::getKey, e -> new ArtifactDataDefinition(e.getValue())));
1698                 artifactsMap = new MapArtifactDataDefinition(artifacts);
1699                 instArtMap.put(entry.getKey(), artifactsMap);
1700             }
1701         }
1702         ModelConverter.setComponentInstancesInformationalArtifactsToComponent(instArtMap, component);
1703         return topologyTemplateOperation.associateInstArtifactsToComponent(vertex, instArtMap);
1704     }
1705
1706     public StorageOperationStatus associateInstAttributeToComponentToInstances(Map<String, List<AttributeDefinition>> instArttributes,
1707                                                                                Component component) {
1708         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao
1709             .getVertexById(component.getUniqueId(), JsonParseFlagEnum.NoParse);
1710         if (getVertexEither.isRight()) {
1711             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, component.getUniqueId(), getVertexEither.right().value());
1712             return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value());
1713         }
1714         GraphVertex vertex = getVertexEither.left().value();
1715         Map<String, MapAttributesDataDefinition> instAttr = new HashMap<>();
1716         if (instArttributes != null) {
1717             MapAttributesDataDefinition attributesMap;
1718             for (Entry<String, List<AttributeDefinition>> entry : instArttributes.entrySet()) {
1719                 final List<AttributeDefinition> value = entry.getValue();
1720                 attributesMap = new MapAttributesDataDefinition();
1721                 attributesMap.setMapToscaDataDefinition(
1722                     value.stream().map(AttributeDefinition::new).collect(Collectors.toMap(AttributeDefinition::getName, e -> e)));
1723                 instAttr.put(entry.getKey(), attributesMap);
1724             }
1725         }
1726         setComponentInstanceAttributesOnComponent(component, instAttr);
1727         return topologyTemplateOperation.associateInstAttributeToComponent(vertex, instAttr);
1728     }
1729
1730     // endregion
1731     private void setComponentInstanceAttributesOnComponent(Component resource, Map<String, MapAttributesDataDefinition> instAttr) {
1732         Map<String, List<ComponentInstanceAttribute>> componentInstancesAttributes = resource.getComponentInstancesAttributes();
1733         if (componentInstancesAttributes == null) {
1734             componentInstancesAttributes = new HashMap<>();
1735         }
1736         componentInstancesAttributes.putAll(ModelConverter.getComponentInstancesAttributes(instAttr));
1737         resource.setComponentInstancesAttributes(componentInstancesAttributes);
1738     }
1739
1740     public StorageOperationStatus associateOrAddCalculatedCapReq(Map<ComponentInstance, Map<String, List<CapabilityDefinition>>> instCapabilties,
1741                                                                  Map<ComponentInstance, Map<String, List<RequirementDefinition>>> instReg,
1742                                                                  Component component) {
1743         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao
1744             .getVertexById(component.getUniqueId(), JsonParseFlagEnum.NoParse);
1745         if (getVertexEither.isRight()) {
1746             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, component.getUniqueId(), getVertexEither.right().value());
1747             return DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value());
1748         }
1749         GraphVertex vertex = getVertexEither.left().value();
1750         Map<String, MapListRequirementDataDefinition> calcRequirements = new HashMap<>();
1751         Map<String, MapListCapabilityDataDefinition> calcCapabilty = new HashMap<>();
1752         Map<String, MapCapabilityProperty> calculatedCapabilitiesProperties = new HashMap<>();
1753         if (instCapabilties != null) {
1754             for (Entry<ComponentInstance, Map<String, List<CapabilityDefinition>>> entry : instCapabilties.entrySet()) {
1755                 Map<String, List<CapabilityDefinition>> caps = entry.getValue();
1756                 Map<String, ListCapabilityDataDefinition> mapToscaDataDefinition = new HashMap<>();
1757                 for (Entry<String, List<CapabilityDefinition>> instCapability : caps.entrySet()) {
1758                     mapToscaDataDefinition.put(instCapability.getKey(), new ListCapabilityDataDefinition(
1759                         instCapability.getValue().stream().map(CapabilityDataDefinition::new).collect(Collectors.toList())));
1760                 }
1761                 ComponentInstanceDataDefinition componentInstance = new ComponentInstanceDataDefinition(entry.getKey());
1762                 MapListCapabilityDataDefinition capMap = nodeTemplateOperation
1763                     .prepareCalculatedCapabiltyForNodeType(mapToscaDataDefinition, componentInstance);
1764                 MapCapabilityProperty mapCapabilityProperty = ModelConverter
1765                     .convertToMapOfMapCapabiltyProperties(caps, componentInstance.getUniqueId(), true);
1766                 calcCapabilty.put(entry.getKey().getUniqueId(), capMap);
1767                 calculatedCapabilitiesProperties.put(entry.getKey().getUniqueId(), mapCapabilityProperty);
1768             }
1769         }
1770         if (instReg != null) {
1771             for (Entry<ComponentInstance, Map<String, List<RequirementDefinition>>> entry : instReg.entrySet()) {
1772                 Map<String, List<RequirementDefinition>> req = entry.getValue();
1773                 Map<String, ListRequirementDataDefinition> mapToscaDataDefinition = new HashMap<>();
1774                 for (Entry<String, List<RequirementDefinition>> instReq : req.entrySet()) {
1775                     mapToscaDataDefinition.put(instReq.getKey(), new ListRequirementDataDefinition(
1776                         instReq.getValue().stream().map(RequirementDataDefinition::new).collect(Collectors.toList())));
1777                 }
1778                 MapListRequirementDataDefinition reqMap = nodeTemplateOperation
1779                     .prepareCalculatedRequirementForNodeType(mapToscaDataDefinition, new ComponentInstanceDataDefinition(entry.getKey()));
1780                 String componentInstanceId = entry.getKey().getUniqueId();
1781                 calcRequirements.put(componentInstanceId, reqMap);
1782             }
1783         }
1784         StorageOperationStatus storageOperationStatus = topologyTemplateOperation
1785             .associateOrAddCalcCapReqToComponent(vertex, calcRequirements, calcCapabilty, calculatedCapabilitiesProperties);
1786         updateInstancesCapAndReqOnComponentFromDB(component);
1787         return storageOperationStatus;
1788     }
1789
1790     private void updateInstancesCapAndReqOnComponentFromDB(Component component) {
1791         ComponentParametersView componentParametersView = new ComponentParametersView(true);
1792         componentParametersView.setIgnoreCapabilities(false);
1793         componentParametersView.setIgnoreRequirements(false);
1794         componentParametersView.setIgnoreCapabiltyProperties(false);
1795         componentParametersView.setIgnoreComponentInstances(false);
1796         Either<Component, StorageOperationStatus> componentEither = getToscaElement(component.getUniqueId(), componentParametersView);
1797         if (componentEither.isRight()) {
1798             throw new StorageException(StorageOperationStatus.NOT_FOUND);
1799         }
1800         Component updatedComponent = componentEither.left().value();
1801         component.setCapabilities(updatedComponent.getCapabilities());
1802         component.setRequirements(updatedComponent.getRequirements());
1803         component.setComponentInstances(updatedComponent.getComponentInstances());
1804     }
1805
1806     private Either<List<Service>, StorageOperationStatus> getLatestVersionNonCheckoutServicesMetadataOnly(Map<GraphPropertyEnum, Object> hasProps,
1807                                                                                                           Map<GraphPropertyEnum, Object> hasNotProps) {
1808         List<Service> services = new ArrayList<>();
1809         List<LifecycleStateEnum> states = new ArrayList<>();
1810         // include props
1811         hasProps.put(GraphPropertyEnum.COMPONENT_TYPE, ComponentTypeEnum.SERVICE.name());
1812         hasProps.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
1813         // exclude props
1814         states.add(LifecycleStateEnum.NOT_CERTIFIED_CHECKOUT);
1815         hasNotProps.put(GraphPropertyEnum.STATE, states);
1816         hasNotProps.put(GraphPropertyEnum.IS_DELETED, true);
1817         hasNotProps.put(GraphPropertyEnum.IS_ARCHIVED, true);
1818         return fetchServicesByCriteria(services, hasProps, hasNotProps);
1819     }
1820
1821     private Either<List<Component>, StorageOperationStatus> getLatestVersionNotAbstractToscaElementsMetadataOnly(boolean isAbstract,
1822                                                                                                                  ComponentTypeEnum componentTypeEnum,
1823                                                                                                                  String internalComponentType,
1824                                                                                                                  VertexTypeEnum vertexType) {
1825         List<Service> services = null;
1826         Map<GraphPropertyEnum, Object> hasProps = new EnumMap<>(GraphPropertyEnum.class);
1827         Map<GraphPropertyEnum, Object> hasNotProps = new EnumMap<>(GraphPropertyEnum.class);
1828         fillPropsMap(hasProps, hasNotProps, internalComponentType, componentTypeEnum, isAbstract, vertexType);
1829         Either<List<GraphVertex>, JanusGraphOperationStatus> getRes = janusGraphDao
1830             .getByCriteria(vertexType, hasProps, hasNotProps, JsonParseFlagEnum.ParseMetadata);
1831         if (getRes.isRight()) {
1832             if (getRes.right().value().equals(JanusGraphOperationStatus.NOT_FOUND)) {
1833                 return Either.left(new ArrayList<>());
1834             } else {
1835                 return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getRes.right().value()));
1836             }
1837         }
1838         // region -> Fetch non checked-out services
1839         if (internalComponentType != null && internalComponentType.toLowerCase().trim().equals(SERVICE) && VertexTypeEnum.NODE_TYPE == vertexType) {
1840             Either<List<Service>, StorageOperationStatus> result = getLatestVersionNonCheckoutServicesMetadataOnly(
1841                 new EnumMap<>(GraphPropertyEnum.class), new EnumMap<>(GraphPropertyEnum.class));
1842             if (result.isRight()) {
1843                 log.debug("Failed to fetch services for");
1844                 return Either.right(result.right().value());
1845             }
1846             services = result.left().value();
1847             if (log.isTraceEnabled() && isEmpty(services)) {
1848                 log.trace("No relevant services available");
1849             }
1850         }
1851         // endregion
1852         List<Component> nonAbstractLatestComponents = new ArrayList<>();
1853         ComponentParametersView params = new ComponentParametersView(true);
1854         params.setIgnoreAllVersions(false);
1855         for (GraphVertex vertexComponent : getRes.left().value()) {
1856             Either<ToscaElement, StorageOperationStatus> componentRes = topologyTemplateOperation
1857                 .getLightComponent(vertexComponent, componentTypeEnum, params);
1858             if (componentRes.isRight()) {
1859                 log.debug("Failed to fetch light element for {} error {}", vertexComponent.getUniqueId(), componentRes.right().value());
1860                 return Either.right(componentRes.right().value());
1861             } else {
1862                 Component component = ModelConverter.convertFromToscaElement(componentRes.left().value());
1863                 nonAbstractLatestComponents.add(component);
1864             }
1865         }
1866         if (CollectionUtils.isNotEmpty(services)) {
1867             nonAbstractLatestComponents.addAll(services);
1868         }
1869         return Either.left(nonAbstractLatestComponents);
1870     }
1871
1872     public Either<ComponentMetadataData, StorageOperationStatus> getLatestComponentMetadataByUuid(String componentUuid, JsonParseFlagEnum parseFlag,
1873                                                                                                   Boolean isHighest) {
1874         Either<ComponentMetadataData, StorageOperationStatus> result;
1875         Map<GraphPropertyEnum, Object> hasProperties = new EnumMap<>(GraphPropertyEnum.class);
1876         hasProperties.put(GraphPropertyEnum.UUID, componentUuid);
1877         if (isHighest != null) {
1878             hasProperties.put(GraphPropertyEnum.IS_HIGHEST_VERSION, isHighest);
1879         }
1880         Map<GraphPropertyEnum, Object> propertiesNotToMatch = new EnumMap<>(GraphPropertyEnum.class);
1881         propertiesNotToMatch.put(GraphPropertyEnum.IS_DELETED, true);
1882         propertiesNotToMatch.put(GraphPropertyEnum.IS_ARCHIVED, true); //US382674, US382683
1883         Either<List<GraphVertex>, JanusGraphOperationStatus> getRes = janusGraphDao
1884             .getByCriteria(null, hasProperties, propertiesNotToMatch, parseFlag);
1885         if (getRes.isRight()) {
1886             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getRes.right().value()));
1887         } else {
1888             List<ComponentMetadataData> latestVersionList = getRes.left().value().stream().map(ModelConverter::convertToComponentMetadata)
1889                 .collect(Collectors.toList());
1890             ComponentMetadataData latestVersion = latestVersionList.size() == 1 ? latestVersionList.get(0) : latestVersionList.stream().max(
1891                 (c1, c2) -> Double.compare(Double.parseDouble(c1.getMetadataDataDefinition().getVersion()),
1892                     Double.parseDouble(c2.getMetadataDataDefinition().getVersion()))).get();
1893             result = Either.left(latestVersion);
1894         }
1895         return result;
1896     }
1897
1898     public Either<ComponentMetadataData, StorageOperationStatus> getComponentMetadata(String componentId) {
1899         Either<ComponentMetadataData, StorageOperationStatus> result;
1900         Either<GraphVertex, JanusGraphOperationStatus> getRes = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.ParseMetadata);
1901         if (getRes.isRight()) {
1902             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getRes.right().value()));
1903         } else {
1904             ComponentMetadataData componentMetadata = ModelConverter.convertToComponentMetadata(getRes.left().value());
1905             result = Either.left(componentMetadata);
1906         }
1907         return result;
1908     }
1909
1910     public Either<List<Component>, StorageOperationStatus> getLatestVersionNotAbstractComponents(boolean isAbstract,
1911                                                                                                  ComponentTypeEnum componentTypeEnum,
1912                                                                                                  String internalComponentType,
1913                                                                                                  List<String> componentUids) {
1914         List<Component> components = new ArrayList<>();
1915         if (componentUids == null) {
1916             Either<List<String>, StorageOperationStatus> componentUidsRes = getComponentUids(isAbstract, componentTypeEnum, internalComponentType);
1917             if (componentUidsRes.isRight()) {
1918                 return Either.right(componentUidsRes.right().value());
1919             }
1920             componentUids = componentUidsRes.left().value();
1921         }
1922         if (!isEmpty(componentUids)) {
1923             for (String componentUid : componentUids) {
1924                 ComponentParametersView componentParametersView = buildComponentViewForNotAbstract();
1925                 if ("vl".equalsIgnoreCase(internalComponentType)) {
1926                     componentParametersView.setIgnoreCapabilities(false);
1927                     componentParametersView.setIgnoreRequirements(false);
1928                 }
1929                 Either<ToscaElement, StorageOperationStatus> getToscaElementRes = nodeTemplateOperation.getToscaElementOperation(componentTypeEnum)
1930                     .getLightComponent(componentUid, componentTypeEnum, componentParametersView);
1931                 if (getToscaElementRes.isRight()) {
1932                     log.debug("Failed to fetch resource for error is {}", getToscaElementRes.right().value());
1933                     return Either.right(getToscaElementRes.right().value());
1934                 }
1935                 Component component = ModelConverter.convertFromToscaElement(getToscaElementRes.left().value());
1936                 nullifySomeComponentProperties(component);
1937                 components.add(component);
1938             }
1939         }
1940         return Either.left(components);
1941     }
1942
1943     public void nullifySomeComponentProperties(Component component) {
1944         component.setContactId(null);
1945         component.setCreationDate(null);
1946         component.setCreatorUserId(null);
1947         component.setCreatorFullName(null);
1948         component.setLastUpdateDate(null);
1949         component.setLastUpdaterUserId(null);
1950         component.setLastUpdaterFullName(null);
1951         component.setNormalizedName(null);
1952     }
1953
1954     private Either<List<String>, StorageOperationStatus> getComponentUids(boolean isAbstract, ComponentTypeEnum componentTypeEnum,
1955                                                                           String internalComponentType) {
1956         Either<List<Component>, StorageOperationStatus> getToscaElementsRes = getLatestVersionNotAbstractMetadataOnly(isAbstract, componentTypeEnum,
1957             internalComponentType);
1958         if (getToscaElementsRes.isRight()) {
1959             return Either.right(getToscaElementsRes.right().value());
1960         }
1961         List<Component> collection = getToscaElementsRes.left().value();
1962         List<String> componentUids;
1963         if (collection == null) {
1964             componentUids = new ArrayList<>();
1965         } else {
1966             componentUids = collection.stream().map(Component::getUniqueId).collect(Collectors.toList());
1967         }
1968         return Either.left(componentUids);
1969     }
1970
1971     private ComponentParametersView buildComponentViewForNotAbstract() {
1972         ComponentParametersView componentParametersView = new ComponentParametersView();
1973         componentParametersView.disableAll();
1974         componentParametersView.setIgnoreCategories(false);
1975         componentParametersView.setIgnoreAllVersions(false);
1976         return componentParametersView;
1977     }
1978
1979     public Either<Boolean, StorageOperationStatus> validateComponentNameExists(String name, ResourceTypeEnum resourceType,
1980                                                                                ComponentTypeEnum componentType) {
1981         Either<Boolean, StorageOperationStatus> result = validateComponentNameUniqueness(name, resourceType, componentType);
1982         if (result.isLeft()) {
1983             result = Either.left(!result.left().value());
1984         }
1985         return result;
1986     }
1987
1988     public Either<Boolean, StorageOperationStatus> validateComponentNameUniqueness(String name, ResourceTypeEnum resourceType,
1989                                                                                    ComponentTypeEnum componentType) {
1990         VertexTypeEnum vertexType = ModelConverter.isAtomicComponent(resourceType) ? VertexTypeEnum.NODE_TYPE : VertexTypeEnum.TOPOLOGY_TEMPLATE;
1991         String normalizedName = ValidationUtils.normaliseComponentName(name);
1992         Map<GraphPropertyEnum, Object> properties = new EnumMap<>(GraphPropertyEnum.class);
1993         properties.put(GraphPropertyEnum.NORMALIZED_NAME, normalizedName);
1994         properties.put(GraphPropertyEnum.COMPONENT_TYPE, componentType.name());
1995         Either<List<GraphVertex>, JanusGraphOperationStatus> vertexEither = janusGraphDao
1996             .getByCriteria(vertexType, properties, JsonParseFlagEnum.NoParse);
1997         if (vertexEither.isRight() && vertexEither.right().value() != JanusGraphOperationStatus.NOT_FOUND) {
1998             log.debug("failed to get vertex from graph with property normalizedName: {}", normalizedName);
1999             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(vertexEither.right().value()));
2000         }
2001         return Either.left(CollectionUtils.isEmpty(vertexEither.isLeft() ? vertexEither.left().value() : null));
2002     }
2003
2004     private void fillNodeTypePropsMap(final Map<GraphPropertyEnum, Object> hasProps, final Map<GraphPropertyEnum, Object> hasNotProps,
2005                                       final String internalComponentType) {
2006         final Configuration configuration = ConfigurationManager.getConfigurationManager().getConfiguration();
2007         final List<String> allowedTypes;
2008         if (ComponentTypeEnum.SERVICE.getValue().equalsIgnoreCase(internalComponentType)) {
2009             allowedTypes = containerInstanceTypesData.getComponentAllowedList(ComponentTypeEnum.SERVICE, null);
2010         } else {
2011             final ResourceTypeEnum resourceType = ResourceTypeEnum.getTypeIgnoreCase(internalComponentType);
2012             allowedTypes = containerInstanceTypesData.getComponentAllowedList(ComponentTypeEnum.RESOURCE, resourceType);
2013         }
2014         final List<String> allResourceTypes = configuration.getResourceTypes();
2015         if (allowedTypes == null) {
2016             hasNotProps.put(GraphPropertyEnum.RESOURCE_TYPE, allResourceTypes);
2017             return;
2018         }
2019         if (ResourceTypeEnum.VL.getValue().equalsIgnoreCase(internalComponentType)) {
2020             hasProps.put(GraphPropertyEnum.RESOURCE_TYPE, allowedTypes);
2021         } else {
2022             final List<String> notAllowedTypes = allResourceTypes.stream().filter(s -> !allowedTypes.contains(s)).collect(Collectors.toList());
2023             hasNotProps.put(GraphPropertyEnum.RESOURCE_TYPE, notAllowedTypes);
2024         }
2025     }
2026
2027     private void fillTopologyTemplatePropsMap(Map<GraphPropertyEnum, Object> hasProps, Map<GraphPropertyEnum, Object> hasNotProps,
2028                                               ComponentTypeEnum componentTypeEnum) {
2029         switch (componentTypeEnum) {
2030             case RESOURCE:
2031                 hasProps.put(GraphPropertyEnum.COMPONENT_TYPE, ComponentTypeEnum.RESOURCE.name());
2032                 break;
2033             case SERVICE:
2034                 hasProps.put(GraphPropertyEnum.COMPONENT_TYPE, ComponentTypeEnum.SERVICE.name());
2035                 break;
2036             default:
2037                 break;
2038         }
2039         hasNotProps.put(GraphPropertyEnum.RESOURCE_TYPE, ResourceTypeEnum.CVFC.name());
2040     }
2041
2042     private void fillPropsMap(Map<GraphPropertyEnum, Object> hasProps, Map<GraphPropertyEnum, Object> hasNotProps, String internalComponentType,
2043                               ComponentTypeEnum componentTypeEnum, boolean isAbstract, VertexTypeEnum internalVertexType) {
2044         hasNotProps.put(GraphPropertyEnum.STATE, LifecycleStateEnum.NOT_CERTIFIED_CHECKOUT.name());
2045         hasNotProps.put(GraphPropertyEnum.IS_DELETED, true);
2046         hasNotProps.put(GraphPropertyEnum.IS_ARCHIVED, true);
2047         hasProps.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
2048         if (VertexTypeEnum.NODE_TYPE == internalVertexType) {
2049             hasProps.put(GraphPropertyEnum.IS_ABSTRACT, isAbstract);
2050             if (internalComponentType != null) {
2051                 fillNodeTypePropsMap(hasProps, hasNotProps, internalComponentType);
2052             }
2053         } else {
2054             fillTopologyTemplatePropsMap(hasProps, hasNotProps, componentTypeEnum);
2055         }
2056     }
2057
2058     private List<VertexTypeEnum> getInternalVertexTypes(ComponentTypeEnum componentTypeEnum, String internalComponentType) {
2059         List<VertexTypeEnum> internalVertexTypes = new ArrayList<>();
2060         if (ComponentTypeEnum.RESOURCE == componentTypeEnum) {
2061             internalVertexTypes.add(VertexTypeEnum.NODE_TYPE);
2062         }
2063         if (ComponentTypeEnum.SERVICE == componentTypeEnum || SERVICE.equalsIgnoreCase(internalComponentType)) {
2064             internalVertexTypes.add(VertexTypeEnum.TOPOLOGY_TEMPLATE);
2065         }
2066         return internalVertexTypes;
2067     }
2068
2069     public Either<List<Component>, StorageOperationStatus> getLatestVersionNotAbstractMetadataOnly(boolean isAbstract,
2070                                                                                                    ComponentTypeEnum componentTypeEnum,
2071                                                                                                    String internalComponentType) {
2072         List<VertexTypeEnum> internalVertexTypes = getInternalVertexTypes(componentTypeEnum, internalComponentType);
2073         List<Component> result = new ArrayList<>();
2074         for (VertexTypeEnum vertexType : internalVertexTypes) {
2075             Either<List<Component>, StorageOperationStatus> listByVertexType = getLatestVersionNotAbstractToscaElementsMetadataOnly(isAbstract,
2076                 componentTypeEnum, internalComponentType, vertexType);
2077             if (listByVertexType.isRight()) {
2078                 return listByVertexType;
2079             }
2080             result.addAll(listByVertexType.left().value());
2081         }
2082         return Either.left(result);
2083     }
2084
2085     private Either<List<Component>, StorageOperationStatus> getLatestComponentListByUuid(String componentUuid,
2086                                                                                          Map<GraphPropertyEnum, Object> additionalPropertiesToMatch) {
2087         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
2088         if (additionalPropertiesToMatch != null) {
2089             propertiesToMatch.putAll(additionalPropertiesToMatch);
2090         }
2091         propertiesToMatch.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
2092         return getComponentListByUuid(componentUuid, propertiesToMatch);
2093     }
2094
2095     public Either<Component, StorageOperationStatus> getComponentByUuidAndVersion(String componentUuid, String version) {
2096         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
2097         propertiesToMatch.put(GraphPropertyEnum.UUID, componentUuid);
2098         propertiesToMatch.put(GraphPropertyEnum.VERSION, version);
2099         Map<GraphPropertyEnum, Object> propertiesNotToMatch = new EnumMap<>(GraphPropertyEnum.class);
2100         propertiesNotToMatch.put(GraphPropertyEnum.IS_DELETED, true);
2101         Either<List<GraphVertex>, JanusGraphOperationStatus> vertexEither = janusGraphDao
2102             .getByCriteria(null, propertiesToMatch, propertiesNotToMatch, JsonParseFlagEnum.ParseAll);
2103         if (vertexEither.isRight()) {
2104             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(vertexEither.right().value()));
2105         }
2106         List<GraphVertex> vertexList = vertexEither.isLeft() ? vertexEither.left().value() : null;
2107         if (vertexList == null || vertexList.isEmpty() || vertexList.size() > 1) {
2108             return Either.right(StorageOperationStatus.NOT_FOUND);
2109         }
2110         return getToscaElementByOperation(vertexList.get(0));
2111     }
2112
2113     public Either<List<Component>, StorageOperationStatus> getComponentListByUuid(String componentUuid,
2114                                                                                   Map<GraphPropertyEnum, Object> additionalPropertiesToMatch) {
2115         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
2116         if (additionalPropertiesToMatch != null) {
2117             propertiesToMatch.putAll(additionalPropertiesToMatch);
2118         }
2119         propertiesToMatch.put(GraphPropertyEnum.UUID, componentUuid);
2120         Map<GraphPropertyEnum, Object> propertiesNotToMatch = new EnumMap<>(GraphPropertyEnum.class);
2121         propertiesNotToMatch.put(GraphPropertyEnum.IS_DELETED, true);
2122         propertiesNotToMatch.put(GraphPropertyEnum.IS_ARCHIVED, true); //US382674, US382683
2123         Either<List<GraphVertex>, JanusGraphOperationStatus> vertexEither = janusGraphDao
2124             .getByCriteria(null, propertiesToMatch, propertiesNotToMatch, JsonParseFlagEnum.ParseAll);
2125         if (vertexEither.isRight()) {
2126             log.debug("Couldn't fetch metadata for component with uuid {}, error: {}", componentUuid, vertexEither.right().value());
2127             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(vertexEither.right().value()));
2128         }
2129         List<GraphVertex> vertexList = vertexEither.isLeft() ? vertexEither.left().value() : null;
2130         if (vertexList == null || vertexList.isEmpty()) {
2131             log.debug("Component with uuid {} was not found", componentUuid);
2132             return Either.right(StorageOperationStatus.NOT_FOUND);
2133         }
2134         ArrayList<Component> latestComponents = new ArrayList<>();
2135         for (GraphVertex vertex : vertexList) {
2136             Either<Component, StorageOperationStatus> toscaElementByOperation = getToscaElementByOperation(vertex);
2137             if (toscaElementByOperation.isRight()) {
2138                 log.debug("Could not fetch the following Component by UUID {}", vertex.getUniqueId());
2139                 return Either.right(toscaElementByOperation.right().value());
2140             }
2141             latestComponents.add(toscaElementByOperation.left().value());
2142         }
2143         if (latestComponents.size() > 1) {
2144             for (Component component : latestComponents) {
2145                 if (Boolean.TRUE.equals(component.isHighestVersion())) {
2146                     LinkedList<Component> highestComponent = new LinkedList<>();
2147                     highestComponent.add(component);
2148                     return Either.left(highestComponent);
2149                 }
2150             }
2151         }
2152         return Either.left(latestComponents);
2153     }
2154
2155     public Either<Component, StorageOperationStatus> getLatestServiceByUuid(String serviceUuid) {
2156         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
2157         propertiesToMatch.put(GraphPropertyEnum.COMPONENT_TYPE, ComponentTypeEnum.SERVICE.name());
2158         return getLatestComponentByUuid(serviceUuid, propertiesToMatch);
2159     }
2160
2161     public Either<Component, StorageOperationStatus> getLatestComponentByUuid(String componentUuid) {
2162         return getLatestComponentByUuid(componentUuid, null);
2163     }
2164
2165     public Either<Component, StorageOperationStatus> getLatestComponentByUuid(String componentUuid,
2166                                                                               Map<GraphPropertyEnum, Object> propertiesToMatch) {
2167         Either<List<Component>, StorageOperationStatus> latestVersionListEither = getLatestComponentListByUuid(componentUuid, propertiesToMatch);
2168         if (latestVersionListEither.isRight()) {
2169             return Either.right(latestVersionListEither.right().value());
2170         }
2171         List<Component> latestVersionList = latestVersionListEither.left().value();
2172         if (latestVersionList.isEmpty()) {
2173             return Either.right(StorageOperationStatus.NOT_FOUND);
2174         }
2175         Component component = latestVersionList.size() == 1 ? latestVersionList.get(0)
2176             : latestVersionList.stream().max((c1, c2) -> Double.compare(Double.parseDouble(c1.getVersion()), Double.parseDouble(c2.getVersion())))
2177                 .get();
2178         return Either.left(component);
2179     }
2180
2181     public Either<List<Resource>, StorageOperationStatus> getAllCertifiedResources(boolean isAbstract, Boolean isHighest) {
2182         List<Resource> resources = new ArrayList<>();
2183         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
2184         Map<GraphPropertyEnum, Object> propertiesNotToMatch = new EnumMap<>(GraphPropertyEnum.class);
2185         propertiesToMatch.put(GraphPropertyEnum.IS_ABSTRACT, isAbstract);
2186         if (isHighest != null) {
2187             propertiesToMatch.put(GraphPropertyEnum.IS_HIGHEST_VERSION, isHighest);
2188         }
2189         propertiesToMatch.put(GraphPropertyEnum.STATE, LifecycleStateEnum.CERTIFIED.name());
2190         propertiesToMatch.put(GraphPropertyEnum.COMPONENT_TYPE, ComponentTypeEnum.RESOURCE.name());
2191         propertiesNotToMatch.put(GraphPropertyEnum.IS_DELETED, true);
2192         Either<List<GraphVertex>, JanusGraphOperationStatus> getResourcesRes = janusGraphDao
2193             .getByCriteria(null, propertiesToMatch, propertiesNotToMatch, JsonParseFlagEnum.ParseAll);
2194         if (getResourcesRes.isRight()) {
2195             log.debug("Failed to fetch all certified resources. Status is {}", getResourcesRes.right().value());
2196             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getResourcesRes.right().value()));
2197         }
2198         List<GraphVertex> resourceVerticies = getResourcesRes.left().value();
2199         for (GraphVertex resourceV : resourceVerticies) {
2200             Either<Resource, StorageOperationStatus> getResourceRes = getToscaElement(resourceV);
2201             if (getResourceRes.isRight()) {
2202                 return Either.right(getResourceRes.right().value());
2203             }
2204             resources.add(getResourceRes.left().value());
2205         }
2206         return Either.left(resources);
2207     }
2208
2209     public <T extends Component> Either<T, StorageOperationStatus> getLatestByNameAndVersion(String name, String version,
2210                                                                                              JsonParseFlagEnum parseFlag) {
2211         Either<T, StorageOperationStatus> result;
2212         Map<GraphPropertyEnum, Object> hasProperties = new EnumMap<>(GraphPropertyEnum.class);
2213         Map<GraphPropertyEnum, Object> hasNotProperties = new EnumMap<>(GraphPropertyEnum.class);
2214         hasProperties.put(GraphPropertyEnum.NAME, name);
2215         hasProperties.put(GraphPropertyEnum.VERSION, version);
2216         hasProperties.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
2217         hasNotProperties.put(GraphPropertyEnum.IS_DELETED, true);
2218         Either<List<GraphVertex>, JanusGraphOperationStatus> getResourceRes = janusGraphDao
2219             .getByCriteria(null, hasProperties, hasNotProperties, parseFlag);
2220         if (getResourceRes.isRight()) {
2221             JanusGraphOperationStatus status = getResourceRes.right().value();
2222             log.debug("failed to find resource with name {}, version {}. Status is {} ", name, version, status);
2223             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
2224             return result;
2225         }
2226         return getToscaElementByOperation(getResourceRes.left().value().get(0));
2227     }
2228
2229     public Either<Resource, StorageOperationStatus> getLatestComponentByCsarOrName(ComponentTypeEnum componentType, String csarUUID,
2230                                                                                    String systemName) {
2231         return getLatestComponentByCsarOrName(componentType, csarUUID, systemName, JsonParseFlagEnum.ParseAll);
2232     }
2233
2234     public Either<Resource, StorageOperationStatus> getLatestComponentByCsarOrName(ComponentTypeEnum componentType, String csarUUID,
2235                                                                                    String systemName, JsonParseFlagEnum parseFlag) {
2236         Map<GraphPropertyEnum, Object> props = new EnumMap<>(GraphPropertyEnum.class);
2237         Map<GraphPropertyEnum, Object> propsHasNot = new EnumMap<>(GraphPropertyEnum.class);
2238         props.put(GraphPropertyEnum.CSAR_UUID, csarUUID);
2239         props.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
2240         if (componentType != null) {
2241             props.put(GraphPropertyEnum.COMPONENT_TYPE, componentType.name());
2242         }
2243         propsHasNot.put(GraphPropertyEnum.IS_DELETED, true);
2244         GraphVertex resourceMetadataData = null;
2245         List<GraphVertex> resourceMetadataDataList = null;
2246         Either<List<GraphVertex>, JanusGraphOperationStatus> byCsar = janusGraphDao
2247             .getByCriteria(null, props, propsHasNot, JsonParseFlagEnum.ParseMetadata);
2248         if (byCsar.isRight()) {
2249             if (JanusGraphOperationStatus.NOT_FOUND == byCsar.right().value()) {
2250                 // Fix Defect DE256036
2251                 if (StringUtils.isEmpty(systemName)) {
2252                     return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(JanusGraphOperationStatus.NOT_FOUND));
2253                 }
2254                 props.clear();
2255                 props.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
2256                 props.put(GraphPropertyEnum.SYSTEM_NAME, systemName);
2257                 Either<List<GraphVertex>, JanusGraphOperationStatus> bySystemname = janusGraphDao
2258                     .getByCriteria(null, props, JsonParseFlagEnum.ParseMetadata);
2259                 if (bySystemname.isRight()) {
2260                     log.debug("getLatestResourceByCsarOrName - Failed to find by system name {}  error {} ", systemName,
2261                         bySystemname.right().value());
2262                     return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(bySystemname.right().value()));
2263                 }
2264                 if (bySystemname.left().value().size() > 2) {
2265                     log.debug(
2266                         "getLatestResourceByCsarOrName - getByCriteria(by system name) must return only 2 latest version, but was returned - {}",
2267                         bySystemname.left().value().size());
2268                     return Either.right(StorageOperationStatus.GENERAL_ERROR);
2269                 }
2270                 resourceMetadataDataList = bySystemname.left().value();
2271                 if (resourceMetadataDataList.size() == 1) {
2272                     resourceMetadataData = resourceMetadataDataList.get(0);
2273                 } else {
2274                     for (GraphVertex curResource : resourceMetadataDataList) {
2275                         if (!((String) curResource.getJsonMetadataField(JsonPresentationFields.LIFECYCLE_STATE)).equals("CERTIFIED")) {
2276                             resourceMetadataData = curResource;
2277                             break;
2278                         }
2279                     }
2280                 }
2281                 if (resourceMetadataData == null) {
2282                     log.debug("getLatestResourceByCsarOrName - getByCriteria(by system name) returned 2 latest CERTIFIED versions");
2283                     return Either.right(StorageOperationStatus.GENERAL_ERROR);
2284                 }
2285                 if (resourceMetadataData.getJsonMetadataField(JsonPresentationFields.CSAR_UUID) != null && !((String) resourceMetadataData
2286                     .getJsonMetadataField(JsonPresentationFields.CSAR_UUID)).equals(csarUUID)) {
2287                     log.debug("getLatestResourceByCsarOrName - same system name {} but different csarUUID. exist {} and new {} ", systemName,
2288                         resourceMetadataData.getJsonMetadataField(JsonPresentationFields.CSAR_UUID), csarUUID);
2289                     // correct error will be returned from create flow. with all
2290
2291                     // correct audit records!!!!!
2292                     return Either.right(StorageOperationStatus.NOT_FOUND);
2293                 }
2294                 return getToscaElement(resourceMetadataData.getUniqueId());
2295             }
2296         } else {
2297             resourceMetadataDataList = byCsar.left().value();
2298             if (resourceMetadataDataList.size() > 2) {
2299                 log.debug("getLatestResourceByCsarOrName - getByCriteria(by csar) must return only 2 latest version, but was returned - {}",
2300                     byCsar.left().value().size());
2301                 return Either.right(StorageOperationStatus.GENERAL_ERROR);
2302             }
2303             if (resourceMetadataDataList.size() == 1) {
2304                 resourceMetadataData = resourceMetadataDataList.get(0);
2305             } else {
2306                 for (GraphVertex curResource : resourceMetadataDataList) {
2307                     if (!((String) curResource.getJsonMetadataField(JsonPresentationFields.LIFECYCLE_STATE)).equals("CERTIFIED")) {
2308                         resourceMetadataData = curResource;
2309                         break;
2310                     }
2311                 }
2312             }
2313             if (resourceMetadataData == null) {
2314                 log.debug("getLatestResourceByCsarOrName - getByCriteria(by csar) returned 2 latest CERTIFIED versions");
2315                 return Either.right(StorageOperationStatus.GENERAL_ERROR);
2316             }
2317             return getToscaElement((String) resourceMetadataData.getJsonMetadataField(JsonPresentationFields.UNIQUE_ID), parseFlag);
2318         }
2319         return null;
2320     }
2321
2322     public Either<Boolean, StorageOperationStatus> validateToscaResourceNameExtends(String templateNameCurrent, String templateNameExtends) {
2323         String currentTemplateNameChecked = templateNameExtends;
2324         while (currentTemplateNameChecked != null && !currentTemplateNameChecked.equalsIgnoreCase(templateNameCurrent)) {
2325             Either<Resource, StorageOperationStatus> latestByToscaResourceName = getLatestByToscaResourceName(currentTemplateNameChecked);
2326             if (latestByToscaResourceName.isRight()) {
2327                 return latestByToscaResourceName.right().value() == StorageOperationStatus.NOT_FOUND ? Either.left(false)
2328                     : Either.right(latestByToscaResourceName.right().value());
2329             }
2330             Resource value = latestByToscaResourceName.left().value();
2331             if (value.getDerivedFrom() != null) {
2332                 currentTemplateNameChecked = value.getDerivedFrom().get(0);
2333             } else {
2334                 currentTemplateNameChecked = null;
2335             }
2336         }
2337         return (currentTemplateNameChecked != null && currentTemplateNameChecked.equalsIgnoreCase(templateNameCurrent)) ? Either.left(true)
2338             : Either.left(false);
2339     }
2340
2341     public Either<List<Component>, StorageOperationStatus> fetchMetaDataByResourceType(String resourceType, ComponentParametersView filterBy) {
2342         Map<GraphPropertyEnum, Object> props = new EnumMap<>(GraphPropertyEnum.class);
2343         props.put(GraphPropertyEnum.RESOURCE_TYPE, resourceType);
2344         props.put(GraphPropertyEnum.IS_HIGHEST_VERSION, true);
2345         Map<GraphPropertyEnum, Object> propsHasNotToMatch = new EnumMap<>(GraphPropertyEnum.class);
2346         propsHasNotToMatch.put(GraphPropertyEnum.IS_DELETED, true);
2347         Either<List<GraphVertex>, JanusGraphOperationStatus> resourcesByTypeEither = janusGraphDao
2348             .getByCriteria(null, props, propsHasNotToMatch, JsonParseFlagEnum.ParseMetadata);
2349         if (resourcesByTypeEither.isRight()) {
2350             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(resourcesByTypeEither.right().value()));
2351         }
2352         List<GraphVertex> vertexList = resourcesByTypeEither.left().value();
2353         List<Component> components = new ArrayList<>();
2354         for (GraphVertex vertex : vertexList) {
2355             components.add(getToscaElementByOperation(vertex, filterBy).left().value());
2356         }
2357         return Either.left(components);
2358     }
2359
2360     public void commit() {
2361         janusGraphDao.commit();
2362     }
2363
2364     public Either<Service, StorageOperationStatus> updateDistributionStatus(Service service, User user, DistributionStatusEnum distributionStatus) {
2365         Either<GraphVertex, StorageOperationStatus> updateDistributionStatus = topologyTemplateOperation
2366             .updateDistributionStatus(service.getUniqueId(), user, distributionStatus);
2367         if (updateDistributionStatus.isRight()) {
2368             return Either.right(updateDistributionStatus.right().value());
2369         }
2370         GraphVertex serviceV = updateDistributionStatus.left().value();
2371         service.setDistributionStatus(distributionStatus);
2372         service.setLastUpdateDate((Long) serviceV.getJsonMetadataField(JsonPresentationFields.LAST_UPDATE_DATE));
2373         return Either.left(service);
2374     }
2375
2376     public Either<ComponentMetadataData, StorageOperationStatus> updateComponentLastUpdateDateOnGraph(Component component) {
2377         Either<ComponentMetadataData, StorageOperationStatus> result = null;
2378         GraphVertex serviceVertex;
2379         Either<GraphVertex, JanusGraphOperationStatus> updateRes = null;
2380         Either<GraphVertex, JanusGraphOperationStatus> getRes = janusGraphDao.getVertexById(component.getUniqueId(), JsonParseFlagEnum.ParseMetadata);
2381         if (getRes.isRight()) {
2382             JanusGraphOperationStatus status = getRes.right().value();
2383             log.error("Failed to fetch component {}. status is {}", component.getUniqueId(), status);
2384             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
2385         }
2386         if (result == null) {
2387             serviceVertex = getRes.left().value();
2388             long lastUpdateDate = System.currentTimeMillis();
2389             serviceVertex.setJsonMetadataField(JsonPresentationFields.LAST_UPDATE_DATE, lastUpdateDate);
2390             component.setLastUpdateDate(lastUpdateDate);
2391             updateRes = janusGraphDao.updateVertex(serviceVertex);
2392             if (updateRes.isRight()) {
2393                 result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(updateRes.right().value()));
2394             }
2395         }
2396         if (result == null) {
2397             result = Either.left(ModelConverter.convertToComponentMetadata(updateRes.left().value()));
2398         }
2399         return result;
2400     }
2401
2402     public HealingJanusGraphDao getJanusGraphDao() {
2403         return janusGraphDao;
2404     }
2405
2406     public Either<List<Service>, StorageOperationStatus> getCertifiedServicesWithDistStatus(Set<DistributionStatusEnum> distStatus) {
2407         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
2408         propertiesToMatch.put(GraphPropertyEnum.STATE, LifecycleStateEnum.CERTIFIED.name());
2409         return getServicesWithDistStatus(distStatus, propertiesToMatch);
2410     }
2411
2412     public Either<List<Service>, StorageOperationStatus> getServicesWithDistStatus(Set<DistributionStatusEnum> distStatus,
2413                                                                                    Map<GraphPropertyEnum, Object> additionalPropertiesToMatch) {
2414         List<Service> servicesAll = new ArrayList<>();
2415         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
2416         Map<GraphPropertyEnum, Object> propertiesNotToMatch = new EnumMap<>(GraphPropertyEnum.class);
2417         if (additionalPropertiesToMatch != null && !additionalPropertiesToMatch.isEmpty()) {
2418             propertiesToMatch.putAll(additionalPropertiesToMatch);
2419         }
2420         propertiesToMatch.put(GraphPropertyEnum.COMPONENT_TYPE, ComponentTypeEnum.SERVICE.name());
2421         propertiesNotToMatch.put(GraphPropertyEnum.IS_DELETED, true);
2422         if (distStatus != null && !distStatus.isEmpty()) {
2423             for (DistributionStatusEnum state : distStatus) {
2424                 propertiesToMatch.put(GraphPropertyEnum.DISTRIBUTION_STATUS, state.name());
2425                 Either<List<Service>, StorageOperationStatus> fetchServicesByCriteria = fetchServicesByCriteria(servicesAll, propertiesToMatch,
2426                     propertiesNotToMatch);
2427                 if (fetchServicesByCriteria.isRight()) {
2428                     return fetchServicesByCriteria;
2429                 } else {
2430                     servicesAll = fetchServicesByCriteria.left().value();
2431                 }
2432             }
2433             return Either.left(servicesAll);
2434         } else {
2435             return fetchServicesByCriteria(servicesAll, propertiesToMatch, propertiesNotToMatch);
2436         }
2437     }
2438
2439     private Either<List<Service>, StorageOperationStatus> fetchServicesByCriteria(List<Service> servicesAll,
2440                                                                                   Map<GraphPropertyEnum, Object> propertiesToMatch,
2441                                                                                   Map<GraphPropertyEnum, Object> propertiesNotToMatch) {
2442         Either<List<GraphVertex>, JanusGraphOperationStatus> getRes = janusGraphDao
2443             .getByCriteria(VertexTypeEnum.TOPOLOGY_TEMPLATE, propertiesToMatch, propertiesNotToMatch, JsonParseFlagEnum.ParseAll);
2444         if (getRes.isRight()) {
2445             if (getRes.right().value() != JanusGraphOperationStatus.NOT_FOUND) {
2446                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG,
2447                     "Failed to fetch certified services by match properties {} not match properties {} . Status is {}. ", propertiesToMatch,
2448                     propertiesNotToMatch, getRes.right().value());
2449                 return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getRes.right().value()));
2450             }
2451         } else {
2452             for (GraphVertex vertex : getRes.left().value()) {
2453                 Either<ToscaElement, StorageOperationStatus> getServiceRes = topologyTemplateOperation
2454                     .getLightComponent(vertex, ComponentTypeEnum.SERVICE, new ComponentParametersView(true));
2455                 if (getServiceRes.isRight()) {
2456                     CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to fetch certified service {}. Status is {}. ",
2457                         vertex.getJsonMetadataField(JsonPresentationFields.NAME), getServiceRes.right().value());
2458                     return Either.right(getServiceRes.right().value());
2459                 } else {
2460                     servicesAll.add(ModelConverter.convertFromToscaElement(getServiceRes.left().value()));
2461                 }
2462             }
2463         }
2464         return Either.left(servicesAll);
2465     }
2466
2467     public void rollback() {
2468         janusGraphDao.rollback();
2469     }
2470
2471     public StorageOperationStatus addDeploymentArtifactsToInstance(String componentId, ComponentInstance componentInstance,
2472                                                                    Map<String, ArtifactDefinition> finalDeploymentArtifacts) {
2473         Map<String, ArtifactDataDefinition> instDeplArtifacts = finalDeploymentArtifacts.entrySet().stream()
2474             .collect(Collectors.toMap(Map.Entry::getKey, e -> new ArtifactDataDefinition(e.getValue())));
2475         return nodeTemplateOperation.addDeploymentArtifactsToInstance(componentId, componentInstance.getUniqueId(), instDeplArtifacts);
2476     }
2477
2478     public StorageOperationStatus addInformationalArtifactsToInstance(String componentId, ComponentInstance componentInstance,
2479                                                                       Map<String, ArtifactDefinition> artifacts) {
2480         StorageOperationStatus status = StorageOperationStatus.OK;
2481         if (MapUtils.isNotEmpty(artifacts)) {
2482             Map<String, ArtifactDataDefinition> instDeplArtifacts = artifacts.entrySet().stream()
2483                 .collect(Collectors.toMap(Map.Entry::getKey, e -> new ArtifactDataDefinition(e.getValue())));
2484             status = nodeTemplateOperation.addInformationalArtifactsToInstance(componentId, componentInstance.getUniqueId(), instDeplArtifacts);
2485         }
2486         return status;
2487     }
2488
2489     public StorageOperationStatus generateCustomizationUUIDOnInstance(String componentId, String instanceId) {
2490         return nodeTemplateOperation.generateCustomizationUUIDOnInstance(componentId, instanceId);
2491     }
2492
2493     public StorageOperationStatus generateCustomizationUUIDOnInstanceGroup(String componentId, String instanceId, List<String> groupInstances) {
2494         return nodeTemplateOperation.generateCustomizationUUIDOnInstanceGroup(componentId, instanceId, groupInstances);
2495     }
2496
2497     public Either<PropertyDefinition, StorageOperationStatus> addPropertyToComponent(String propertyName, PropertyDefinition newPropertyDefinition,
2498                                                                                      Component component) {
2499         newPropertyDefinition.setName(propertyName);
2500         StorageOperationStatus status = getToscaElementOperation(component)
2501             .addToscaDataToToscaElement(component.getUniqueId(), EdgeLabelEnum.PROPERTIES, VertexTypeEnum.PROPERTIES, newPropertyDefinition,
2502                 JsonPresentationFields.NAME);
2503         if (status != StorageOperationStatus.OK) {
2504             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to add the property {} to the component {}. Status is {}. ", propertyName,
2505                 component.getName(), status);
2506             return Either.right(status);
2507         }
2508         ComponentParametersView filter = new ComponentParametersView(true);
2509         filter.setIgnoreProperties(false);
2510         filter.setIgnoreInputs(false);
2511         Either<Component, StorageOperationStatus> getUpdatedComponentRes = getToscaElement(component.getUniqueId(), filter);
2512         if (getUpdatedComponentRes.isRight()) {
2513             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to get updated component {}. Status is {}. ", component.getUniqueId(),
2514                 getUpdatedComponentRes.right().value());
2515             return Either.right(status);
2516         }
2517         PropertyDefinition newProperty = null;
2518         List<PropertyDefinition> properties = (getUpdatedComponentRes.left().value()).getProperties();
2519         if (CollectionUtils.isNotEmpty(properties)) {
2520             Optional<PropertyDefinition> propertyOptional = properties.stream().filter(propertyEntry -> propertyEntry.getName().equals(propertyName))
2521                 .findAny();
2522             if (propertyOptional.isPresent()) {
2523                 newProperty = propertyOptional.get();
2524             }
2525         }
2526         if (newProperty == null) {
2527             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to find recently added property {} on the component {}. Status is {}. ",
2528                 propertyName, component.getUniqueId(), StorageOperationStatus.NOT_FOUND);
2529             return Either.right(StorageOperationStatus.NOT_FOUND);
2530         }
2531         return Either.left(newProperty);
2532     }
2533
2534     public Either<InputDefinition, StorageOperationStatus> addInputToComponent(String inputName, InputDefinition newInputDefinition,
2535                                                                                Component component) {
2536         newInputDefinition.setName(inputName);
2537         StorageOperationStatus status = getToscaElementOperation(component)
2538             .addToscaDataToToscaElement(component.getUniqueId(), EdgeLabelEnum.INPUTS, VertexTypeEnum.INPUTS, newInputDefinition,
2539                 JsonPresentationFields.NAME);
2540         if (status != StorageOperationStatus.OK) {
2541             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to add the input {} to the component {}. Status is {}. ", inputName,
2542                 component.getName(), status);
2543             return Either.right(status);
2544         }
2545         ComponentParametersView filter = new ComponentParametersView(true);
2546         filter.setIgnoreProperties(false);
2547         filter.setIgnoreInputs(false);
2548         Either<Component, StorageOperationStatus> getUpdatedComponentRes = getToscaElement(component.getUniqueId(), filter);
2549         if (getUpdatedComponentRes.isRight()) {
2550             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to get updated component {}. Status is {}. ", component.getUniqueId(),
2551                 getUpdatedComponentRes.right().value());
2552             return Either.right(status);
2553         }
2554         InputDefinition newInput = null;
2555         List<InputDefinition> inputs = (getUpdatedComponentRes.left().value()).getInputs();
2556         if (CollectionUtils.isNotEmpty(inputs)) {
2557             Optional<InputDefinition> inputOptional = inputs.stream().filter(inputEntry -> inputEntry.getName().equals(inputName)).findAny();
2558             if (inputOptional.isPresent()) {
2559                 newInput = inputOptional.get();
2560             }
2561         }
2562         if (newInput == null) {
2563             CommonUtility
2564                 .addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to find recently added input {} " + "on the component {}. Status is {}. ", inputs,
2565                     component.getUniqueId(), StorageOperationStatus.NOT_FOUND);
2566             return Either.right(StorageOperationStatus.NOT_FOUND);
2567         }
2568         return Either.left(newInput);
2569     }
2570
2571     public StorageOperationStatus deletePropertyOfComponent(Component component, String propertyName) {
2572         return getToscaElementOperation(component)
2573             .deleteToscaDataElement(component.getUniqueId(), EdgeLabelEnum.PROPERTIES, VertexTypeEnum.PROPERTIES, propertyName,
2574                 JsonPresentationFields.NAME);
2575     }
2576
2577     public StorageOperationStatus deleteAttributeOfResource(Component component, String attributeName) {
2578         return getToscaElementOperation(component)
2579             .deleteToscaDataElement(component.getUniqueId(), EdgeLabelEnum.ATTRIBUTES, VertexTypeEnum.ATTRIBUTES, attributeName,
2580                 JsonPresentationFields.NAME);
2581     }
2582
2583     public StorageOperationStatus deleteInputOfResource(Component resource, String inputName) {
2584         return getToscaElementOperation(resource)
2585             .deleteToscaDataElement(resource.getUniqueId(), EdgeLabelEnum.INPUTS, VertexTypeEnum.INPUTS, inputName, JsonPresentationFields.NAME);
2586     }
2587
2588     public StorageOperationStatus deleteOutputOfResource(final Component resource, final String outputName) {
2589         return getToscaElementOperation(resource)
2590             .deleteToscaDataElement(resource.getUniqueId(), EdgeLabelEnum.OUTPUTS, VertexTypeEnum.OUTPUTS, outputName, JsonPresentationFields.NAME);
2591     }
2592
2593     /**
2594      * Deletes a data type from a component.
2595      *
2596      * @param component    the container which has the data type
2597      * @param dataTypeName the data type name to be deleted
2598      * @return Operation result.
2599      */
2600     public StorageOperationStatus deleteDataTypeOfComponent(Component component, String dataTypeName) {
2601         return getToscaElementOperation(component)
2602             .deleteToscaDataElement(component.getUniqueId(), EdgeLabelEnum.DATA_TYPES, VertexTypeEnum.DATA_TYPES, dataTypeName,
2603                 JsonPresentationFields.NAME);
2604     }
2605
2606     public Either<PropertyDefinition, StorageOperationStatus> updatePropertyOfComponent(Component component,
2607                                                                                         PropertyDefinition newPropertyDefinition) {
2608         Either<Component, StorageOperationStatus> getUpdatedComponentRes = null;
2609         Either<PropertyDefinition, StorageOperationStatus> result = null;
2610         StorageOperationStatus status = getToscaElementOperation(component)
2611             .updateToscaDataOfToscaElement(component.getUniqueId(), EdgeLabelEnum.PROPERTIES, VertexTypeEnum.PROPERTIES, newPropertyDefinition,
2612                 JsonPresentationFields.NAME);
2613         if (status != StorageOperationStatus.OK) {
2614             CommonUtility
2615                 .addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_ADD_THE_PROPERTY_TO_THE_RESOURCE_STATUS_IS, newPropertyDefinition.getName(),
2616                     component.getName(), status);
2617             result = Either.right(status);
2618         }
2619         if (result == null) {
2620             ComponentParametersView filter = new ComponentParametersView(true);
2621             filter.setIgnoreProperties(false);
2622             getUpdatedComponentRes = getToscaElement(component.getUniqueId(), filter);
2623             if (getUpdatedComponentRes.isRight()) {
2624                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_GET_UPDATED_RESOURCE_STATUS_IS, component.getUniqueId(),
2625                     getUpdatedComponentRes.right().value());
2626                 result = Either.right(status);
2627             }
2628         }
2629         if (result == null) {
2630             Optional<PropertyDefinition> newProperty = (getUpdatedComponentRes.left().value()).getProperties().stream()
2631                 .filter(p -> p.getName().equals(newPropertyDefinition.getName())).findAny();
2632             if (newProperty.isPresent()) {
2633                 result = Either.left(newProperty.get());
2634             } else {
2635                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_FIND_RECENTLY_ADDED_PROPERTY_ON_THE_RESOURCE_STATUS_IS,
2636                     newPropertyDefinition.getName(), component.getUniqueId(), StorageOperationStatus.NOT_FOUND);
2637                 result = Either.right(StorageOperationStatus.NOT_FOUND);
2638             }
2639         }
2640         return result;
2641     }
2642
2643     public Either<AttributeDefinition, StorageOperationStatus> updateAttributeOfComponent(Component component,
2644                                                                                           AttributeDefinition newPropertyDefinition) {
2645         Either<Component, StorageOperationStatus> getUpdatedComponentRes = null;
2646         Either<AttributeDefinition, StorageOperationStatus> result = null;
2647         StorageOperationStatus status = getToscaElementOperation(component)
2648             .updateToscaDataOfToscaElement(component.getUniqueId(), EdgeLabelEnum.ATTRIBUTES, VertexTypeEnum.ATTRIBUTES, newPropertyDefinition,
2649                 JsonPresentationFields.NAME);
2650         if (status != StorageOperationStatus.OK) {
2651             CommonUtility
2652                 .addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_ADD_THE_PROPERTY_TO_THE_RESOURCE_STATUS_IS, newPropertyDefinition.getName(),
2653                     component.getName(), status);
2654             result = Either.right(status);
2655         }
2656         if (result == null) {
2657             ComponentParametersView filter = new ComponentParametersView(true);
2658             filter.setIgnoreProperties(false);
2659             getUpdatedComponentRes = getToscaElement(component.getUniqueId(), filter);
2660             if (getUpdatedComponentRes.isRight()) {
2661                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_GET_UPDATED_RESOURCE_STATUS_IS, component.getUniqueId(),
2662                     getUpdatedComponentRes.right().value());
2663                 result = Either.right(status);
2664             }
2665         }
2666         if (result == null) {
2667             Optional<AttributeDefinition> newProperty = (getUpdatedComponentRes.left().value()).getAttributes().stream()
2668                 .filter(p -> p.getName().equals(newPropertyDefinition.getName())).findAny();
2669             if (newProperty.isPresent()) {
2670                 result = Either.left(newProperty.get());
2671             } else {
2672                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_FIND_RECENTLY_ADDED_PROPERTY_ON_THE_RESOURCE_STATUS_IS,
2673                     newPropertyDefinition.getName(), component.getUniqueId(), StorageOperationStatus.NOT_FOUND);
2674                 result = Either.right(StorageOperationStatus.NOT_FOUND);
2675             }
2676         }
2677         return result;
2678     }
2679
2680     public Either<AttributeDefinition, StorageOperationStatus> addAttributeOfResource(Component component, AttributeDefinition newAttributeDef) {
2681         Either<Component, StorageOperationStatus> getUpdatedComponentRes = null;
2682         Either<AttributeDefinition, StorageOperationStatus> result = null;
2683         if (newAttributeDef.getUniqueId() == null || newAttributeDef.getUniqueId().isEmpty()) {
2684             String attUniqueId = UniqueIdBuilder.buildAttributeUid(component.getUniqueId(), newAttributeDef.getName());
2685             newAttributeDef.setUniqueId(attUniqueId);
2686             newAttributeDef.setOwnerId(component.getUniqueId());
2687         }
2688         StorageOperationStatus status = getToscaElementOperation(component)
2689             .addToscaDataToToscaElement(component.getUniqueId(), EdgeLabelEnum.ATTRIBUTES, VertexTypeEnum.ATTRIBUTES, newAttributeDef,
2690                 JsonPresentationFields.NAME);
2691         if (status != StorageOperationStatus.OK) {
2692             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_ADD_THE_PROPERTY_TO_THE_RESOURCE_STATUS_IS, newAttributeDef.getName(),
2693                 component.getName(), status);
2694             result = Either.right(status);
2695         }
2696         if (result == null) {
2697             ComponentParametersView filter = new ComponentParametersView(true);
2698             filter.setIgnoreAttributes(false);
2699             getUpdatedComponentRes = getToscaElement(component.getUniqueId(), filter);
2700             if (getUpdatedComponentRes.isRight()) {
2701                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_GET_UPDATED_RESOURCE_STATUS_IS, component.getUniqueId(),
2702                     getUpdatedComponentRes.right().value());
2703                 result = Either.right(status);
2704             }
2705         }
2706         if (result == null) {
2707             Optional<AttributeDefinition> newAttribute = ((Resource) getUpdatedComponentRes.left().value()).getAttributes().stream()
2708                 .filter(p -> p.getName().equals(newAttributeDef.getName())).findAny();
2709             if (newAttribute.isPresent()) {
2710                 result = Either.left(newAttribute.get());
2711             } else {
2712                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_FIND_RECENTLY_ADDED_PROPERTY_ON_THE_RESOURCE_STATUS_IS,
2713                     newAttributeDef.getName(), component.getUniqueId(), StorageOperationStatus.NOT_FOUND);
2714                 result = Either.right(StorageOperationStatus.NOT_FOUND);
2715             }
2716         }
2717         return result;
2718     }
2719
2720     public Either<AttributeDefinition, StorageOperationStatus> updateAttributeOfResource(Component component, AttributeDefinition newAttributeDef) {
2721         Either<Component, StorageOperationStatus> getUpdatedComponentRes = null;
2722         Either<AttributeDefinition, StorageOperationStatus> result = null;
2723         StorageOperationStatus status = getToscaElementOperation(component)
2724             .updateToscaDataOfToscaElement(component.getUniqueId(), EdgeLabelEnum.ATTRIBUTES, VertexTypeEnum.ATTRIBUTES, newAttributeDef,
2725                 JsonPresentationFields.NAME);
2726         if (status != StorageOperationStatus.OK) {
2727             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_ADD_THE_PROPERTY_TO_THE_RESOURCE_STATUS_IS, newAttributeDef.getName(),
2728                 component.getName(), status);
2729             result = Either.right(status);
2730         }
2731         if (result == null) {
2732             ComponentParametersView filter = new ComponentParametersView(true);
2733             filter.setIgnoreAttributes(false);
2734             getUpdatedComponentRes = getToscaElement(component.getUniqueId(), filter);
2735             if (getUpdatedComponentRes.isRight()) {
2736                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_GET_UPDATED_RESOURCE_STATUS_IS, component.getUniqueId(),
2737                     getUpdatedComponentRes.right().value());
2738                 result = Either.right(status);
2739             }
2740         }
2741         if (result == null) {
2742             Optional<AttributeDefinition> newProperty = ((Resource) getUpdatedComponentRes.left().value()).getAttributes().stream()
2743                 .filter(p -> p.getName().equals(newAttributeDef.getName())).findAny();
2744             if (newProperty.isPresent()) {
2745                 result = Either.left(newProperty.get());
2746             } else {
2747                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_FIND_RECENTLY_ADDED_PROPERTY_ON_THE_RESOURCE_STATUS_IS,
2748                     newAttributeDef.getName(), component.getUniqueId(), StorageOperationStatus.NOT_FOUND);
2749                 result = Either.right(StorageOperationStatus.NOT_FOUND);
2750             }
2751         }
2752         return result;
2753     }
2754
2755     public Either<InputDefinition, StorageOperationStatus> updateInputOfComponent(Component component, InputDefinition newInputDefinition) {
2756         Either<Component, StorageOperationStatus> getUpdatedComponentRes = null;
2757         Either<InputDefinition, StorageOperationStatus> result = null;
2758         StorageOperationStatus status = getToscaElementOperation(component)
2759             .updateToscaDataOfToscaElement(component.getUniqueId(), EdgeLabelEnum.INPUTS, VertexTypeEnum.INPUTS, newInputDefinition,
2760                 JsonPresentationFields.NAME);
2761         if (status != StorageOperationStatus.OK) {
2762             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to update the input {} to the component {}. Status is {}. ",
2763                 newInputDefinition.getName(), component.getName(), status);
2764             result = Either.right(status);
2765         }
2766         if (result == null) {
2767             ComponentParametersView filter = new ComponentParametersView(true);
2768             filter.setIgnoreInputs(false);
2769             getUpdatedComponentRes = getToscaElement(component.getUniqueId(), filter);
2770             if (getUpdatedComponentRes.isRight()) {
2771                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, FAILED_TO_GET_UPDATED_RESOURCE_STATUS_IS, component.getUniqueId(),
2772                     getUpdatedComponentRes.right().value());
2773                 result = Either.right(status);
2774             }
2775         }
2776         if (result == null) {
2777             Optional<InputDefinition> updatedInput = getUpdatedComponentRes.left().value().getInputs().stream()
2778                 .filter(p -> p.getName().equals(newInputDefinition.getName())).findAny();
2779             if (updatedInput.isPresent()) {
2780                 result = Either.left(updatedInput.get());
2781             } else {
2782                 CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to find recently updated inputs {} on the resource {}. Status is {}. ",
2783                     newInputDefinition.getName(), component.getUniqueId(), StorageOperationStatus.NOT_FOUND);
2784                 result = Either.right(StorageOperationStatus.NOT_FOUND);
2785             }
2786         }
2787         return result;
2788     }
2789
2790     /**
2791      * method - ename the group instances after referenced container name renamed flow - VF rename -(triggers)-> Group rename
2792      *
2793      * @param containerComponent  - container such as service
2794      * @param componentInstance   - context component
2795      * @param componentInstanceId - id
2796      * @return - successfull/failed status
2797      **/
2798     public Either<StorageOperationStatus, StorageOperationStatus> cleanAndAddGroupInstancesToComponentInstance(Component containerComponent,
2799                                                                                                                ComponentInstance componentInstance,
2800                                                                                                                String componentInstanceId) {
2801         String uniqueId = componentInstance.getUniqueId();
2802         StorageOperationStatus status = nodeTemplateOperation
2803             .deleteToscaDataDeepElementsBlockOfToscaElement(containerComponent.getUniqueId(), EdgeLabelEnum.INST_GROUPS, VertexTypeEnum.INST_GROUPS,
2804                 uniqueId);
2805         if (status != StorageOperationStatus.OK && status != StorageOperationStatus.NOT_FOUND) {
2806             CommonUtility
2807                 .addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to delete group instances for container {}. error {] ", componentInstanceId, status);
2808             return Either.right(status);
2809         }
2810         if (componentInstance.getGroupInstances() != null) {
2811             status = addGroupInstancesToComponentInstance(containerComponent, componentInstance, componentInstance.getGroupInstances());
2812             if (status != StorageOperationStatus.OK && status != StorageOperationStatus.NOT_FOUND) {
2813                 CommonUtility
2814                     .addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to add group instances for container {}. error {] ", componentInstanceId,
2815                         status);
2816                 return Either.right(status);
2817             }
2818         }
2819         return Either.left(status);
2820     }
2821
2822     public StorageOperationStatus addGroupInstancesToComponentInstance(Component containerComponent, ComponentInstance componentInstance,
2823                                                                        List<GroupDefinition> groups,
2824                                                                        Map<String, List<ArtifactDefinition>> groupInstancesArtifacts) {
2825         return nodeTemplateOperation.addGroupInstancesToComponentInstance(containerComponent, componentInstance, groups, groupInstancesArtifacts);
2826     }
2827
2828     public Either<List<GroupDefinition>, StorageOperationStatus> updateGroupsOnComponent(Component component,
2829                                                                                          List<GroupDataDefinition> updatedGroups) {
2830         return groupsOperation.updateGroups(component, updatedGroups, PromoteVersionEnum.MINOR);
2831     }
2832
2833     public Either<List<GroupInstance>, StorageOperationStatus> updateGroupInstancesOnComponent(Component component, String instanceId,
2834                                                                                                List<GroupInstance> updatedGroupInstances) {
2835         return groupsOperation.updateGroupInstances(component, instanceId, updatedGroupInstances);
2836     }
2837
2838     public StorageOperationStatus addGroupInstancesToComponentInstance(Component containerComponent, ComponentInstance componentInstance,
2839                                                                        List<GroupInstance> groupInstances) {
2840         return nodeTemplateOperation.addGroupInstancesToComponentInstance(containerComponent, componentInstance, groupInstances);
2841     }
2842
2843     public StorageOperationStatus addDeploymentArtifactsToComponentInstance(Component containerComponent, ComponentInstance componentInstance,
2844                                                                             Map<String, ArtifactDefinition> deploymentArtifacts) {
2845         return nodeTemplateOperation.addDeploymentArtifactsToComponentInstance(containerComponent, componentInstance, deploymentArtifacts);
2846     }
2847
2848     public StorageOperationStatus updateComponentInstanceProperty(Component containerComponent, String componentInstanceId,
2849                                                                   ComponentInstanceProperty property) {
2850         return nodeTemplateOperation.updateComponentInstanceProperty(containerComponent, componentInstanceId, property);
2851     }
2852
2853     public StorageOperationStatus updateComponentInstanceProperties(Component containerComponent, String componentInstanceId,
2854                                                                     List<ComponentInstanceProperty> properties) {
2855         return nodeTemplateOperation.updateComponentInstanceProperties(containerComponent, componentInstanceId, properties);
2856     }
2857
2858     public StorageOperationStatus updateComponentInstanceAttributes(final Component containerComponent, final String componentInstanceId,
2859                                                                     final List<ComponentInstanceAttribute> attributes) {
2860         return nodeTemplateOperation.updateComponentInstanceAttributes(containerComponent, componentInstanceId, attributes);
2861     }
2862
2863     public StorageOperationStatus addComponentInstanceProperty(Component containerComponent, String componentInstanceId,
2864                                                                ComponentInstanceProperty property) {
2865         return nodeTemplateOperation.addComponentInstanceProperty(containerComponent, componentInstanceId, property);
2866     }
2867
2868     public StorageOperationStatus updateComponentInstanceAttribute(final Component containerComponent, final String componentInstanceId,
2869                                                                    final ComponentInstanceAttribute attribute) {
2870         return nodeTemplateOperation.updateComponentInstanceAttribute(containerComponent, componentInstanceId, attribute);
2871     }
2872
2873     public StorageOperationStatus addComponentInstanceAttribute(Component containerComponent, String componentInstanceId,
2874                                                                 ComponentInstanceAttribute attribute) {
2875         return nodeTemplateOperation.addComponentInstanceAttribute(containerComponent, componentInstanceId, attribute);
2876     }
2877
2878     public StorageOperationStatus updateComponentInstanceInput(Component containerComponent, String componentInstanceId,
2879                                                                ComponentInstanceInput property) {
2880         return nodeTemplateOperation.updateComponentInstanceInput(containerComponent, componentInstanceId, property);
2881     }
2882
2883     public StorageOperationStatus updateComponentInstanceOutput(Component containerComponent, String componentInstanceId,
2884                                                                 ComponentInstanceOutput property) {
2885         return nodeTemplateOperation.updateComponentInstanceOutput(containerComponent, componentInstanceId, property);
2886     }
2887
2888     public StorageOperationStatus updateComponentInstanceInputs(Component containerComponent, String componentInstanceId,
2889                                                                 List<ComponentInstanceInput> instanceInputs) {
2890         return nodeTemplateOperation.updateComponentInstanceInputs(containerComponent, componentInstanceId, instanceInputs);
2891     }
2892
2893     public StorageOperationStatus updateComponentInstanceOutputs(Component containerComponent, String componentInstanceId,
2894                                                                  List<ComponentInstanceOutput> instanceInputs) {
2895         return nodeTemplateOperation.updateComponentInstanceOutputs(containerComponent, componentInstanceId, instanceInputs);
2896     }
2897
2898     public StorageOperationStatus addComponentInstanceInput(Component containerComponent, String componentInstanceId,
2899                                                             ComponentInstanceInput property) {
2900         return nodeTemplateOperation.addComponentInstanceInput(containerComponent, componentInstanceId, property);
2901     }
2902
2903     public StorageOperationStatus addComponentInstanceOutput(Component containerComponent, String componentInstanceId,
2904                                                              ComponentInstanceOutput property) {
2905         return nodeTemplateOperation.addComponentInstanceOutput(containerComponent, componentInstanceId, property);
2906     }
2907
2908     public void setNodeTypeOperation(NodeTypeOperation nodeTypeOperation) {
2909         this.nodeTypeOperation = nodeTypeOperation;
2910     }
2911
2912     public void setTopologyTemplateOperation(TopologyTemplateOperation topologyTemplateOperation) {
2913         this.topologyTemplateOperation = topologyTemplateOperation;
2914     }
2915
2916     public StorageOperationStatus deleteComponentInstanceInputsFromTopologyTemplate(Component containerComponent,
2917                                                                                     List<InputDefinition> inputsToDelete) {
2918         return topologyTemplateOperation.deleteToscaDataElements(containerComponent.getUniqueId(), EdgeLabelEnum.INPUTS,
2919             inputsToDelete.stream().map(PropertyDataDefinition::getName).collect(Collectors.toList()));
2920     }
2921
2922     public StorageOperationStatus deleteComponentInstanceOutputsFromTopologyTemplate(final Component containerComponent,
2923                                                                                      final List<OutputDefinition> outputsToDelete) {
2924         return topologyTemplateOperation.deleteToscaDataElements(containerComponent.getUniqueId(), EdgeLabelEnum.OUTPUTS,
2925             outputsToDelete.stream().map(AttributeDataDefinition::getName).collect(Collectors.toList()));
2926     }
2927
2928     public StorageOperationStatus updateComponentInstanceCapabiltyProperty(Component containerComponent, String componentInstanceUniqueId,
2929                                                                            String capabilityPropertyKey, ComponentInstanceProperty property) {
2930         return nodeTemplateOperation
2931             .updateComponentInstanceCapabilityProperty(containerComponent, componentInstanceUniqueId, capabilityPropertyKey, property);
2932     }
2933
2934     public StorageOperationStatus updateComponentInstanceCapabilityProperties(Component containerComponent, String componentInstanceUniqueId) {
2935         return convertComponentInstanceProperties(containerComponent, componentInstanceUniqueId).map(instanceCapProps -> topologyTemplateOperation
2936             .updateComponentInstanceCapabilityProperties(containerComponent, componentInstanceUniqueId, instanceCapProps))
2937             .orElse(StorageOperationStatus.NOT_FOUND);
2938     }
2939
2940     public StorageOperationStatus updateComponentInstanceRequirement(String containerComponentId, String componentInstanceUniqueId,
2941                                                                      RequirementDataDefinition requirementDataDefinition) {
2942         return nodeTemplateOperation.updateComponentInstanceRequirement(containerComponentId, componentInstanceUniqueId, requirementDataDefinition);
2943     }
2944
2945     public StorageOperationStatus updateComponentInstanceInterfaces(Component containerComponent, String componentInstanceUniqueId) {
2946         MapInterfaceDataDefinition mapInterfaceDataDefinition = convertComponentInstanceInterfaces(containerComponent, componentInstanceUniqueId);
2947         return topologyTemplateOperation.updateComponentInstanceInterfaces(containerComponent, componentInstanceUniqueId, mapInterfaceDataDefinition);
2948     }
2949
2950     public StorageOperationStatus updateComponentCalculatedCapabilitiesProperties(Component containerComponent) {
2951         Map<String, MapCapabilityProperty> mapCapabiltyPropertyMap = convertComponentCapabilitiesProperties(containerComponent);
2952         return nodeTemplateOperation.overrideComponentCapabilitiesProperties(containerComponent, mapCapabiltyPropertyMap);
2953     }
2954
2955     public StorageOperationStatus deleteAllCalculatedCapabilitiesRequirements(String topologyTemplateId) {
2956         StorageOperationStatus status = topologyTemplateOperation
2957             .removeToscaData(topologyTemplateId, EdgeLabelEnum.CALCULATED_CAPABILITIES, VertexTypeEnum.CALCULATED_CAPABILITIES);
2958         if (status == StorageOperationStatus.OK) {
2959             status = topologyTemplateOperation
2960                 .removeToscaData(topologyTemplateId, EdgeLabelEnum.CALCULATED_REQUIREMENTS, VertexTypeEnum.CALCULATED_REQUIREMENTS);
2961         }
2962         if (status == StorageOperationStatus.OK) {
2963             status = topologyTemplateOperation
2964                 .removeToscaData(topologyTemplateId, EdgeLabelEnum.CALCULATED_CAP_PROPERTIES, VertexTypeEnum.CALCULATED_CAP_PROPERTIES);
2965         }
2966         return status;
2967     }
2968
2969     public Either<Component, StorageOperationStatus> shouldUpgradeToLatestDerived(Resource clonedResource) {
2970         String componentId = clonedResource.getUniqueId();
2971         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
2972         if (getVertexEither.isRight()) {
2973             log.debug(COULDNT_FETCH_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
2974             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
2975         }
2976         GraphVertex nodeTypeV = getVertexEither.left().value();
2977         ToscaElement toscaElementToUpdate = ModelConverter.convertToToscaElement(clonedResource);
2978         Either<ToscaElement, StorageOperationStatus> shouldUpdateDerivedVersion = nodeTypeOperation
2979             .shouldUpdateDerivedVersion(toscaElementToUpdate, nodeTypeV);
2980         if (shouldUpdateDerivedVersion.isRight() && StorageOperationStatus.OK != shouldUpdateDerivedVersion.right().value()) {
2981             log.debug("Failed to update derived version for node type {} derived {}, error: {}", componentId, clonedResource.getDerivedFrom().get(0),
2982                 shouldUpdateDerivedVersion.right().value());
2983             return Either.right(shouldUpdateDerivedVersion.right().value());
2984         }
2985         if (shouldUpdateDerivedVersion.isLeft()) {
2986             return Either.left(ModelConverter.convertFromToscaElement(shouldUpdateDerivedVersion.left().value()));
2987         }
2988         return Either.left(clonedResource);
2989     }
2990
2991     /**
2992      * Returns list of ComponentInstanceProperty belonging to component instance capability specified by name, type and ownerId
2993      */
2994     public Either<List<ComponentInstanceProperty>, StorageOperationStatus> getComponentInstanceCapabilityProperties(String componentId,
2995                                                                                                                     String instanceId,
2996                                                                                                                     String capabilityName,
2997                                                                                                                     String capabilityType,
2998                                                                                                                     String ownerId) {
2999         return topologyTemplateOperation.getComponentInstanceCapabilityProperties(componentId, instanceId, capabilityName, capabilityType, ownerId);
3000     }
3001
3002     private MapInterfaceDataDefinition convertComponentInstanceInterfaces(Component currComponent, String componentInstanceId) {
3003         MapInterfaceDataDefinition mapInterfaceDataDefinition = new MapInterfaceDataDefinition();
3004         List<ComponentInstanceInterface> componentInterface = currComponent.getComponentInstancesInterfaces().get(componentInstanceId);
3005         if (CollectionUtils.isNotEmpty(componentInterface)) {
3006             componentInterface.stream().forEach(interfaceDef -> mapInterfaceDataDefinition.put(interfaceDef.getUniqueId(), interfaceDef));
3007         }
3008         return mapInterfaceDataDefinition;
3009     }
3010
3011     private Map<String, MapCapabilityProperty> convertComponentCapabilitiesProperties(Component currComponent) {
3012         Map<String, MapCapabilityProperty> map = ModelConverter.extractCapabilityPropertiesFromGroups(currComponent.getGroups(), true);
3013         map.putAll(ModelConverter.extractCapabilityProperteisFromInstances(currComponent.getComponentInstances(), true));
3014         return map;
3015     }
3016
3017     private Optional<MapCapabilityProperty> convertComponentInstanceProperties(Component component, String instanceId) {
3018         return component.fetchInstanceById(instanceId)
3019             .map(ci -> ModelConverter.convertToMapOfMapCapabilityProperties(ci.getCapabilities(), instanceId, ci.getOriginType().isAtomicType()));
3020     }
3021
3022     public Either<PolicyDefinition, StorageOperationStatus> associatePolicyToComponent(String componentId, PolicyDefinition policyDefinition,
3023                                                                                        int counter) {
3024         Either<PolicyDefinition, StorageOperationStatus> result = null;
3025         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither;
3026         getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.ParseMetadata);
3027         if (getVertexEither.isRight()) {
3028             log.error(COULDNT_FETCH_A_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
3029             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
3030         } else {
3031             if (getVertexEither.left().value().getLabel() != VertexTypeEnum.TOPOLOGY_TEMPLATE) {
3032                 log.error("Policy association to component of Tosca type {} is not allowed. ", getVertexEither.left().value().getLabel());
3033                 result = Either.right(StorageOperationStatus.BAD_REQUEST);
3034             }
3035         }
3036         if (result == null) {
3037             StorageOperationStatus status = topologyTemplateOperation
3038                 .addPolicyToToscaElement(getVertexEither.left().value(), policyDefinition, counter);
3039             if (status != StorageOperationStatus.OK) {
3040                 return Either.right(status);
3041             }
3042         }
3043         if (result == null) {
3044             result = Either.left(policyDefinition);
3045         }
3046         return result;
3047     }
3048
3049     public StorageOperationStatus associatePoliciesToComponent(String componentId, List<PolicyDefinition> policies) {
3050         log.debug("#associatePoliciesToComponent - associating policies for component {}.", componentId);
3051         return janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.ParseMetadata)
3052             .either(containerVertex -> topologyTemplateOperation.addPoliciesToToscaElement(containerVertex, policies),
3053                 DaoStatusConverter::convertJanusGraphStatusToStorageStatus);
3054     }
3055
3056     public Either<PolicyDefinition, StorageOperationStatus> updatePolicyOfComponent(String componentId, PolicyDefinition policyDefinition,
3057                                                                                     PromoteVersionEnum promoteVersionEnum) {
3058         Either<PolicyDefinition, StorageOperationStatus> result = null;
3059         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither;
3060         getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
3061         if (getVertexEither.isRight()) {
3062             log.error(COULDNT_FETCH_A_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
3063             result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value()));
3064         }
3065         if (result == null) {
3066             policyDefinition.setVersion(GroupUtils.updateVersion(promoteVersionEnum, policyDefinition.getVersion()));
3067             StorageOperationStatus status = topologyTemplateOperation.updatePolicyOfToscaElement(getVertexEither.left().value(), policyDefinition);
3068             if (status != StorageOperationStatus.OK) {
3069                 return Either.right(status);
3070             }
3071         }
3072         if (result == null) {
3073             result = Either.left(policyDefinition);
3074         }
3075         return result;
3076     }
3077
3078     public StorageOperationStatus updatePoliciesOfComponent(String componentId, List<PolicyDefinition> policyDefinition) {
3079         log.debug("#updatePoliciesOfComponent - updating policies for component {}", componentId);
3080         return janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse).right()
3081             .map(DaoStatusConverter::convertJanusGraphStatusToStorageStatus)
3082             .either(containerVertex -> topologyTemplateOperation.updatePoliciesOfToscaElement(containerVertex, policyDefinition), err -> err);
3083     }
3084
3085     public StorageOperationStatus removePolicyFromComponent(String componentId, String policyId) {
3086         StorageOperationStatus status = null;
3087         Either<GraphVertex, JanusGraphOperationStatus> getVertexEither = janusGraphDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
3088         if (getVertexEither.isRight()) {
3089             log.error(COULDNT_FETCH_A_COMPONENT_WITH_AND_UNIQUE_ID_ERROR, componentId, getVertexEither.right().value());
3090             status = DaoStatusConverter.convertJanusGraphStatusToStorageStatus(getVertexEither.right().value());
3091         }
3092         if (status == null) {
3093             status = topologyTemplateOperation.removePolicyFromToscaElement(getVertexEither.left().value(), policyId);
3094         }
3095         return status;
3096     }
3097
3098     public boolean canAddGroups(String componentId) {
3099         GraphVertex vertex = janusGraphDao.getVertexById(componentId).left().on(this::onJanusGraphError);
3100         return topologyTemplateOperation.hasEdgeOfType(vertex, EdgeLabelEnum.GROUPS);
3101     }
3102
3103     GraphVertex onJanusGraphError(JanusGraphOperationStatus toe) {
3104         throw new StorageException(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(toe));
3105     }
3106
3107     public CatalogUpdateTimestamp updateCatalogTimes() {
3108         long now = System.currentTimeMillis();
3109         GraphVertex catalogRoot = janusGraphDao.getVertexByLabel(VertexTypeEnum.CATALOG_ROOT).left().on(this::onJanusGraphError);
3110         Long currentTime = (Long) catalogRoot.getMetadataProperty(GraphPropertyEnum.CURRENT_CATALOG_UPDATE_TIME);
3111         catalogRoot.addMetadataProperty(GraphPropertyEnum.PREV_CATALOG_UPDATE_TIME, currentTime);
3112         catalogRoot.addMetadataProperty(GraphPropertyEnum.CURRENT_CATALOG_UPDATE_TIME, now);
3113         janusGraphDao.updateVertex(catalogRoot).left().on(this::onJanusGraphError);
3114         return new CatalogUpdateTimestamp(currentTime, now);
3115     }
3116
3117     public CatalogUpdateTimestamp getCatalogTimes() {
3118         GraphVertex catalogRoot = janusGraphDao.getVertexByLabel(VertexTypeEnum.CATALOG_ROOT).left().on(this::onJanusGraphError);
3119         Long currentTime = (Long) catalogRoot.getMetadataProperty(GraphPropertyEnum.CURRENT_CATALOG_UPDATE_TIME);
3120         Long prevTime = (Long) catalogRoot.getMetadataProperty(GraphPropertyEnum.PREV_CATALOG_UPDATE_TIME);
3121         return new CatalogUpdateTimestamp(prevTime == null ? 0 : prevTime.longValue(), currentTime == null ? 0 : currentTime.longValue());
3122     }
3123
3124     public void updateNamesOfCalculatedCapabilitiesRequirements(String componentId) {
3125         topologyTemplateOperation.updateNamesOfCalculatedCapabilitiesRequirements(componentId, getTopologyTemplate(componentId));
3126     }
3127
3128     public void revertNamesOfCalculatedCapabilitiesRequirements(String componentId) {
3129         topologyTemplateOperation.revertNamesOfCalculatedCapabilitiesRequirements(componentId, getTopologyTemplate(componentId));
3130     }
3131
3132     private TopologyTemplate getTopologyTemplate(String componentId) {
3133         return (TopologyTemplate) topologyTemplateOperation.getToscaElement(componentId, getFilterComponentWithCapProperties()).left()
3134             .on(this::throwStorageException);
3135     }
3136
3137     private ComponentParametersView getFilterComponentWithCapProperties() {
3138         ComponentParametersView filter = new ComponentParametersView();
3139         filter.setIgnoreCapabiltyProperties(false);
3140         return filter;
3141     }
3142
3143     private ToscaElement throwStorageException(StorageOperationStatus status) {
3144         throw new StorageException(status);
3145     }
3146
3147     public Either<Boolean, StorageOperationStatus> isComponentInUse(String componentId) {
3148         final List<EdgeLabelEnum> forbiddenEdgeLabelEnums = Arrays
3149             .asList(EdgeLabelEnum.INSTANCE_OF, EdgeLabelEnum.PROXY_OF, EdgeLabelEnum.ALLOTTED_OF);
3150         Either<GraphVertex, JanusGraphOperationStatus> vertexById = janusGraphDao.getVertexById(componentId);
3151         if (vertexById.isLeft()) {
3152             for (EdgeLabelEnum edgeLabelEnum : forbiddenEdgeLabelEnums) {
3153                 Iterator<Edge> edgeItr = vertexById.left().value().getVertex().edges(Direction.IN, edgeLabelEnum.name());
3154                 if (edgeItr != null && edgeItr.hasNext()) {
3155                     return Either.left(true);
3156                 }
3157             }
3158         }
3159         return Either.left(false);
3160     }
3161
3162     public Either<List<Component>, StorageOperationStatus> getComponentListByInvariantUuid(String componentInvariantUuid,
3163                                                                                            Map<GraphPropertyEnum, Object> additionalPropertiesToMatch) {
3164         Map<GraphPropertyEnum, Object> propertiesToMatch = new EnumMap<>(GraphPropertyEnum.class);
3165         if (MapUtils.isNotEmpty(additionalPropertiesToMatch)) {
3166             propertiesToMatch.putAll(additionalPropertiesToMatch);
3167         }
3168         propertiesToMatch.put(GraphPropertyEnum.INVARIANT_UUID, componentInvariantUuid);
3169         Either<List<GraphVertex>, JanusGraphOperationStatus> vertexEither = janusGraphDao
3170             .getByCriteria(null, propertiesToMatch, JsonParseFlagEnum.ParseMetadata);
3171         if (vertexEither.isRight()) {
3172             log.debug("Couldn't fetch metadata for component with type {} and invariantUUId {}, error: {}", componentInvariantUuid,
3173                 vertexEither.right().value());
3174             return Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(vertexEither.right().value()));
3175         }
3176         List<GraphVertex> vertexList = vertexEither.isLeft() ? vertexEither.left().value() : null;
3177         if (vertexList == null || vertexList.isEmpty()) {
3178             log.debug("Component with invariantUUId {} was not found", componentInvariantUuid);
3179             return Either.right(StorageOperationStatus.NOT_FOUND);
3180         }
3181         ArrayList<Component> components = new ArrayList<>();
3182         for (GraphVertex vertex : vertexList) {
3183             Either<Component, StorageOperationStatus> toscaElementByOperation = getToscaElementByOperation(vertex);
3184             if (toscaElementByOperation.isRight()) {
3185                 log.debug("Could not fetch the following Component by Invariant UUID {}", vertex.getUniqueId());
3186                 return Either.right(toscaElementByOperation.right().value());
3187             }
3188             components.add(toscaElementByOperation.left().value());
3189         }
3190         return Either.left(components);
3191     }
3192
3193     public Either<List<Component>, StorageOperationStatus> getParentComponents(String componentId) {
3194         List<Component> parentComponents = new ArrayList<>();
3195         final List<EdgeLabelEnum> relationEdgeLabelEnums = Arrays.asList(EdgeLabelEnum.INSTANCE_OF, EdgeLabelEnum.PROXY_OF);
3196         Either<GraphVertex, JanusGraphOperationStatus> vertexById = janusGraphDao.getVertexById(componentId);
3197         if (vertexById.isLeft()) {
3198             for (EdgeLabelEnum edgeLabelEnum : relationEdgeLabelEnums) {
3199                 Either<GraphVertex, JanusGraphOperationStatus> parentVertexEither = janusGraphDao
3200                     .getParentVertex(vertexById.left().value(), edgeLabelEnum, JsonParseFlagEnum.ParseJson);
3201                 if (parentVertexEither.isLeft()) {
3202                     Either<Component, StorageOperationStatus> componentEither = getToscaElement(parentVertexEither.left().value().getUniqueId());
3203                     if (componentEither.isLeft()) {
3204                         parentComponents.add(componentEither.left().value());
3205                     }
3206                 }
3207             }
3208         }
3209         return Either.left(parentComponents);
3210     }
3211
3212     public void updateCapReqPropertiesOwnerId(String componentId) {
3213         topologyTemplateOperation.updateCapReqPropertiesOwnerId(componentId, getTopologyTemplate(componentId));
3214     }
3215
3216     public <T extends Component> Either<T, StorageOperationStatus> getLatestByServiceName(String serviceName) {
3217         return getLatestByName(GraphPropertyEnum.NAME, serviceName);
3218     }
3219 }