Upgrade SDC from Titan to Janus Graph
[sdc.git] / catalog-model / src / main / java / org / openecomp / sdc / be / model / operations / impl / AdditionalInformationOperation.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.operations.impl;
22
23 import org.janusgraph.core.JanusGraphVertex;
24 import fj.data.Either;
25 import org.apache.commons.lang3.tuple.ImmutablePair;
26 import org.apache.tinkerpop.gremlin.structure.Vertex;
27 import org.openecomp.sdc.be.config.BeEcompErrorManager;
28 import org.openecomp.sdc.be.dao.graph.GraphElementFactory;
29 import org.openecomp.sdc.be.dao.graph.datatype.GraphEdge;
30 import org.openecomp.sdc.be.dao.graph.datatype.GraphElementTypeEnum;
31 import org.openecomp.sdc.be.dao.graph.datatype.GraphRelation;
32 import org.openecomp.sdc.be.dao.janusgraph.JanusGraphOperationStatus;
33 import org.openecomp.sdc.be.dao.neo4j.GraphEdgeLabels;
34 import org.openecomp.sdc.be.dao.neo4j.GraphPropertiesDictionary;
35 import org.openecomp.sdc.be.dao.janusgraph.JanusGraphGenericDao;
36 import org.openecomp.sdc.be.datatypes.elements.AdditionalInfoParameterDataDefinition;
37 import org.openecomp.sdc.be.datatypes.elements.AdditionalInfoParameterInfo;
38 import org.openecomp.sdc.be.datatypes.enums.NodeTypeEnum;
39 import org.openecomp.sdc.be.model.AdditionalInformationDefinition;
40 import org.openecomp.sdc.be.model.operations.api.IAdditionalInformationOperation;
41 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
42 import org.openecomp.sdc.be.resources.data.AdditionalInfoParameterData;
43 import org.openecomp.sdc.be.resources.data.ResourceMetadataData;
44 import org.openecomp.sdc.be.resources.data.ServiceMetadataData;
45 import org.openecomp.sdc.be.resources.data.UniqueIdData;
46 import org.openecomp.sdc.common.log.wrappers.Logger;
47 import org.springframework.stereotype.Component;
48
49 import java.util.ArrayList;
50 import java.util.HashMap;
51 import java.util.List;
52 import java.util.Map;
53 import java.util.Map.Entry;
54
55 @Component("additional-information-operation")
56 public class AdditionalInformationOperation implements IAdditionalInformationOperation {
57
58     private static final Logger log = Logger.getLogger(AdditionalInformationOperation.class.getName());
59
60     @javax.annotation.Resource
61     private JanusGraphGenericDao janusGraphGenericDao;
62
63     private static final String GOING_TO_EXECUTE_COMMIT_ON_GRAPH = "Going to execute commit on graph.";
64         private static final String GOING_TO_EXECUTE_ROLLBACK_ON_GRAPH = "Going to execute rollback on graph.";
65         private static final String ADDITIONAL_INFORMATION_OF = "additional information of ";
66         public static final String EMPTY_VALUE = null;
67
68     public AdditionalInformationOperation() {
69         super();
70     }
71
72
73     @Override
74     public Either<AdditionalInformationDefinition, JanusGraphOperationStatus> addAdditionalInformationParameter(NodeTypeEnum nodeType, String componentId, String key, String value) {
75
76         JanusGraphOperationStatus
77             verifyNodeTypeVsComponent = verifyNodeTypeVsComponent(nodeType, componentId);
78         if (verifyNodeTypeVsComponent != JanusGraphOperationStatus.OK) {
79             return Either.right(verifyNodeTypeVsComponent);
80         }
81
82         Either<ImmutablePair<AdditionalInfoParameterData, GraphEdge>, JanusGraphOperationStatus> getResult = janusGraphGenericDao
83             .getChild(UniqueIdBuilder.getKeyByNodeType(nodeType), componentId, GraphEdgeLabels.ADDITIONAL_INFORMATION,
84                 NodeTypeEnum.AdditionalInfoParameters, AdditionalInfoParameterData.class);
85
86         if (getResult.isRight()) {
87             JanusGraphOperationStatus status = getResult.right().value();
88             return Either.right(status);
89         }
90
91         ImmutablePair<AdditionalInfoParameterData, GraphEdge> immutablePair = getResult.left().value();
92         AdditionalInfoParameterData parameterData = immutablePair.getLeft();
93         Map<String, String> parameters = parameterData.getParameters();
94         if (parameters == null) {
95             parameters = new HashMap<>();
96             parameterData.setParameters(parameters);
97         }
98         Map<String, String> idToKey = parameterData.getIdToKey();
99         if (idToKey == null) {
100             idToKey = new HashMap<>();
101             parameterData.setIdToKey(idToKey);
102         }
103
104         Integer lastCreatedCounter = parameterData.getAdditionalInfoParameterDataDefinition().getLastCreatedCounter();
105         lastCreatedCounter++;
106
107         if (parameters.containsKey(key)) {
108             log.debug("The key {} already exists under component {}", key, componentId);
109             return Either.right(JanusGraphOperationStatus.ALREADY_EXIST);
110         }
111
112         idToKey.put(String.valueOf(lastCreatedCounter), key);
113         parameters.put(key, value);
114         parameterData.getAdditionalInfoParameterDataDefinition().setLastCreatedCounter(lastCreatedCounter);
115
116         Either<AdditionalInfoParameterData, JanusGraphOperationStatus> updateNode = janusGraphGenericDao
117             .updateNode(parameterData, AdditionalInfoParameterData.class);
118
119         if (updateNode.isRight()) {
120             JanusGraphOperationStatus status = updateNode.right().value();
121             BeEcompErrorManager.getInstance().logBeFailedUpdateNodeError("UpdateAdditionalInformationParameter", ADDITIONAL_INFORMATION_OF + nodeType.getName() + " " + componentId, String.valueOf(status));
122             return Either.right(status);
123         }
124
125         AdditionalInformationDefinition informationDefinition = createInformationDefinitionFromNode(componentId, parameters, idToKey, updateNode.left().value());
126
127         return Either.left(informationDefinition);
128
129     }
130
131     @Override
132     public Either<AdditionalInformationDefinition, JanusGraphOperationStatus> updateAdditionalInformationParameter(NodeTypeEnum nodeType, String componentId, String id, String key, String value) {
133
134         JanusGraphOperationStatus
135             verifyNodeTypeVsComponent = verifyNodeTypeVsComponent(nodeType, componentId);
136         if (verifyNodeTypeVsComponent != JanusGraphOperationStatus.OK) {
137             return Either.right(verifyNodeTypeVsComponent);
138         }
139
140         Either<ImmutablePair<AdditionalInfoParameterData, GraphEdge>, JanusGraphOperationStatus> getResult = janusGraphGenericDao
141             .getChild(UniqueIdBuilder.getKeyByNodeType(nodeType), componentId, GraphEdgeLabels.ADDITIONAL_INFORMATION,
142                 NodeTypeEnum.AdditionalInfoParameters, AdditionalInfoParameterData.class);
143
144         if (getResult.isRight()) {
145             JanusGraphOperationStatus status = getResult.right().value();
146             return Either.right(status);
147         }
148
149         ImmutablePair<AdditionalInfoParameterData, GraphEdge> immutablePair = getResult.left().value();
150         AdditionalInfoParameterData parameterData = immutablePair.getLeft();
151         Map<String, String> parameters = parameterData.getParameters();
152         Map<String, String> idToKey = parameterData.getIdToKey();
153         if (idToKey == null || !idToKey.containsKey(id)) {
154             return Either.right(JanusGraphOperationStatus.INVALID_ID);
155         }
156
157         String origKey = idToKey.get(id);
158
159         if (!origKey.equals(key)) {
160             if (parameters.containsKey(key)) {
161                 log.debug("The key {} already exists", key);
162                 return Either.right(JanusGraphOperationStatus.ALREADY_EXIST);
163             }
164             String removed = parameters.remove(origKey);
165             log.trace("The key-value {} = {} was removed from additionalInformation", origKey, removed);
166         }
167         parameters.put(key, value);
168         idToKey.put(id, key);
169
170         Either<AdditionalInfoParameterData, JanusGraphOperationStatus> updateNode = janusGraphGenericDao
171             .updateNode(parameterData, AdditionalInfoParameterData.class);
172
173         if (updateNode.isRight()) {
174             JanusGraphOperationStatus status = updateNode.right().value();
175             BeEcompErrorManager.getInstance().logBeFailedUpdateNodeError("UpdateAdditionalInformationParameter", "additional information of resource " + componentId, String.valueOf(status));
176             return Either.right(status);
177         }
178
179         AdditionalInformationDefinition informationDefinition = createInformationDefinitionFromNode(componentId, parameters, idToKey, updateNode.left().value());
180
181         return Either.left(informationDefinition);
182
183     }
184
185     @Override
186     public Either<AdditionalInformationDefinition, JanusGraphOperationStatus> deleteAdditionalInformationParameter(NodeTypeEnum nodeType, String componentId, String id) {
187
188         JanusGraphOperationStatus
189             verifyNodeTypeVsComponent = verifyNodeTypeVsComponent(nodeType, componentId);
190         if (verifyNodeTypeVsComponent != JanusGraphOperationStatus.OK) {
191             return Either.right(verifyNodeTypeVsComponent);
192         }
193
194         Either<ImmutablePair<AdditionalInfoParameterData, GraphEdge>, JanusGraphOperationStatus> getResult = janusGraphGenericDao
195             .getChild(UniqueIdBuilder.getKeyByNodeType(nodeType), componentId, GraphEdgeLabels.ADDITIONAL_INFORMATION,
196                 NodeTypeEnum.AdditionalInfoParameters, AdditionalInfoParameterData.class);
197
198         if (getResult.isRight()) {
199             JanusGraphOperationStatus status = getResult.right().value();
200             return Either.right(status);
201         }
202
203         ImmutablePair<AdditionalInfoParameterData, GraphEdge> immutablePair = getResult.left().value();
204         AdditionalInfoParameterData parameterData = immutablePair.getLeft();
205         Map<String, String> parameters = parameterData.getParameters();
206         Map<String, String> idToKey = parameterData.getIdToKey();
207
208         if (idToKey == null || !idToKey.containsKey(id)) {
209             return Either.right(JanusGraphOperationStatus.INVALID_ID);
210         }
211
212         String key = idToKey.get(id);
213         String removedKey = idToKey.remove(id);
214         String removedValue = parameters.remove(key);
215         log.trace("The key-value {} = {} was removed from additionalInformation", removedKey, removedValue);
216
217         Either<AdditionalInfoParameterData, JanusGraphOperationStatus> updateNode = janusGraphGenericDao
218             .updateNode(parameterData, AdditionalInfoParameterData.class);
219
220         if (updateNode.isRight()) {
221             JanusGraphOperationStatus status = updateNode.right().value();
222             BeEcompErrorManager.getInstance().logBeFailedUpdateNodeError("DeleteAdditionalInformationParameter", ADDITIONAL_INFORMATION_OF + nodeType.getName() + " " + componentId, String.valueOf(status));
223             return Either.right(status);
224         }
225
226         AdditionalInformationDefinition informationDefinition = createInformationDefinitionFromNode(componentId, parameters, idToKey, updateNode.left().value());
227
228         return Either.left(informationDefinition);
229
230     }
231
232     private AdditionalInformationDefinition createInformationDefinitionFromNode(String resourceId, Map<String, String> parameters, Map<String, String> idToKey, AdditionalInfoParameterData additionalInfoParameterData) {
233         AdditionalInfoParameterDataDefinition dataDefinition = additionalInfoParameterData.getAdditionalInfoParameterDataDefinition();
234
235         return new AdditionalInformationDefinition(dataDefinition, resourceId, convertParameters(parameters, idToKey));
236     }
237
238     private List<AdditionalInfoParameterInfo> convertParameters(Map<String, String> parameters, Map<String, String> idToKey) {
239
240         List<AdditionalInfoParameterInfo> list = new ArrayList<>();
241
242         if (parameters != null) {
243             for (Entry<String, String> idToKeyEntry : idToKey.entrySet()) {
244
245                 String id = idToKeyEntry.getKey();
246                 String key = idToKeyEntry.getValue();
247
248                 String value = parameters.get(key);
249
250                 AdditionalInfoParameterInfo parameterInfo = new AdditionalInfoParameterInfo(id, key, value);
251                 list.add(parameterInfo);
252             }
253
254         }
255
256         return list;
257     }
258
259     @Override
260     public Either<AdditionalInfoParameterData, JanusGraphOperationStatus> addAdditionalInformationNode(NodeTypeEnum nodeType, String componentId) {
261
262         UniqueIdData from = new UniqueIdData(nodeType, componentId);
263
264         String uniqueId = UniqueIdBuilder.buildAdditionalInformationUniqueId(componentId);
265         AdditionalInfoParameterDataDefinition additionalInfoParameterDataDefinition = new AdditionalInfoParameterDataDefinition();
266         additionalInfoParameterDataDefinition.setUniqueId(uniqueId);
267
268         AdditionalInfoParameterData additionalInfoParameterData = new AdditionalInfoParameterData(additionalInfoParameterDataDefinition, new HashMap<>(), new HashMap<>());
269
270         Either<AdditionalInfoParameterData, JanusGraphOperationStatus> createNode = janusGraphGenericDao
271             .createNode(additionalInfoParameterData, AdditionalInfoParameterData.class);
272         if (createNode.isRight()) {
273             JanusGraphOperationStatus status = createNode.right().value();
274             BeEcompErrorManager.getInstance().logBeFailedCreateNodeError("AddAdditionalInformationNode", uniqueId, String.valueOf(status));
275             return Either.right(status);
276         }
277
278         AdditionalInfoParameterData to = createNode.left().value();
279
280         Either<GraphRelation, JanusGraphOperationStatus> createRelation = janusGraphGenericDao
281             .createRelation(from, to, GraphEdgeLabels.ADDITIONAL_INFORMATION, null);
282         if (createRelation.isRight()) {
283             JanusGraphOperationStatus status = createRelation.right().value();
284             return Either.right(status);
285         }
286
287         return Either.left(to);
288     }
289
290     @Override
291     public Either<JanusGraphVertex, JanusGraphOperationStatus> addAdditionalInformationNode(NodeTypeEnum nodeType, String componentId, JanusGraphVertex metadataVertex) {
292
293         String uniqueId = UniqueIdBuilder.buildAdditionalInformationUniqueId(componentId);
294         AdditionalInfoParameterDataDefinition additionalInfoParameterDataDefinition = new AdditionalInfoParameterDataDefinition();
295         additionalInfoParameterDataDefinition.setUniqueId(uniqueId);
296
297         AdditionalInfoParameterData additionalInfoParameterData = new AdditionalInfoParameterData(additionalInfoParameterDataDefinition, new HashMap<>(), new HashMap<>());
298
299         Either<JanusGraphVertex, JanusGraphOperationStatus> createNode = janusGraphGenericDao.createNode(additionalInfoParameterData);
300         if (createNode.isRight()) {
301             JanusGraphOperationStatus status = createNode.right().value();
302             BeEcompErrorManager.getInstance().logBeFailedCreateNodeError("AddAdditionalInformationNode", uniqueId, String.valueOf(status));
303             return Either.right(status);
304         }
305
306         JanusGraphVertex additionalInfoVertex = createNode.left().value();
307
308         JanusGraphOperationStatus createRelation = janusGraphGenericDao
309             .createEdge(metadataVertex, additionalInfoVertex, GraphEdgeLabels.ADDITIONAL_INFORMATION, null);
310
311         if (!createRelation.equals(JanusGraphOperationStatus.OK)) {
312             return Either.right(createRelation);
313         }
314         return Either.left(additionalInfoVertex);
315     }
316
317     public Either<AdditionalInformationDefinition, JanusGraphOperationStatus> addAdditionalInformationNode(NodeTypeEnum nodeType, String componentId, AdditionalInformationDefinition parameters) {
318
319         Either<AdditionalInfoParameterData, JanusGraphOperationStatus> status = this.addAdditionalInformationNode(nodeType, componentId);
320
321         if (status.isRight()) {
322             return Either.right(status.right().value());
323         }
324
325         AdditionalInfoParameterData parameterData = status.left().value();
326
327         populateParameterNodeWithParameters(parameterData, parameters);
328
329         Either<AdditionalInfoParameterData, JanusGraphOperationStatus> updateNode = janusGraphGenericDao
330             .updateNode(parameterData, AdditionalInfoParameterData.class);
331
332         if (updateNode.isRight()) {
333             return Either.right(updateNode.right().value());
334         }
335
336         AdditionalInformationDefinition informationDefinition = convertAdditionalInformationDataToDefinition(updateNode.left().value(), componentId);
337
338         return Either.left(informationDefinition);
339     }
340
341     public JanusGraphOperationStatus addAdditionalInformationNode(NodeTypeEnum nodeType, String componentId, AdditionalInformationDefinition parameters, JanusGraphVertex metadataVertex) {
342
343         Either<JanusGraphVertex, JanusGraphOperationStatus> status = this.addAdditionalInformationNode(nodeType, componentId, metadataVertex);
344
345         if (status.isRight()) {
346             return status.right().value();
347         }
348         JanusGraphVertex additionalInfoVertex = status.left().value();
349
350         Map<String, Object> newProp = janusGraphGenericDao.getProperties(additionalInfoVertex);
351         AdditionalInfoParameterData parameterData = GraphElementFactory.createElement(NodeTypeEnum.AdditionalInfoParameters.getName(), GraphElementTypeEnum.Node, newProp, AdditionalInfoParameterData.class);
352
353         populateParameterNodeWithParameters(parameterData, parameters);
354
355         return janusGraphGenericDao.updateVertex(parameterData, additionalInfoVertex);
356     }
357
358     private void populateParameterNodeWithParameters(AdditionalInfoParameterData parameterData, AdditionalInformationDefinition aiDefinition) {
359
360         if (aiDefinition != null) {
361
362             Integer lastCreatedCounter = aiDefinition.getLastCreatedCounter();
363             parameterData.getAdditionalInfoParameterDataDefinition().setLastCreatedCounter(lastCreatedCounter);
364             log.trace("Set last created counter of additional information to {}", lastCreatedCounter);
365
366             List<AdditionalInfoParameterInfo> parameters = aiDefinition.getParameters();
367             if (parameters != null) {
368
369                 Map<String, String> idToKey = new HashMap<>();
370                 Map<String, String> parametersMap = new HashMap<>();
371                 for (AdditionalInfoParameterInfo additionalInfoParameterInfo : parameters) {
372                     String uniqueId = additionalInfoParameterInfo.getUniqueId();
373                     String key = additionalInfoParameterInfo.getKey();
374                     String value = additionalInfoParameterInfo.getValue();
375
376                     if (key != null && !key.isEmpty()) {
377                         idToKey.put(uniqueId, key);
378                         parametersMap.put(key, value);
379                     }
380                 }
381                 parameterData.setIdToKey(idToKey);
382                 parameterData.setParameters(parametersMap);
383             }
384         }
385
386     }
387
388     @Override
389     public JanusGraphOperationStatus findResourceAllAdditionalInformationRecursively(String uniqueId, List<AdditionalInformationDefinition> properties) {
390
391         log.trace("Going to fetch additional information under resource {}", uniqueId);
392         JanusGraphOperationStatus resourceCapabilitiesStatus = findAdditionalInformationOfNode(NodeTypeEnum.Resource, uniqueId, properties);
393
394         if (!resourceCapabilitiesStatus.equals(JanusGraphOperationStatus.OK)) {
395             return resourceCapabilitiesStatus;
396         }
397
398         Either<ImmutablePair<ResourceMetadataData, GraphEdge>, JanusGraphOperationStatus> parentNodes = janusGraphGenericDao
399             .getChild(UniqueIdBuilder.getKeyByNodeType(NodeTypeEnum.Resource), uniqueId, GraphEdgeLabels.DERIVED_FROM, NodeTypeEnum.Resource,
400                 ResourceMetadataData.class);
401
402         if (parentNodes.isRight()) {
403             JanusGraphOperationStatus parentNodesStatus = parentNodes.right().value();
404             if (!parentNodesStatus.equals(JanusGraphOperationStatus.NOT_FOUND)) {
405                 log.error("Failed to find parent additional information of resource {}. status is {}", uniqueId, parentNodesStatus);
406                 return parentNodesStatus;
407             }
408         }
409
410         if (parentNodes.isLeft()) {
411             ImmutablePair<ResourceMetadataData, GraphEdge> parnetNodePair = parentNodes.left().value();
412             String parentUniqueId = parnetNodePair.getKey().getMetadataDataDefinition().getUniqueId();
413             JanusGraphOperationStatus addParentIntStatus = findResourceAllAdditionalInformationRecursively(parentUniqueId, properties);
414
415             if (addParentIntStatus != JanusGraphOperationStatus.OK) {
416                 log.error("Failed to find all resource additional information of resource {}", parentUniqueId);
417                 return addParentIntStatus;
418             }
419         }
420         return JanusGraphOperationStatus.OK;
421
422     }
423
424     @Override
425     public JanusGraphOperationStatus findServiceAllAdditionalInformationRecursively(String uniqueId, List<AdditionalInformationDefinition> properties) {
426
427         log.trace("Going to fetch additional information under service {}", uniqueId);
428         JanusGraphOperationStatus resourceCapabilitiesStatus = findAdditionalInformationOfNode(NodeTypeEnum.Service, uniqueId, properties);
429
430         if (!resourceCapabilitiesStatus.equals(JanusGraphOperationStatus.OK)) {
431             return resourceCapabilitiesStatus;
432         }
433
434         Either<ImmutablePair<ServiceMetadataData, GraphEdge>, JanusGraphOperationStatus> parentNodes = janusGraphGenericDao
435             .getChild(UniqueIdBuilder.getKeyByNodeType(NodeTypeEnum.Service), uniqueId, GraphEdgeLabels.DERIVED_FROM, NodeTypeEnum.Service,
436                 ServiceMetadataData.class);
437
438         if (parentNodes.isRight()) {
439             JanusGraphOperationStatus parentNodesStatus = parentNodes.right().value();
440             if (!parentNodesStatus.equals(JanusGraphOperationStatus.NOT_FOUND)) {
441                 log.error("Failed to find parent additional information of resource {}. status is {}", uniqueId, parentNodesStatus);
442                 return parentNodesStatus;
443             }
444         }
445
446         if (parentNodes.isLeft()) {
447             ImmutablePair<ServiceMetadataData, GraphEdge> parnetNodePair = parentNodes.left().value();
448             String parentUniqueId = parnetNodePair.getKey().getMetadataDataDefinition().getUniqueId();
449             JanusGraphOperationStatus addParentIntStatus = findServiceAllAdditionalInformationRecursively(parentUniqueId, properties);
450
451             if (addParentIntStatus != JanusGraphOperationStatus.OK) {
452                 log.error("Failed to find all resource additional information of resource {}", parentUniqueId);
453                 return addParentIntStatus;
454             }
455         }
456         return JanusGraphOperationStatus.OK;
457
458     }
459
460     private JanusGraphOperationStatus findAdditionalInformationOfNode(NodeTypeEnum nodeType, String uniqueId, List<AdditionalInformationDefinition> properties) {
461
462         Either<ImmutablePair<AdditionalInfoParameterData, GraphEdge>, JanusGraphOperationStatus> childNode = janusGraphGenericDao
463             .getChild(UniqueIdBuilder.getKeyByNodeType(nodeType), uniqueId, GraphEdgeLabels.ADDITIONAL_INFORMATION,
464                 NodeTypeEnum.AdditionalInfoParameters, AdditionalInfoParameterData.class);
465
466         if (childNode.isRight()) {
467             JanusGraphOperationStatus status = childNode.right().value();
468             if (status == JanusGraphOperationStatus.NOT_FOUND) {
469                 status = JanusGraphOperationStatus.OK;
470             }
471             return status;
472         }
473
474         ImmutablePair<AdditionalInfoParameterData, GraphEdge> immutablePair = childNode.left().value();
475         AdditionalInfoParameterData propertyData = immutablePair.getKey();
476
477         Map<String, String> parameters = propertyData.getParameters();
478         if (parameters != null && !parameters.isEmpty()) {
479             AdditionalInformationDefinition additionalInfoDef = this.convertAdditionalInformationDataToDefinition(propertyData, uniqueId);
480             properties.add(additionalInfoDef);
481         }
482
483         return JanusGraphOperationStatus.OK;
484
485     }
486
487     private AdditionalInformationDefinition convertAdditionalInformationDataToDefinition(AdditionalInfoParameterData additionalInfoData, String uniqueId) {
488
489         Map<String, String> parameters = additionalInfoData.getParameters();
490         Map<String, String> idToKey = additionalInfoData.getIdToKey();
491
492         return new AdditionalInformationDefinition(additionalInfoData.getAdditionalInfoParameterDataDefinition(), uniqueId, convertParameters(parameters, idToKey));
493     }
494
495     @Override
496     public Either<AdditionalInformationDefinition, StorageOperationStatus> createAdditionalInformationParameter(NodeTypeEnum nodeType, String resourceId, String key, String value, boolean inTransaction) {
497
498         Either<AdditionalInformationDefinition, StorageOperationStatus> result = null;
499
500         try {
501
502             Either<AdditionalInformationDefinition, JanusGraphOperationStatus> either = this.addAdditionalInformationParameter(nodeType, resourceId, key, value);
503
504             if (either.isRight()) {
505                 JanusGraphOperationStatus status = either.right().value();
506                 log.debug("Failed to add additional information property {} to component {}. Status is {}", key, resourceId, status);
507                 BeEcompErrorManager.getInstance().logBeFailedUpdateNodeError("CreateAdditionalInformationParameter", ADDITIONAL_INFORMATION_OF + nodeType.getName() + " " + resourceId, String.valueOf(status));
508                 result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
509             } else {
510                 AdditionalInformationDefinition additionalInformationDefinition = either.left().value();
511                 result = Either.left(additionalInformationDefinition);
512             }
513
514             return result;
515         } finally {
516             commitOrRollback(inTransaction, result);
517         }
518
519     }
520
521     @Override
522     public Either<AdditionalInformationDefinition, StorageOperationStatus> updateAdditionalInformationParameter(NodeTypeEnum nodeType, String resourceId, String id, String key, String value, boolean inTransaction) {
523
524         Either<AdditionalInformationDefinition, StorageOperationStatus> result = null;
525
526         try {
527
528             Either<AdditionalInformationDefinition, JanusGraphOperationStatus> either = this.updateAdditionalInformationParameter(nodeType, resourceId, id, key, value);
529
530             if (either.isRight()) {
531                 log.info("Failed to update additional information property {} to component {}", key, resourceId);
532                 result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(either.right().value()));
533             } else {
534                 AdditionalInformationDefinition additionalInformationDefinition = either.left().value();
535                 result = Either.left(additionalInformationDefinition);
536             }
537
538             return result;
539
540         } finally {
541             commitOrRollback(inTransaction, result);
542         }
543
544     }
545
546     @Override
547     public Either<AdditionalInformationDefinition, StorageOperationStatus> deleteAdditionalInformationParameter(NodeTypeEnum nodeType, String resourceId, String id, boolean inTransaction) {
548
549         Either<AdditionalInformationDefinition, StorageOperationStatus> result = null;
550
551         try {
552
553             Either<AdditionalInformationDefinition, JanusGraphOperationStatus> either = this.deleteAdditionalInformationParameter(nodeType, resourceId, id);
554
555             if (either.isRight()) {
556                 log.error("Failed to delete additional information id {} to component {}", id, resourceId);
557                 result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(either.right().value()));
558             } else {
559                 AdditionalInformationDefinition additionalInformationDefinition = either.left().value();
560                 result = Either.left(additionalInformationDefinition);
561             }
562
563             return result;
564
565         } finally {
566             commitOrRollback(inTransaction, result);
567         }
568
569     }
570
571     @Override
572     public Either<Integer, StorageOperationStatus> getNumberOfAdditionalInformationParameters(NodeTypeEnum nodeType, String resourceId, boolean inTransaction) {
573
574         Either<Integer, StorageOperationStatus> result = null;
575
576         try {
577
578             Either<Integer, JanusGraphOperationStatus> either = this.getNumberOfParameters(nodeType, resourceId);
579
580             if (either.isRight()) {
581                 log.error("Failed to get the number of additional information properties in component {}", resourceId);
582                 result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(either.right().value()));
583             } else {
584                 Integer counter = either.left().value();
585                 result = Either.left(counter);
586             }
587
588             return result;
589         } finally {
590             if (!inTransaction) {
591                 if (result == null || result.isRight()) {
592                     log.error(GOING_TO_EXECUTE_ROLLBACK_ON_GRAPH);
593                     janusGraphGenericDao.rollback();
594                 } else {
595                     log.debug(GOING_TO_EXECUTE_COMMIT_ON_GRAPH);
596                     janusGraphGenericDao.commit();
597                 }
598             }
599         }
600
601     }
602
603     @Override
604     public Either<Integer, JanusGraphOperationStatus> getNumberOfParameters(NodeTypeEnum nodeType, String resourceId) {
605
606         Either<ImmutablePair<AdditionalInfoParameterData, GraphEdge>, JanusGraphOperationStatus> getResult = janusGraphGenericDao
607             .getChild(UniqueIdBuilder.getKeyByNodeType(nodeType), resourceId, GraphEdgeLabels.ADDITIONAL_INFORMATION,
608                 NodeTypeEnum.AdditionalInfoParameters, AdditionalInfoParameterData.class);
609
610         if (getResult.isRight()) {
611             JanusGraphOperationStatus status = getResult.right().value();
612             return Either.right(status);
613         }
614
615         ImmutablePair<AdditionalInfoParameterData, GraphEdge> immutablePair = getResult.left().value();
616         AdditionalInfoParameterData parameterData = immutablePair.getLeft();
617         Map<String, String> parameters = parameterData.getParameters();
618
619         Integer counter = 0;
620         if (parameters != null) {
621             counter = parameters.size();
622         }
623
624         return Either.left(counter);
625
626     }
627
628     @Override
629     public Either<AdditionalInfoParameterInfo, JanusGraphOperationStatus> getAdditionalInformationParameter(NodeTypeEnum nodeType, String componentId, String id) {
630
631         JanusGraphOperationStatus
632             verifyNodeTypeVsComponent = verifyNodeTypeVsComponent(nodeType, componentId);
633         if (verifyNodeTypeVsComponent != JanusGraphOperationStatus.OK) {
634             return Either.right(verifyNodeTypeVsComponent);
635         }
636
637         Either<ImmutablePair<AdditionalInfoParameterData, GraphEdge>, JanusGraphOperationStatus> getResult = janusGraphGenericDao
638             .getChild(UniqueIdBuilder.getKeyByNodeType(nodeType), componentId, GraphEdgeLabels.ADDITIONAL_INFORMATION,
639                 NodeTypeEnum.AdditionalInfoParameters, AdditionalInfoParameterData.class);
640
641         if (getResult.isRight()) {
642             JanusGraphOperationStatus status = getResult.right().value();
643             return Either.right(status);
644         }
645
646         ImmutablePair<AdditionalInfoParameterData, GraphEdge> immutablePair = getResult.left().value();
647         AdditionalInfoParameterData parameterData = immutablePair.getLeft();
648         Map<String, String> parameters = parameterData.getParameters();
649         Map<String, String> idToKey = parameterData.getIdToKey();
650
651         if (idToKey == null || !idToKey.containsKey(id)) {
652             return Either.right(JanusGraphOperationStatus.INVALID_ID);
653         }
654
655         String key = idToKey.get(id);
656         String value = parameters.get(key);
657
658         log.trace("The key-value {} = {} was retrieved for id {}", key, value, id);
659
660         Either<AdditionalInfoParameterData, JanusGraphOperationStatus> updateNode = janusGraphGenericDao
661             .updateNode(parameterData, AdditionalInfoParameterData.class);
662
663         if (updateNode.isRight()) {
664             JanusGraphOperationStatus status = updateNode.right().value();
665             if (status != JanusGraphOperationStatus.NOT_FOUND) {
666                 BeEcompErrorManager.getInstance().logBeFailedRetrieveNodeError("GetAdditionnalInformationParameter", ADDITIONAL_INFORMATION_OF + nodeType.getName() + " " + componentId, String.valueOf(status));
667             }
668             return Either.right(status);
669         }
670
671         AdditionalInfoParameterInfo additionalInfoParameterInfo = new AdditionalInfoParameterInfo(id, key, value);
672
673         return Either.left(additionalInfoParameterInfo);
674
675     }
676
677     @Override
678     public Either<AdditionalInformationDefinition, JanusGraphOperationStatus> getAllAdditionalInformationParameters(NodeTypeEnum nodeType, String componentId, boolean ignoreVerification) {
679
680         if (!ignoreVerification) {
681             JanusGraphOperationStatus
682                 verifyNodeTypeVsComponent = verifyNodeTypeVsComponent(nodeType, componentId);
683             if (verifyNodeTypeVsComponent != JanusGraphOperationStatus.OK) {
684                 return Either.right(verifyNodeTypeVsComponent);
685             }
686         }
687
688         Either<ImmutablePair<AdditionalInfoParameterData, GraphEdge>, JanusGraphOperationStatus> getResult = janusGraphGenericDao
689             .getChild(UniqueIdBuilder.getKeyByNodeType(nodeType), componentId, GraphEdgeLabels.ADDITIONAL_INFORMATION,
690                 NodeTypeEnum.AdditionalInfoParameters, AdditionalInfoParameterData.class);
691
692         if (getResult.isRight()) {
693             JanusGraphOperationStatus status = getResult.right().value();
694             if (status != JanusGraphOperationStatus.NOT_FOUND) {
695                 BeEcompErrorManager.getInstance().logBeFailedRetrieveNodeError("GetAdditionnalInformationParameters", ADDITIONAL_INFORMATION_OF + nodeType.getName() + " " + componentId, String.valueOf(status));
696             }
697             return Either.right(status);
698         }
699
700         ImmutablePair<AdditionalInfoParameterData, GraphEdge> immutablePair = getResult.left().value();
701         AdditionalInfoParameterData parameterData = immutablePair.getLeft();
702         Map<String, String> parameters = parameterData.getParameters();
703         Map<String, String> idToKey = parameterData.getIdToKey();
704
705         AdditionalInformationDefinition informationDefinition = createInformationDefinitionFromNode(componentId, parameters, idToKey, parameterData);
706
707         return Either.left(informationDefinition);
708
709     }
710
711     @Override
712     public Either<AdditionalInformationDefinition, StorageOperationStatus> getAllAdditionalInformationParameters(NodeTypeEnum nodeType, String resourceId, boolean ignoreVerification, boolean inTransaction) {
713
714         Either<AdditionalInformationDefinition, StorageOperationStatus> result = null;
715
716         try {
717
718             Either<AdditionalInformationDefinition, JanusGraphOperationStatus> either = this.getAllAdditionalInformationParameters(nodeType, resourceId, ignoreVerification);
719
720             if (either.isRight()) {
721                 JanusGraphOperationStatus status = either.right().value();
722                 result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
723             } else {
724                 AdditionalInformationDefinition additionalInformationDefinition = either.left().value();
725                 result = Either.left(additionalInformationDefinition);
726             }
727
728             return result;
729
730         } finally {
731             commitOrRollback(inTransaction, result);
732         }
733
734     }
735
736     private void commitOrRollback(boolean inTransaction, Either<? extends Object, StorageOperationStatus> result) {
737
738         if (!inTransaction) {
739             if (result == null || result.isRight()) {
740                 log.error(GOING_TO_EXECUTE_ROLLBACK_ON_GRAPH);
741                 janusGraphGenericDao.rollback();
742             } else {
743                 log.debug(GOING_TO_EXECUTE_COMMIT_ON_GRAPH);
744                 janusGraphGenericDao.commit();
745             }
746         }
747     }
748     
749
750     @Override
751     public Either<AdditionalInfoParameterInfo, StorageOperationStatus> getAdditionalInformationParameter(NodeTypeEnum nodeType, String resourceId, String id, boolean inTransaction) {
752
753         Either<AdditionalInfoParameterInfo, StorageOperationStatus> result = null;
754
755         try {
756
757             Either<AdditionalInfoParameterInfo, JanusGraphOperationStatus> either = this.getAdditionalInformationParameter(nodeType, resourceId, id);
758
759             if (either.isRight()) {
760                 log.error("Failed to fetch additional information property with id {} of component {}", id, resourceId);
761                 result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(either.right().value()));
762             } else {
763                 AdditionalInfoParameterInfo additionalInformationDefinition = either.left().value();
764                 result = Either.left(additionalInformationDefinition);
765             }
766
767             return result;
768
769         } finally {
770             commitOrRollback(inTransaction, result);
771         }
772     }
773
774     @Override
775     public Either<AdditionalInformationDefinition, StorageOperationStatus> deleteAllAdditionalInformationParameters(NodeTypeEnum nodeType, String resourceId, boolean inTransaction) {
776
777         Either<AdditionalInformationDefinition, StorageOperationStatus> result = null;
778
779         try {
780
781             Either<ImmutablePair<AdditionalInfoParameterData, GraphEdge>, JanusGraphOperationStatus> getResult = janusGraphGenericDao
782                 .getChild(UniqueIdBuilder.getKeyByNodeType(nodeType), resourceId, GraphEdgeLabels.ADDITIONAL_INFORMATION,
783                     NodeTypeEnum.AdditionalInfoParameters, AdditionalInfoParameterData.class);
784
785             if (getResult.isRight()) {
786                 JanusGraphOperationStatus status = getResult.right().value();
787                 if (status == JanusGraphOperationStatus.NOT_FOUND) {
788                     return Either.right(StorageOperationStatus.OK);
789                 } else {
790                     BeEcompErrorManager.getInstance().logBeFailedDeleteNodeError("DeleteAdditionalInformationNode", ADDITIONAL_INFORMATION_OF + nodeType.getName() + " " + resourceId, String.valueOf(status));
791                     result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
792                 }
793                 return result;
794             }
795
796             ImmutablePair<AdditionalInfoParameterData, GraphEdge> value = getResult.left().value();
797             AdditionalInfoParameterData parameterData = value.getLeft();
798
799             Either<AdditionalInfoParameterData, JanusGraphOperationStatus> deleteNodeRes = janusGraphGenericDao
800                 .deleteNode(parameterData, AdditionalInfoParameterData.class);
801             if (deleteNodeRes.isRight()) {
802                 JanusGraphOperationStatus status = getResult.right().value();
803                 BeEcompErrorManager.getInstance().logBeFailedDeleteNodeError("DeleteAdditionalInformationNode", (String) parameterData.getUniqueId(), String.valueOf(status));
804                 result = Either.right(DaoStatusConverter.convertJanusGraphStatusToStorageStatus(status));
805                 return result;
806             }
807
808             AdditionalInformationDefinition informationDefinition = convertAdditionalInformationDataToDefinition(deleteNodeRes.left().value(), resourceId);
809
810             result = Either.left(informationDefinition);
811
812             return result;
813
814         } finally {
815             commitOrRollback(inTransaction, result);
816         }
817     }
818
819     private JanusGraphOperationStatus verifyNodeTypeVsComponent(NodeTypeEnum nodeType, String componentId) {
820         Either<JanusGraphVertex, JanusGraphOperationStatus> vertexByProperty = janusGraphGenericDao
821             .getVertexByProperty(UniqueIdBuilder.getKeyByNodeType(nodeType), componentId);
822         if (vertexByProperty.isRight()) {
823             JanusGraphOperationStatus status = vertexByProperty.right().value();
824             if (status == JanusGraphOperationStatus.NOT_FOUND) {
825                 status = JanusGraphOperationStatus.INVALID_ID;
826             }
827             return status;
828         } else {
829             Vertex v = vertexByProperty.left().value();
830             String label = (String) v.property(GraphPropertiesDictionary.LABEL.getProperty()).value();
831             if (label != null) {
832                 if (!label.equals(nodeType.getName())) {
833                     log.debug("The node type {} is not appropriate to component {}", nodeType, componentId);
834                     return JanusGraphOperationStatus.INVALID_ID;
835                 }
836             } else {
837                 log.debug("The node type {}  with id {} does not have a label property.", nodeType, componentId);
838                 return JanusGraphOperationStatus.INVALID_ID;
839             }
840         }
841         return JanusGraphOperationStatus.OK;
842     }
843
844 }