re base code
[sdc.git] / catalog-model / src / main / java / org / openecomp / sdc / be / model / jsontitan / operations / ArtifactsOperations.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * SDC
4  * ================================================================================
5  * Copyright (C) 2017 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  * 
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  * 
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  */
20
21 package org.openecomp.sdc.be.model.jsontitan.operations;
22
23 import fj.data.Either;
24 import org.apache.commons.collections.MapUtils;
25 import org.apache.commons.lang3.tuple.ImmutableTriple;
26 import org.apache.commons.lang3.tuple.Triple;
27 import org.apache.tinkerpop.gremlin.structure.Direction;
28 import org.openecomp.sdc.be.config.BeEcompErrorManager;
29 import org.openecomp.sdc.be.dao.jsongraph.GraphVertex;
30 import org.openecomp.sdc.be.dao.jsongraph.types.EdgeLabelEnum;
31 import org.openecomp.sdc.be.dao.jsongraph.types.JsonParseFlagEnum;
32 import org.openecomp.sdc.be.dao.jsongraph.types.VertexTypeEnum;
33 import org.openecomp.sdc.be.dao.titan.TitanOperationStatus;
34 import org.openecomp.sdc.be.datatypes.elements.ArtifactDataDefinition;
35 import org.openecomp.sdc.be.datatypes.elements.InterfaceDataDefinition;
36 import org.openecomp.sdc.be.datatypes.elements.MapArtifactDataDefinition;
37 import org.openecomp.sdc.be.datatypes.elements.OperationDataDefinition;
38 import org.openecomp.sdc.be.datatypes.enums.ComponentTypeEnum;
39 import org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields;
40 import org.openecomp.sdc.be.datatypes.enums.NodeTypeEnum;
41 import org.openecomp.sdc.be.datatypes.tosca.ToscaDataDefinition;
42 import org.openecomp.sdc.be.model.ArtifactDefinition;
43 import org.openecomp.sdc.be.model.HeatParameterDefinition;
44 import org.openecomp.sdc.be.model.InterfaceDefinition;
45 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
46 import org.openecomp.sdc.be.model.operations.impl.DaoStatusConverter;
47 import org.openecomp.sdc.be.model.operations.impl.UniqueIdBuilder;
48 import org.openecomp.sdc.common.api.ArtifactGroupTypeEnum;
49 import org.openecomp.sdc.common.api.ArtifactTypeEnum;
50 import org.openecomp.sdc.common.jsongraph.util.CommonUtility;
51 import org.openecomp.sdc.common.jsongraph.util.CommonUtility.LogLevelEnum;
52 import org.openecomp.sdc.common.log.wrappers.Logger;
53 import org.slf4j.MDC;
54
55 import java.util.*;
56 import java.util.Map.Entry;
57 import java.util.stream.Collectors;
58
59 @org.springframework.stereotype.Component("artifacts-operations")
60
61 public class ArtifactsOperations extends BaseOperation {
62     private static final String FAILED_TO_FETCH_FOR_TOSCA_ELEMENT_WITH_ID_ERROR = "failed to fetch {} for tosca element with id {}, error {}";
63         private static final Logger log = Logger.getLogger(ArtifactsOperations.class.getName());
64
65     public Either<ArtifactDefinition, StorageOperationStatus> addArifactToComponent(ArtifactDefinition artifactInfo, String parentId, NodeTypeEnum type, boolean failIfExist, String instanceId) {
66
67         String artifactId = artifactInfo.getUniqueId();
68         if (artifactId == null && artifactInfo.getEsId() != null) {
69             artifactId = artifactInfo.getEsId();
70         }
71         Either<ArtifactDataDefinition, StorageOperationStatus> status = updateArtifactOnGraph(parentId, artifactInfo, type, artifactId, instanceId, false, false);
72         if (status.isRight()) {
73
74             log.debug("Failed to update artifact {} of {} {}. status is {}", artifactInfo.getArtifactName(), type.getName(), parentId, status.right().value());
75             BeEcompErrorManager.getInstance().logBeFailedUpdateNodeError("Update Artifact", artifactInfo.getArtifactName(), String.valueOf(status.right().value()));
76             return Either.right(status.right().value());
77         } else {
78
79             ArtifactDataDefinition artifactData = status.left().value();
80
81             ArtifactDefinition artifactDefResult = convertArtifactDataToArtifactDefinition(artifactInfo, artifactData);
82             log.debug("The returned ArtifactDefintion is {}", artifactDefResult);
83             return Either.left(artifactDefResult);
84         }
85
86     }
87
88     public Either<ArtifactDefinition, StorageOperationStatus> updateArtifactOnResource(ArtifactDefinition artifactInfo, String id, String artifactId, NodeTypeEnum type, String instanceId) {
89
90         Either<ArtifactDataDefinition, StorageOperationStatus> status = updateArtifactOnGraph(id, artifactInfo, type, artifactId, instanceId, true, false);
91         if (status.isRight()) {
92
93             log.debug("Failed to update artifact {} of {} {}. status is {}", artifactInfo.getArtifactName(), type.getName(), id, status.right().value());
94             BeEcompErrorManager.getInstance().logBeFailedUpdateNodeError("Update Artifact", artifactInfo.getArtifactName(), String.valueOf(status.right().value()));
95             return Either.right(status.right().value());
96         } else {
97
98             ArtifactDataDefinition artifactData = status.left().value();
99
100             ArtifactDefinition artifactDefResult = convertArtifactDataToArtifactDefinition(artifactInfo, artifactData);
101             log.debug("The returned ArtifactDefintion is {}", artifactDefResult);
102             return Either.left(artifactDefResult);
103         }
104     }
105
106     public Either<Boolean, StorageOperationStatus> isCloneNeeded(String parentId, ArtifactDefinition artifactInfo, NodeTypeEnum type) {
107         ArtifactGroupTypeEnum groupType = artifactInfo.getArtifactGroupType();
108
109         Triple<EdgeLabelEnum, Boolean, VertexTypeEnum> triple = getEdgeLabelEnumFromArtifactGroupType(groupType, type);
110         EdgeLabelEnum edgeLabelEnum = triple.getLeft();
111         return super.isCloneNeeded(parentId, edgeLabelEnum);
112     }
113
114     public Either<ArtifactDefinition, StorageOperationStatus> getArtifactById(String parentId, String id) {
115         return getArtifactById(parentId, id, null, null);
116     }
117
118     public Either<ArtifactDefinition, StorageOperationStatus> getArtifactById(String parentId, String id, ComponentTypeEnum componentType, String containerId) {
119         Either<ArtifactDefinition, StorageOperationStatus> result = null;
120         ArtifactDataDefinition foundArtifact = null;
121         if (componentType != null && componentType == ComponentTypeEnum.RESOURCE_INSTANCE) {
122             foundArtifact = getInstanceArtifactByLabelAndId(parentId, id, containerId, EdgeLabelEnum.INST_DEPLOYMENT_ARTIFACTS);
123             if (foundArtifact == null) {
124                 foundArtifact = getInstanceArtifactByLabelAndId(parentId, id, containerId, EdgeLabelEnum.INSTANCE_ARTIFACTS);
125             }
126         }
127         if (foundArtifact == null) {
128             foundArtifact = getArtifactByLabelAndId(parentId, id, EdgeLabelEnum.DEPLOYMENT_ARTIFACTS);
129         }
130         if (foundArtifact == null) {
131             foundArtifact = getArtifactByLabelAndId(parentId, id, EdgeLabelEnum.TOSCA_ARTIFACTS);
132         }
133
134         if (foundArtifact == null) {
135             foundArtifact = getArtifactByLabelAndId(parentId, id, EdgeLabelEnum.ARTIFACTS);
136         }
137
138         if (foundArtifact == null) {
139             foundArtifact = getArtifactByLabelAndId(parentId, id, EdgeLabelEnum.SERVICE_API_ARTIFACTS);
140         }
141                 if (foundArtifact == null) {
142                         foundArtifact = findInterfaceArtifact(parentId, id);
143
144                 }
145
146         if (foundArtifact == null) {
147             result = Either.right(StorageOperationStatus.NOT_FOUND);
148             return result;
149         }
150
151         ArtifactDefinition artifactDefResult = convertArtifactDataToArtifactDefinition(null, foundArtifact);
152         return Either.left(artifactDefResult);
153
154     }
155         private ArtifactDataDefinition findInterfaceArtifact(String parentId, String id) {
156                 Either<Map<String, InterfaceDefinition>, TitanOperationStatus> dataFromGraph = getDataFromGraph(parentId, EdgeLabelEnum.INTERFACE_ARTIFACTS);
157                 if (dataFromGraph.isRight()){
158                         log.debug("failed to fetch interfaces {} for tosca element with id {}, error {}", id, parentId ,dataFromGraph.right().value());
159                         return null;
160                 }
161
162                 Map<String, InterfaceDefinition> interfaceDefinitionMap = dataFromGraph.left().value();
163                 if(interfaceDefinitionMap == null) {
164                         return null;
165                 }
166                 Collection<InterfaceDefinition> interfaces = interfaceDefinitionMap.values();
167                 if (interfaces == null){
168                         return null;
169                 }
170                 for (InterfaceDataDefinition interfaceDataDefinition : interfaces){
171                         Map<String, OperationDataDefinition> operationsMap = interfaceDataDefinition.getOperations();
172                         if (operationsMap == null) {
173                                 return null;
174                         }
175                         ArtifactDataDefinition implementationArtifact = getArtifactDataDefinition(id, operationsMap);
176                         if (implementationArtifact != null)
177                                 return implementationArtifact;
178                 }
179                 return null;
180         }
181
182         private ArtifactDataDefinition getArtifactDataDefinition(String id,
183                         Map<String, OperationDataDefinition> operationsMap) {
184                 for(OperationDataDefinition operationDataDefinition : operationsMap.values()){
185                         ArtifactDataDefinition implementationArtifact = operationDataDefinition.getImplementation();
186                         if(implementationArtifact != null){
187                                 String uniqueId = implementationArtifact.getUniqueId();
188                                 if (id.equals(uniqueId)) {
189                                         return  implementationArtifact;
190                                 }
191                         }
192                 }
193                 return null;
194         }
195
196
197     public Either<ArtifactDefinition, StorageOperationStatus> removeArifactFromResource(String id, String artifactId, NodeTypeEnum type, boolean deleteMandatoryArtifact) {
198         Either<ArtifactDefinition, StorageOperationStatus> status = removeArtifactOnGraph(id, artifactId, type, deleteMandatoryArtifact);
199
200         if (status.isRight()) {
201
202             log.debug("Failed to delete artifact {} of resource {}", artifactId, id);
203
204             BeEcompErrorManager.getInstance().logBeFailedDeleteNodeError("Delete Artifact", artifactId, String.valueOf(status.right().value()));
205             return Either.right(status.right().value());
206         } else {
207
208             return Either.left(status.left().value());
209         }
210     }
211
212     public Either<Map<String, ArtifactDefinition>, StorageOperationStatus> getArtifacts(String parentId, NodeTypeEnum parentType, ArtifactGroupTypeEnum groupType, String instanceId) {
213
214         Triple<EdgeLabelEnum, Boolean, VertexTypeEnum> triple = getEdgeLabelEnumFromArtifactGroupType(groupType, parentType);
215         EdgeLabelEnum edgeLabelEnum = triple.getLeft();
216
217         Either<Map<String, ArtifactDefinition>, TitanOperationStatus> foundArtifact = null;
218         Map<String, ArtifactDefinition> resMap = new HashMap<>();
219         foundArtifact = getArtifactByLabel(parentId, instanceId, edgeLabelEnum);
220         if (foundArtifact.isRight()) {
221             log.debug("Failed to find artifact in component {} with label {} ", parentId, edgeLabelEnum);
222             return Either.right(DaoStatusConverter.convertTitanStatusToStorageStatus(foundArtifact.right().value()));
223         }
224
225         resMap.putAll(foundArtifact.left().value());
226
227         return Either.left(resMap);
228     }
229
230     /**
231      * @param parentId   the id of the instance container
232      * @param instanceId the id of the instance of which to return its artifacts
233      * @return instance and instance deployment artifacts mapped by artifact label name
234      */
235     public Either<Map<String, ArtifactDefinition>, StorageOperationStatus> getAllInstanceArtifacts(String parentId, String instanceId) {
236         Map<String, ArtifactDataDefinition> resMap = new HashMap<>();
237         Either<Map<String, ArtifactDataDefinition>, TitanOperationStatus> instArtifacts = getInstanceArtifactsByLabel(parentId, instanceId, EdgeLabelEnum.INSTANCE_ARTIFACTS);
238         if (instArtifacts.isRight()) {
239             return Either.right(DaoStatusConverter.convertTitanStatusToStorageStatus(instArtifacts.right().value()));
240         }
241         Either<Map<String, ArtifactDataDefinition>, TitanOperationStatus> deployInstArtifacts = getInstanceArtifactsByLabel(parentId, instanceId, EdgeLabelEnum.INST_DEPLOYMENT_ARTIFACTS);
242         if (deployInstArtifacts.isRight()) {
243             return Either.right(DaoStatusConverter.convertTitanStatusToStorageStatus(deployInstArtifacts.right().value()));
244         }
245         resMap.putAll(instArtifacts.left().value());
246         resMap.putAll(deployInstArtifacts.left().value());
247         return Either.left(convertArtifactMapToArtifactDefinitionMap(resMap));
248     }
249
250     public Either<Map<String, ArtifactDefinition>, StorageOperationStatus> getArtifacts(String parentId) {
251
252         Either<Map<String, ArtifactDefinition>, TitanOperationStatus> foundArtifact = null;
253         Map<String, ArtifactDefinition> resMap = new HashMap<>();
254         foundArtifact = getArtifactByLabel(parentId, null, EdgeLabelEnum.ARTIFACTS);
255         if (foundArtifact.isLeft()) {
256             resMap.putAll(foundArtifact.left().value());
257
258         }
259         foundArtifact = getArtifactByLabel(parentId, null, EdgeLabelEnum.DEPLOYMENT_ARTIFACTS);
260         if (foundArtifact.isLeft()) {
261             resMap.putAll(foundArtifact.left().value());
262
263         }
264         foundArtifact = getArtifactByLabel(parentId, null, EdgeLabelEnum.TOSCA_ARTIFACTS);
265         if (foundArtifact.isLeft()) {
266             resMap.putAll(foundArtifact.left().value());
267
268         }
269
270         return Either.left(resMap);
271
272     }
273
274     public Either<ArtifactDefinition, StorageOperationStatus> removeArtifactOnGraph(String id, String artifactId, NodeTypeEnum type, boolean deleteMandatoryArtifact) {
275
276         Either<ArtifactDefinition, StorageOperationStatus> artifactData = this.getArtifactById(id, artifactId);
277         if (artifactData.isRight()) {
278             log.debug("Failed to find artifact in component {} with id {} ", id, artifactId);
279             return Either.right(artifactData.right().value());
280         }
281         ArtifactDataDefinition artifactDefinition = artifactData.left().value();
282         boolean isMandatory = false;
283         if ((artifactDefinition.getMandatory() || artifactDefinition.getServiceApi()) && !deleteMandatoryArtifact) {
284             // return Either.left(artifactData.left().value());
285             isMandatory = true;
286         }
287
288         Triple<EdgeLabelEnum, Boolean, VertexTypeEnum> triple = getEdgeLabelEnumFromArtifactGroupType(artifactDefinition.getArtifactGroupType(), type);
289         EdgeLabelEnum edgeLabelEnum = triple.getLeft();
290         VertexTypeEnum vertexTypeEnum = triple.getRight();
291
292         if (!isMandatory) {
293             StorageOperationStatus status = deleteToscaDataElement(id, edgeLabelEnum, vertexTypeEnum, artifactDefinition.getArtifactLabel(), JsonPresentationFields.ARTIFACT_LABEL);
294             if (status != StorageOperationStatus.OK)
295                 return Either.right(status);
296         }
297
298         return Either.left(artifactData.left().value());
299
300     }
301
302     public void updateUUID(ArtifactDataDefinition artifactData, String oldChecksum, String oldVesrion, boolean isUpdate, EdgeLabelEnum edgeLabel) {
303         if (oldVesrion == null || oldVesrion.isEmpty())
304             oldVesrion = "0";
305
306         String currentChecksum = artifactData.getArtifactChecksum();
307
308         if (isUpdate) {
309             ArtifactTypeEnum type = ArtifactTypeEnum.findType(artifactData.getArtifactType());
310             switch (type) {
311                 case HEAT_ENV:
312                     if (edgeLabel == EdgeLabelEnum.INST_DEPLOYMENT_ARTIFACTS) {
313                         generateUUID(artifactData, oldVesrion);
314                     } else {
315                         updateVersionAndDate(artifactData, oldVesrion);
316                     }
317                     break;
318                 case HEAT:
319                 case HEAT_NET:
320                 case HEAT_VOL:
321                     generateUUID(artifactData, oldVesrion);
322                     break;
323                 default:
324                     if (oldChecksum == null || oldChecksum.isEmpty()) {
325                         if (currentChecksum != null) {
326                             generateUUID(artifactData, oldVesrion);
327                         }
328                     } else if ((currentChecksum != null && !currentChecksum.isEmpty()) && !oldChecksum.equals(currentChecksum)) {
329                         generateUUID(artifactData, oldVesrion);
330                     }
331                     break;
332             }
333         } else {
334             if (oldChecksum == null || oldChecksum.isEmpty()) {
335                 if (currentChecksum != null) {
336                     generateUUID(artifactData, oldVesrion);
337                 }
338             } else if ((currentChecksum != null && !currentChecksum.isEmpty()) && !oldChecksum.equals(currentChecksum)) {
339                 generateUUID(artifactData, oldVesrion);
340             }
341         }
342     }
343
344     // @TODO add implementation
345
346     public Either<Map<String, ArtifactDefinition>, StorageOperationStatus> getArtifacts(String parentId, NodeTypeEnum parentType) {
347         return null;
348     }
349
350     public Either<ArtifactDefinition, StorageOperationStatus> addHeatEnvArtifact(ArtifactDefinition artifactHeatEnv, ArtifactDefinition artifactHeat, String componentId, NodeTypeEnum parentType, boolean failIfExist, String instanceId) {
351         artifactHeatEnv.setGeneratedFromId(artifactHeat.getUniqueId());
352         return addArifactToComponent(artifactHeatEnv, componentId, parentType, failIfExist, instanceId);
353     }
354
355     public Either<ArtifactDefinition, StorageOperationStatus> getHeatArtifactByHeatEnvId(String parentId, ArtifactDefinition heatEnv, NodeTypeEnum parentType, String containerId, ComponentTypeEnum componentType) {
356         String id = heatEnv.getGeneratedFromId();
357         ComponentTypeEnum compType;
358         switch (parentType) {
359             case ResourceInstance:
360                 compType = ComponentTypeEnum.RESOURCE_INSTANCE;
361                 break;
362             default:
363                 compType = componentType;
364         }
365         return getArtifactById(parentId, id, compType, containerId);
366     }
367
368     public Either<ArtifactDefinition, StorageOperationStatus> updateHeatEnvArtifact(String id, ArtifactDefinition artifactEnvInfo, String artifactId, String newArtifactId, NodeTypeEnum type, String instanceId) {
369
370         Either<Map<String, ArtifactDefinition>, TitanOperationStatus> artifactsEither = getArtifactByLabel(id, instanceId, EdgeLabelEnum.DEPLOYMENT_ARTIFACTS);
371         if (artifactsEither.isRight()) {
372             log.debug("Failed to find artifacts in component {} with id {} ", id, artifactsEither.right().value());
373             return Either.right(DaoStatusConverter.convertTitanStatusToStorageStatus(artifactsEither.right().value()));
374         }
375
376         Map<String, ArtifactDefinition> artifacts = artifactsEither.left().value();
377         List<ArtifactDefinition> envList = artifacts.values().stream().filter(a -> a.getGeneratedFromId() != null && a.getGeneratedFromId().equals(artifactId)).collect(Collectors.toList());
378         if (envList != null && !envList.isEmpty()) {
379             envList.forEach(a -> {
380                 a.setGeneratedFromId(newArtifactId);
381                 updateArtifactOnResource(a, id, a.getUniqueId(), type, instanceId);
382
383             });
384
385         }
386         return Either.left(artifactEnvInfo);
387     }
388
389     public Either<ArtifactDefinition, StorageOperationStatus> updateHeatEnvPlaceholder(ArtifactDefinition artifactInfo, String parentId, NodeTypeEnum type) {
390                 return updateArtifactOnResource(artifactInfo, parentId, artifactInfo.getUniqueId(), type, null);
391     }
392
393
394     ///////////////////////////////////////////// private methods ////////////////////////////////////////////////////
395
396     protected ArtifactDefinition convertArtifactDataToArtifactDefinition(ArtifactDefinition artifactInfo, ArtifactDataDefinition artifactDefResult) {
397         log.debug("The object returned after create property is {}", artifactDefResult);
398
399         ArtifactDefinition propertyDefResult = new ArtifactDefinition(artifactDefResult);
400         if (artifactInfo != null)
401             propertyDefResult.setPayload(artifactInfo.getPayloadData());
402
403         List<HeatParameterDefinition> parameters = new ArrayList<>();
404         /*
405          * StorageOperationStatus heatParametersOfNode = heatParametersOperation.getHeatParametersOfNode(NodeTypeEnum.ArtifactRef, artifactDefResult.getUniqueId().toString(), parameters); if ((heatParametersOfNode.equals(StorageOperationStatus.OK))
406          * && !parameters.isEmpty()) { propertyDefResult.setHeatParameters(parameters); }
407          */
408         return propertyDefResult;
409     }
410
411     private ArtifactDataDefinition getInstanceArtifactByLabelAndId(String parentId, String id, String containerId, EdgeLabelEnum edgeLabelEnum) {
412         ArtifactDataDefinition foundArtifact = null;
413         Either<Map<String, MapArtifactDataDefinition>, TitanOperationStatus> artifactsEither = getDataFromGraph(containerId, edgeLabelEnum);
414         if (artifactsEither.isRight()) {
415             log.debug(FAILED_TO_FETCH_FOR_TOSCA_ELEMENT_WITH_ID_ERROR, edgeLabelEnum, containerId, artifactsEither.right().value());
416             return null;
417         }
418
419         Map<String, MapArtifactDataDefinition> artifacts = artifactsEither.left().value();
420
421         MapArtifactDataDefinition artifactsPerInstance = artifacts.get(parentId);
422         if (artifactsPerInstance == null) {
423             log.debug("failed to fetch artifacts for instance {} in tosca element with id {}, error {}", parentId, containerId, artifactsEither.right().value());
424             return null;
425         }
426         Optional<ArtifactDataDefinition> op = artifactsPerInstance.getMapToscaDataDefinition().values().stream().filter(p -> p.getUniqueId().equals(id)).findAny();
427         if (op.isPresent()) {
428             foundArtifact = op.get();
429         }
430         return foundArtifact;
431     }
432
433     private ArtifactDataDefinition getArtifactByLabelAndId(String parentId, String id, EdgeLabelEnum edgeLabelEnum) {
434         ArtifactDataDefinition foundArtifact = null;
435         Either<Map<String, ArtifactDataDefinition>, TitanOperationStatus> artifactsEither = getDataFromGraph(parentId, edgeLabelEnum);
436         if (artifactsEither.isRight()) {
437             log.debug(FAILED_TO_FETCH_FOR_TOSCA_ELEMENT_WITH_ID_ERROR, edgeLabelEnum, parentId, artifactsEither.right().value());
438             return null;
439         }
440
441         Map<String, ArtifactDataDefinition> artifacts = artifactsEither.left().value();
442         Optional<ArtifactDataDefinition> op = artifacts.values().stream().filter(p -> p.getUniqueId().equals(id)).findAny();
443         if (op.isPresent()) {
444             foundArtifact = op.get();
445         }
446         return foundArtifact;
447     }
448
449     private Either<Map<String, ArtifactDefinition>, TitanOperationStatus> getArtifactByLabel(String parentId, String instanceId, EdgeLabelEnum edgeLabelEnum) {
450         Either<Map<String, ArtifactDataDefinition>, TitanOperationStatus> artifactsEither = getArtifactsDataByLabel(parentId, instanceId, edgeLabelEnum);
451         if (artifactsEither.isRight()) {
452             log.debug(FAILED_TO_FETCH_FOR_TOSCA_ELEMENT_WITH_ID_ERROR, edgeLabelEnum, parentId, artifactsEither.right().value());
453             return Either.right(artifactsEither.right().value());
454         }
455         Map<String, ArtifactDataDefinition> artifactDataMap = artifactsEither.left().value();
456         return Either.left(convertArtifactMapToArtifactDefinitionMap(artifactDataMap));
457     }
458
459     private Either<Map<String, ArtifactDataDefinition>, TitanOperationStatus> getArtifactsDataByLabel(String parentId, String instanceId, EdgeLabelEnum edgeLabelEnum) {
460         return edgeLabelEnum.isInstanceArtifactsLabel() ? getInstanceArtifactsByLabel(parentId, instanceId, edgeLabelEnum) : getDataFromGraph(parentId, edgeLabelEnum);
461     }
462
463     private Map<String, ArtifactDefinition> convertArtifactMapToArtifactDefinitionMap(Map<String, ArtifactDataDefinition> artifactDataMap) {
464         Map<String, ArtifactDefinition> artMap = new HashMap<>();
465         if (artifactDataMap != null && !artifactDataMap.isEmpty()) {
466             artMap = artifactDataMap.entrySet().stream().collect(Collectors.toMap(Entry::getKey, e -> convertArtifactDataToArtifactDefinition(null, e.getValue())));
467         }
468         return artMap;
469     }
470
471     private Either<Map<String, ArtifactDataDefinition>, TitanOperationStatus> getInstanceArtifactsByLabel(String parentId, String instanceId, EdgeLabelEnum edgeLabelEnum) {
472         Either<Map<String, MapArtifactDataDefinition>, TitanOperationStatus> resultEither = getDataFromGraph(parentId, edgeLabelEnum);
473         if (resultEither.isRight()) {
474             log.debug(FAILED_TO_FETCH_FOR_TOSCA_ELEMENT_WITH_ID_ERROR, edgeLabelEnum, parentId, resultEither.right().value());
475             return Either.right(resultEither.right().value());
476         }
477         Map<String, MapArtifactDataDefinition> mapArtifacts = resultEither.left().value();
478         MapArtifactDataDefinition artifactPerInstance = mapArtifacts.get(instanceId);
479         return artifactPerInstance != null ? Either.left(artifactPerInstance.getMapToscaDataDefinition()) : Either.left(new HashMap<>());
480     }
481
482     private Triple<EdgeLabelEnum, Boolean, VertexTypeEnum> getEdgeLabelEnumFromArtifactGroupType(ArtifactGroupTypeEnum groupType, NodeTypeEnum nodeType) {
483         EdgeLabelEnum edgeLabelEnum;
484         VertexTypeEnum vertexTypeEnum;
485         Boolean isDeepElement = false;
486         /*
487          * if (nodeType == NodeTypeEnum.ResourceInstance) { edgeLabelEnum = EdgeLabelEnum.INST_DEPLOYMENT_ARTIFACTS; vertexTypeEnum = VertexTypeEnum.INST_DEPLOYMENT_ARTIFACTS; isDeepElement = true; } else {
488          */
489         switch (groupType) {
490             case TOSCA:
491                 edgeLabelEnum = EdgeLabelEnum.TOSCA_ARTIFACTS;
492                 vertexTypeEnum = VertexTypeEnum.TOSCA_ARTIFACTS;
493                 break;
494             case DEPLOYMENT:
495                 if (nodeType == NodeTypeEnum.ResourceInstance) {
496                     edgeLabelEnum = EdgeLabelEnum.INST_DEPLOYMENT_ARTIFACTS;
497                     vertexTypeEnum = VertexTypeEnum.INST_DEPLOYMENT_ARTIFACTS;
498                     isDeepElement = true;
499                 } else {
500                     edgeLabelEnum = EdgeLabelEnum.DEPLOYMENT_ARTIFACTS;
501                     vertexTypeEnum = VertexTypeEnum.DEPLOYMENT_ARTIFACTS;
502                 }
503                 break;
504             case SERVICE_API:
505                 edgeLabelEnum = EdgeLabelEnum.SERVICE_API_ARTIFACTS;
506                 vertexTypeEnum = VertexTypeEnum.SERVICE_API_ARTIFACTS;
507                 break;
508             default:
509                 if (nodeType == NodeTypeEnum.ResourceInstance) {
510                     edgeLabelEnum = EdgeLabelEnum.INSTANCE_ARTIFACTS;
511                     vertexTypeEnum = VertexTypeEnum.INSTANCE_ARTIFACTS;
512                     isDeepElement = true;
513                 } else {
514                     edgeLabelEnum = EdgeLabelEnum.ARTIFACTS;
515                     vertexTypeEnum = VertexTypeEnum.ARTIFACTS;
516                 }
517                 break;
518         }
519         // }
520         return new ImmutableTriple<>(edgeLabelEnum, isDeepElement, vertexTypeEnum);
521
522     }
523
524     public Either<ArtifactDataDefinition, StorageOperationStatus> updateArtifactOnGraph(String componentId, ArtifactDefinition artifactInfo, NodeTypeEnum type, String artifactId, String instanceId, boolean isUpdate, boolean isDeletePlaceholder) {
525         Either<ArtifactDataDefinition, StorageOperationStatus> res = null;
526         ArtifactDataDefinition artifactToUpdate = new ArtifactDataDefinition(artifactInfo);
527         ArtifactGroupTypeEnum groupType = artifactInfo.getArtifactGroupType();
528
529         Triple<EdgeLabelEnum, Boolean, VertexTypeEnum> triple = getEdgeLabelEnumFromArtifactGroupType(groupType, type);
530         EdgeLabelEnum edgeLabelEnum = triple.getLeft();
531         VertexTypeEnum vertexTypeEnum = triple.getRight();
532
533         Either<Boolean, StorageOperationStatus> isNeedToCloneEither = isCloneNeeded(componentId, edgeLabelEnum);
534         if (isNeedToCloneEither.isRight()) {
535             log.debug("Failed check is clone needed {}", componentId);
536             return Either.right(isNeedToCloneEither.right().value());
537
538         }
539         boolean isNeedToClone = isNeedToCloneEither.left().value();
540
541         if (artifactId == null || isNeedToClone) {
542             String uniqueId;
543             if (edgeLabelEnum != EdgeLabelEnum.INST_DEPLOYMENT_ARTIFACTS && edgeLabelEnum != EdgeLabelEnum.INSTANCE_ARTIFACTS) {
544                 uniqueId = UniqueIdBuilder.buildPropertyUniqueId(componentId, artifactToUpdate.getArtifactLabel());
545             } else {
546                 uniqueId = UniqueIdBuilder.buildInstanceArtifactUniqueId(componentId, instanceId, artifactToUpdate.getArtifactLabel());
547             }
548             artifactToUpdate.setUniqueId(uniqueId);
549             if (!isDeletePlaceholder)
550                 artifactToUpdate.setEsId(uniqueId);
551         } else
552             artifactToUpdate.setUniqueId(artifactId);
553
554         Map<String, ArtifactDataDefinition> artifacts = new HashMap<>();
555         Map<String, MapArtifactDataDefinition> artifactInst = null;
556         if (edgeLabelEnum != EdgeLabelEnum.INST_DEPLOYMENT_ARTIFACTS && edgeLabelEnum != EdgeLabelEnum.INSTANCE_ARTIFACTS) {
557
558             Either<Map<String, ArtifactDataDefinition>, TitanOperationStatus> artifactsEither = this.getDataFromGraph(componentId, edgeLabelEnum);
559
560             if (artifactsEither.isLeft() && artifactsEither.left().value() != null && !artifactsEither.left().value().isEmpty()) {
561                 artifacts = artifactsEither.left().value();
562                 if (isNeedToClone && artifacts != null) {
563                     artifacts.values().stream().forEach(a -> a.setDuplicated(Boolean.TRUE));
564                 }
565             }
566         } else {
567
568             Either<Map<String, MapArtifactDataDefinition>, TitanOperationStatus> artifactsEither = this.getDataFromGraph(componentId, edgeLabelEnum);
569             if (artifactsEither.isLeft()) {
570                 artifactInst = artifactsEither.left().value();
571                 if (isNeedToClone && artifactInst != null) {
572                     artifactInst.values().forEach(ma -> ma.getMapToscaDataDefinition().values().forEach(a -> a.setDuplicated(Boolean.TRUE)));
573                 }
574                 MapArtifactDataDefinition artifatcsOnInstance = artifactInst.get(instanceId);
575                 if (artifatcsOnInstance != null) {
576                     artifacts = artifatcsOnInstance.getMapToscaDataDefinition();
577                 }
578             }
579         }
580         String oldChecksum = null;
581         String oldVersion = null;
582         if (artifacts != null && artifacts.containsKey(artifactInfo.getArtifactLabel())) {
583             ArtifactDataDefinition oldArtifactData = artifacts.get(artifactInfo.getArtifactLabel());
584             oldChecksum = oldArtifactData.getArtifactChecksum();
585             oldVersion = oldArtifactData.getArtifactVersion();
586             //duplicated flag didn't receive from UI, take from DB
587             artifactToUpdate.setDuplicated(oldArtifactData.getDuplicated());
588
589             if (isNeedToClone)
590                 artifactToUpdate.setDuplicated(Boolean.FALSE);
591             else {
592                 if (artifactToUpdate.getDuplicated()) {
593                     String uniqueId = "";
594                     if(type != NodeTypeEnum.ResourceInstance)
595                         uniqueId = UniqueIdBuilder.buildPropertyUniqueId(componentId, artifactToUpdate.getArtifactLabel());
596                     else
597                         uniqueId = UniqueIdBuilder.buildInstanceArtifactUniqueId(componentId, instanceId, artifactToUpdate.getArtifactLabel());
598
599                     artifactToUpdate.setUniqueId(uniqueId);
600                     if (!isDeletePlaceholder)
601                         artifactToUpdate.setEsId(uniqueId);
602                     artifactToUpdate.setDuplicated(Boolean.FALSE);
603                 }
604             }
605         }
606         updateUUID(artifactToUpdate, oldChecksum, oldVersion, isUpdate, edgeLabelEnum);
607
608         if (artifactInfo.getPayloadData() == null) {
609             if (!artifactToUpdate.getMandatory() || artifactToUpdate.getEsId() != null) {
610                 artifactToUpdate.setEsId(artifactToUpdate.getUniqueId());
611             }
612         } else {
613             if (artifactToUpdate.getEsId() == null) {
614                 artifactToUpdate.setEsId(artifactToUpdate.getUniqueId());
615             }
616         }
617
618         StorageOperationStatus status = StorageOperationStatus.OK;
619         if (edgeLabelEnum != EdgeLabelEnum.INST_DEPLOYMENT_ARTIFACTS && edgeLabelEnum != EdgeLabelEnum.INSTANCE_ARTIFACTS) {
620             List<ArtifactDataDefinition> toscaDataList = new ArrayList<>();
621             toscaDataList.add(artifactToUpdate);
622
623             if (isNeedToClone && artifacts != null) {
624                 artifacts.values().stream().filter(a -> !a.getArtifactLabel().equals(artifactToUpdate.getArtifactLabel())).forEach(toscaDataList::add);
625             }
626             status = updateToscaDataOfToscaElement(componentId, edgeLabelEnum, vertexTypeEnum, toscaDataList, JsonPresentationFields.ARTIFACT_LABEL);
627         } else {
628             List<ArtifactDataDefinition> toscaDataList = new ArrayList<>();
629             toscaDataList.add(artifactToUpdate);
630             List<String> pathKeys = new ArrayList<>();
631             pathKeys.add(instanceId);
632             if (isNeedToClone) {
633                 MapArtifactDataDefinition artifatcsOnInstance = artifactInst.get(instanceId);
634                 if (artifatcsOnInstance != null) {
635                     artifacts = artifatcsOnInstance.getMapToscaDataDefinition();
636                     artifacts.put(artifactToUpdate.getArtifactLabel(), artifactToUpdate);
637                 }
638
639                 for (Entry<String, MapArtifactDataDefinition> e : artifactInst.entrySet()) {
640                     List<ArtifactDataDefinition> toscaDataListPerInst = e.getValue().getMapToscaDataDefinition().values().stream().collect(Collectors.toList());
641                     List<String> pathKeysPerInst = new ArrayList<>();
642                     pathKeysPerInst.add(e.getKey());
643                     status = updateToscaDataDeepElementsOfToscaElement(componentId, edgeLabelEnum, vertexTypeEnum, toscaDataListPerInst, pathKeysPerInst, JsonPresentationFields.ARTIFACT_LABEL);
644                     if (status != StorageOperationStatus.OK) {
645                         log.debug("Failed to update atifacts group for instance {} in component {} edge type {} error {}", instanceId, componentId, edgeLabelEnum, status);
646                         res = Either.right(status);
647                         break;
648                     }
649                 }
650             } else {
651                 status = updateToscaDataDeepElementsOfToscaElement(componentId, edgeLabelEnum, vertexTypeEnum, toscaDataList, pathKeys, JsonPresentationFields.ARTIFACT_LABEL);
652             }
653         }
654         if (status == StorageOperationStatus.OK)
655             res = Either.left(artifactToUpdate);
656         else
657             res = Either.right(status);
658         return res;
659     }
660
661     public void generateUUID(ArtifactDataDefinition artifactData, String oldVesrion) {
662
663         UUID uuid = UUID.randomUUID();
664         artifactData.setArtifactUUID(uuid.toString());
665         MDC.put("serviceInstanceID", uuid.toString());
666         updateVersionAndDate(artifactData, oldVesrion);
667     }
668
669     private void updateVersionAndDate(ArtifactDataDefinition artifactData, String oldVesrion) {
670         if (artifactData.getArtifactChecksum() != null) {
671             long time = System.currentTimeMillis();
672             artifactData.setPayloadUpdateDate(time);
673         }
674         int newVersion = new Integer(oldVesrion).intValue();
675         newVersion++;
676         artifactData.setArtifactVersion(String.valueOf(newVersion));
677     }
678
679     public Either<ArtifactDataDefinition, StorageOperationStatus> removeArtifactOnGraph(ArtifactDefinition artifactFromGraph, String componentId, String instanceId, NodeTypeEnum type, boolean deleteMandatoryArtifact) {
680
681         Triple<EdgeLabelEnum, Boolean, VertexTypeEnum> triple = getEdgeLabelEnumFromArtifactGroupType(artifactFromGraph.getArtifactGroupType(), type);
682         EdgeLabelEnum edgeLabelEnum = triple.getLeft();
683         VertexTypeEnum vertexTypeEnum = triple.getRight();
684
685         if (deleteMandatoryArtifact || !(artifactFromGraph.getMandatory() || artifactFromGraph.getServiceApi())) {
686             StorageOperationStatus status;
687             if (triple.getMiddle()) {
688                 List<String> pathKeys = new ArrayList<>();
689                 pathKeys.add(instanceId);
690                 status = deleteToscaDataDeepElement(componentId, edgeLabelEnum, vertexTypeEnum, artifactFromGraph.getArtifactLabel(), pathKeys, JsonPresentationFields.ARTIFACT_LABEL);
691             } else {
692                 status = deleteToscaDataElement(componentId, edgeLabelEnum, vertexTypeEnum, artifactFromGraph.getArtifactLabel(), JsonPresentationFields.ARTIFACT_LABEL);
693             }
694             if (status != StorageOperationStatus.OK)
695                 return Either.right(status);
696         }
697         return Either.left(artifactFromGraph);
698
699     }
700
701     public Either<ArtifactDataDefinition, StorageOperationStatus> deleteArtifactWithCloningOnGraph(String componentId, ArtifactDefinition artifactToDelete, NodeTypeEnum type, String instanceId, boolean deleteMandatoryArtifact) {
702
703         Either<ArtifactDataDefinition, StorageOperationStatus> result = null;
704         Triple<EdgeLabelEnum, Boolean, VertexTypeEnum> triple = getEdgeLabelEnumFromArtifactGroupType(artifactToDelete.getArtifactGroupType(), type);
705         EdgeLabelEnum edgeLabel = triple.getLeft();
706         VertexTypeEnum vertexLabel = triple.getRight();
707
708         Boolean deleteElement = deleteMandatoryArtifact || !(artifactToDelete.getMandatory() || artifactToDelete.getServiceApi());
709         Map<String, ToscaDataDefinition> artifacts = null;
710         GraphVertex parentVertex = null;
711         Either<Map<String, ToscaDataDefinition>, TitanOperationStatus> getArtifactsRes = null;
712
713         Either<GraphVertex, TitanOperationStatus> getToscaElementRes = titanDao.getVertexById(componentId, JsonParseFlagEnum.NoParse);
714         if (getToscaElementRes.isRight()) {
715             CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to get tosca element {} upon getting tosca data from graph. Status is {}. ", componentId, getToscaElementRes.right().value());
716             result = Either.right(DaoStatusConverter.convertTitanStatusToStorageStatus(getToscaElementRes.right().value()));
717         }
718         if (result == null) {
719             parentVertex = getToscaElementRes.left().value();
720             getArtifactsRes = this.getDataFromGraph(parentVertex, edgeLabel);
721             if (getArtifactsRes.isRight()) {
722                 result = Either.right(DaoStatusConverter.convertTitanStatusToStorageStatus(getArtifactsRes.right().value()));
723             }
724         }
725         if (result == null) {
726             artifacts = getArtifactsRes.left().value();
727             if (triple.getMiddle()) {
728                 artifacts.values().forEach(ma -> ((MapArtifactDataDefinition) ma).getMapToscaDataDefinition().values().forEach(a -> a.setDuplicated(Boolean.TRUE)));
729                 MapArtifactDataDefinition artifatcsOnInstance = (MapArtifactDataDefinition) artifacts.get(instanceId);
730                 if (artifatcsOnInstance != null && deleteElement) {
731                     artifatcsOnInstance.getMapToscaDataDefinition().remove(artifactToDelete.getArtifactLabel());
732                 }
733             } else {
734                 if (deleteElement) {
735                     artifacts.remove(artifactToDelete.getArtifactLabel());
736                 }
737                 artifacts.values().stream().forEach(a -> ((ArtifactDataDefinition) a).setDuplicated(Boolean.TRUE));
738             }
739             artifactToDelete.setDuplicated(Boolean.TRUE);
740         }
741         if (artifacts != null) {
742             TitanOperationStatus status = titanDao.deleteEdgeByDirection(parentVertex, Direction.OUT, edgeLabel);
743             if (status != TitanOperationStatus.OK) {
744                 result = Either.right(DaoStatusConverter.convertTitanStatusToStorageStatus(status));
745             } else if (MapUtils.isNotEmpty(artifacts)) {
746                 Either<GraphVertex, StorageOperationStatus> associateResult = associateElementToData(parentVertex, vertexLabel, edgeLabel, artifacts);
747                 if (associateResult.isRight()) {
748                     result = Either.right(associateResult.right().value());
749                 }
750             }
751         }
752         if (result == null) {
753             result = Either.left(artifactToDelete);
754         }
755         return result;
756     }
757
758 }