Policies import when import VSP
[sdc.git] / catalog-be / src / main / java / org / openecomp / sdc / be / components / impl / PolicyBusinessLogic.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * SDC
4  * ================================================================================
5  * Copyright (C) 2019 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.components.impl;
22
23 import fj.data.Either;
24 import java.util.ArrayList;
25 import java.util.Collections;
26 import java.util.EnumMap;
27 import org.apache.commons.collections.CollectionUtils;
28 import org.apache.commons.collections.MapUtils;
29 import org.apache.commons.lang.StringUtils;
30 import org.openecomp.sdc.be.components.impl.exceptions.ByActionStatusComponentException;
31 import org.openecomp.sdc.be.components.impl.exceptions.ComponentException;
32 import org.openecomp.sdc.be.components.property.PropertyDeclarationOrchestrator;
33 import org.openecomp.sdc.be.components.validation.PolicyUtils;
34 import org.openecomp.sdc.be.dao.api.ActionStatus;
35 import org.openecomp.sdc.be.datatypes.elements.GetPolicyValueDataDefinition;
36 import org.openecomp.sdc.be.datatypes.elements.PolicyTargetType;
37 import org.openecomp.sdc.be.datatypes.elements.PropertyDataDefinition;
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.PromoteVersionEnum;
41 import org.openecomp.sdc.be.model.Component;
42 import org.openecomp.sdc.be.model.ComponentInstInputsMap;
43 import org.openecomp.sdc.be.model.ComponentInstance;
44 import org.openecomp.sdc.be.model.ComponentInstanceProperty;
45 import org.openecomp.sdc.be.model.ComponentParametersView;
46 import org.openecomp.sdc.be.model.PolicyDefinition;
47 import org.openecomp.sdc.be.model.PolicyTypeDefinition;
48 import org.openecomp.sdc.be.model.Resource;
49 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.ArtifactsOperations;
50 import org.openecomp.sdc.be.model.jsonjanusgraph.operations.InterfaceOperation;
51 import org.openecomp.sdc.be.model.operations.api.IElementOperation;
52 import org.openecomp.sdc.be.model.operations.api.IGroupInstanceOperation;
53 import org.openecomp.sdc.be.model.operations.api.IGroupOperation;
54 import org.openecomp.sdc.be.model.operations.api.IGroupTypeOperation;
55 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
56 import org.openecomp.sdc.be.model.operations.impl.InterfaceLifecycleOperation;
57 import org.openecomp.sdc.common.datastructure.Wrapper;
58 import org.openecomp.sdc.common.log.elements.LoggerSupportability;
59 import org.openecomp.sdc.common.log.enums.LoggerSupportabilityActions;
60 import org.openecomp.sdc.common.log.enums.StatusCode;
61 import org.openecomp.sdc.common.log.wrappers.Logger;
62 import org.openecomp.sdc.exception.ResponseFormat;
63 import org.springframework.beans.factory.annotation.Autowired;
64
65 import java.util.Arrays;
66 import java.util.HashMap;
67 import java.util.List;
68 import java.util.Map;
69 import java.util.Optional;
70 import java.util.Set;
71 import java.util.function.Function;
72 import java.util.stream.Collectors;
73
74 import static java.util.stream.Collectors.toMap;
75 import static org.openecomp.sdc.be.components.validation.PolicyUtils.getExcludedPolicyTypesByComponent;
76 import static org.openecomp.sdc.be.components.validation.PolicyUtils.getNextPolicyCounter;
77 import static org.openecomp.sdc.be.components.validation.PolicyUtils.validatePolicyFields;
78
79 /**
80  * Provides specified business logic to create, retrieve, update, delete a policy
81  */
82 @org.springframework.stereotype.Component("policyBusinessLogic")
83 public class PolicyBusinessLogic extends BaseBusinessLogic {
84
85     private static final String FAILED_TO_VALIDATE_COMPONENT = "#{} - failed to validate the component {} before policy processing. ";
86     private static final String DECLARE_PROPERTIES_TO_POLICIES = "declare properties to policies";
87     private static final Logger log = Logger.getLogger(PolicyBusinessLogic.class);
88     private static final LoggerSupportability loggerSupportability= LoggerSupportability.getLogger(PolicyBusinessLogic.class.getName());
89
90     private PropertyDeclarationOrchestrator propertyDeclarationOrchestrator;
91
92     @Autowired
93     public PolicyBusinessLogic(IElementOperation elementDao,
94         IGroupOperation groupOperation,
95         IGroupInstanceOperation groupInstanceOperation,
96         IGroupTypeOperation groupTypeOperation,
97         InterfaceOperation interfaceOperation,
98         InterfaceLifecycleOperation interfaceLifecycleTypeOperation,
99         ArtifactsOperations artifactToscaOperation) {
100         super(elementDao, groupOperation, groupInstanceOperation, groupTypeOperation,
101             interfaceOperation, interfaceLifecycleTypeOperation, artifactToscaOperation);
102     }
103
104     @Autowired
105     public void setPropertyDeclarationOrchestrator(PropertyDeclarationOrchestrator propertyDeclarationOrchestrator) {
106         this.propertyDeclarationOrchestrator = propertyDeclarationOrchestrator;
107     }
108
109     /**
110      * Adds the newly created policy of the specified type to the component
111      *
112      * @param componentType  the type of the component
113      * @param componentId    the id of the component which the policy resides under
114      * @param policyTypeName the name of the policy type
115      * @param userId         the user creator id
116      * @param shouldLock     the flag defining if the component should be locked
117      * @return a policy or an error in a response format
118      */
119
120     public PolicyDefinition createPolicy(ComponentTypeEnum componentType, String componentId, String policyTypeName, String userId, boolean shouldLock) {
121
122         log.trace("#createPolicy - starting to create policy of the type {} on the component {}. ", policyTypeName, componentId);
123         Component component = null;
124         boolean failed = false;
125         try {
126             component = validateAndLockComponentAndUserBeforeWriteOperation(componentType, componentId, userId, shouldLock);
127             return createPolicy(policyTypeName, component);
128         }catch (ComponentException e){
129             failed = true;
130             throw e;
131         }finally {
132             unlockComponent(shouldLock, failed, component);
133         }
134     }
135
136     public Map<String, PolicyDefinition> createPoliciesFromParsedCsar(Component component,
137             final Map<String, PolicyDefinition> incomingPolicyDefinitions) {
138         if (MapUtils.isEmpty(incomingPolicyDefinitions)) {
139             return Collections.emptyMap();
140         }
141         Map<String, PolicyDefinition> createdPolicies = new HashMap<>();
142         for (Map.Entry<String, PolicyDefinition> policyEntry : incomingPolicyDefinitions.entrySet()) {
143             PolicyDefinition incomingPolicyDefinition = policyEntry.getValue();
144             String policyName = incomingPolicyDefinition.getName();
145             log.trace("Going to create policy {}", incomingPolicyDefinition);
146             loggerSupportability.log(LoggerSupportabilityActions.CREATE_GROUP_POLICY,component.getComponentMetadataForSupportLog(),
147                     StatusCode.STARTED,"Start to create policy: {} for component {}", policyName, component.getName());
148             String policyType = incomingPolicyDefinition.getType();
149             if (StringUtils.isEmpty(policyType)) {
150                 log.debug("Policy type '{}' for policy '{}' not found.", policyType, policyName);
151                 throw new ByActionStatusComponentException(ActionStatus.POLICY_MISSING_POLICY_TYPE, policyName);
152             }
153             // create policyDefinition
154             String policyTypeName = incomingPolicyDefinition.getPolicyTypeName();
155             PolicyDefinition createdPolicyDefinition = createPolicy(policyTypeName, component);
156             // set isFromCsar
157             createdPolicyDefinition.setToscaPresentationValue(JsonPresentationFields.IS_FROM_CSAR, true);
158             // link policy to component
159             component.addPolicy(createdPolicyDefinition);
160             // process targets
161             Map<PolicyTargetType, List<String>> policyTargets = incomingPolicyDefinition.getTargets();
162             createdPolicyDefinition = setUpdatePolicyTargets(component, createdPolicyDefinition, policyTargets);
163             // process policy properties
164             List<PropertyDataDefinition> properties = incomingPolicyDefinition.getProperties();
165             createdPolicyDefinition = setUpdatePolicyProperties(component, createdPolicyDefinition, properties);
166             createdPolicies.put(policyName, createdPolicyDefinition);
167             loggerSupportability.log(LoggerSupportabilityActions.CREATE_POLICIES,component.getComponentMetadataForSupportLog(), StatusCode.COMPLETE,"policy {} has been created ", policyName);
168         }
169         return createdPolicies;
170     }
171
172     private PolicyDefinition setUpdatePolicyProperties(Component component, PolicyDefinition policyDefinition, List<PropertyDataDefinition> properties) {
173         if (CollectionUtils.isNotEmpty(properties)) {
174             PropertyDataDefinition[] propertiesArray = properties.toArray(new PropertyDataDefinition[properties.size()]);
175             List<PropertyDataDefinition> updatedPropertiesList = setComponentValidateUpdatePolicyProperties(
176                     policyDefinition.getUniqueId(),
177                     propertiesArray,
178                     component
179             );
180             policyDefinition.setProperties(updatedPropertiesList);
181         }
182         return policyDefinition;
183     }
184
185     private PolicyDefinition setUpdatePolicyTargets(Component component, PolicyDefinition policyDefinition,
186             Map<PolicyTargetType, List<String>> targets) {
187         if (MapUtils.isEmpty(targets)) {
188             return policyDefinition;
189         }
190         List<String> targetsToUpdate = targets.get(PolicyTargetType.COMPONENT_INSTANCES);
191         if (CollectionUtils.isEmpty(targetsToUpdate)) {
192             return policyDefinition;
193         }
194         // update targets to uniqueIds of respective component instance
195         List<String> targetsUniqueIds = new ArrayList<>();
196         for (String targetName : targetsToUpdate) {
197             Optional<ComponentInstance> componentInstance = component.getComponentInstanceByName(targetName);
198             String componentUniqueId = componentInstance
199                                                .orElseThrow(
200                                                        () -> new ByActionStatusComponentException(
201                                                                ActionStatus.COMPONENT_INSTANCE_NOT_FOUND
202                                                        )
203                                                )
204                                                .getUniqueId();
205             targetsUniqueIds.add(componentUniqueId);
206         }
207         EnumMap<PolicyTargetType, List<String>> updatedTargets = new EnumMap<>(PolicyTargetType.class);
208         updatedTargets.put(PolicyTargetType.COMPONENT_INSTANCES, targetsUniqueIds);
209         policyDefinition.setTargets(updatedTargets);
210         policyDefinition = validateAndUpdatePolicyTargets(component, policyDefinition.getUniqueId(),
211                 policyDefinition.getTargets());
212         return policyDefinition;
213     }
214
215     /*public Either<PolicyDefinition, ResponseFormat> createPolicy(ComponentTypeEnum componentType, String componentId, String policyTypeName, String userId, boolean shouldLock) {
216
217         Either<PolicyDefinition, ResponseFormat> result = null;
218         log.trace("#createPolicy - starting to create policy of the type {} on the component {}. ", policyTypeName, componentId);
219         Wrapper<Component> component = new Wrapper<>();
220         try {
221             result = validateAndLockComponentAndUserBeforeWriteOperation(componentType, componentId, userId, shouldLock)
222                     .left()
223                     .bind(c -> {
224                         component.setInnerElement(c);
225                         return createPolicy(policyTypeName, c);
226                     });
227         } catch (Exception e) {
228             if (ComponentException.class.equals(e.getClass())) {
229                 throw e;
230             }
231             log.error("#createPolicy - the exception  occurred upon creation of a policy of the type {} for the component {}: ", policyTypeName, componentId, e);
232             result = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
233         } finally {
234             //TODO Andrey result = boolean
235             unlockComponent(shouldLock, result, component);
236         }
237         return result;
238     }*/
239
240     public Either<List<PolicyDefinition>, ResponseFormat> getPoliciesList(ComponentTypeEnum componentType, String componentId, String userId) {
241         Either<List<PolicyDefinition>, ResponseFormat> result;
242         log.trace("#getPolicies - starting to retrieve policies of component {}. ", componentId);
243         try {
244             Component component = validateContainerComponentAndUserBeforeReadOperation(componentType, componentId, userId);
245             result = Either.left(component.resolvePoliciesList());
246         } catch (Exception e) {
247             log.error("#getPolicy - the exception occurred upon retrieving policies list of component {}: ", componentId, e);
248             result = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
249         }
250         return result;
251     }
252
253
254
255     /**
256      * Retrieves the policy of the component by UniqueId
257      *
258      * @param componentType the type of the component
259      * @param componentId   the ID of the component
260      * @param policyId      the ID of the policy
261      * @param userId        the ID of the user
262      * @return either policy or error response
263      */
264     public PolicyDefinition getPolicy(ComponentTypeEnum componentType, String componentId, String policyId, String userId) {
265         log.trace("#getPolicy - starting to retrieve the policy {} of the component {}. ", policyId, componentId);
266         Component component = validateContainerComponentAndUserBeforeReadOperation(componentType, componentId, userId);
267         return getPolicyById(component, policyId);
268     }
269
270     /*public Either<PolicyDefinition, ResponseFormat> getPolicy(ComponentTypeEnum componentType, String componentId, String policyId, String userId) {
271         Either<PolicyDefinition, ResponseFormat> result;
272         log.trace("#getPolicy - starting to retrieve the policy {} of the component {}. ", policyId, componentId);
273         try {
274             result = validateContainerComponentAndUserBeforeReadOperation(componentType, componentId, userId)
275                     .left()
276                     .bind(c -> getPolicyById(c, policyId));
277         } catch (Exception e) {
278             log.error("#getPolicy - the exception occurred upon retrieving the policy {} of the component {}: ", policyId, componentId, e);
279             result = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
280         }
281         return result;
282     }*/
283
284     /**
285      * Updates the policy of the component
286      *
287      * @param componentType the type of the component
288      * @param componentId   the id of the component which the policy resides under
289      * @param policy        the policy to update
290      * @param userId        the user modifier id
291      * @param shouldLock    the flag defining if the component should be locked
292      * @return a policy or an error in a response format
293      */
294     public PolicyDefinition updatePolicy(ComponentTypeEnum componentType, String componentId, PolicyDefinition policy, String userId, boolean shouldLock) {
295         Component component = null;
296         boolean failed = false;
297         log.trace("#updatePolicy - starting to update the policy {} on the component {}. ", policy.getUniqueId(), componentId);
298         try {
299             component = validateAndLockComponentAndUserBeforeWriteOperation(componentType, componentId, userId, shouldLock);
300             return validateAndUpdatePolicy(component, policy);
301         } catch (ComponentException e) {
302             failed = true;
303             log.error("#updatePolicy - the exception occurred upon update of a policy of the type {} for the component {}: ", policy.getUniqueId(), componentId, e);
304             throw e;
305         } finally {
306             //TODO Andrey result = boolean
307             unlockComponent(shouldLock, failed, component);
308         }
309     }
310
311
312     /*public Either<PolicyDefinition, ResponseFormat> updatePolicy(ComponentTypeEnum componentType, String componentId, PolicyDefinition policy, String userId, boolean shouldLock) {
313         Either<PolicyDefinition, ResponseFormat> result = null;
314         log.trace("#updatePolicy - starting to update the policy {} on the component {}. ", policy.getUniqueId(), componentId);
315         Wrapper<Component> component = new Wrapper<>();
316         try {
317             result = validateAndLockComponentAndUserBeforeWriteOperation(componentType, componentId, userId, shouldLock)
318                     .left()
319                     .bind(c -> {
320                         component.setInnerElement(c);
321                         return validateAndUpdatePolicy(c, policy);
322                     });
323         } catch (Exception e) {
324             log.error("#updatePolicy - the exception occurred upon update of a policy of the type {} for the component {}: ", policy.getUniqueId(), componentId, e);
325             result = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
326         } finally {
327             //TODO Andrey result = boolean
328             unlockComponent(shouldLock, result, component);
329         }
330         return result;
331     }*/
332
333     /**
334      * Deletes the policy from the component
335      *
336      * @param componentType the type of the component
337      * @param componentId   the id of the component which the policy resides under
338      * @param policyId      the id of the policy which its properties to return
339      * @param userId        the user modifier id
340      * @param shouldLock    the flag defining if the component should be locked
341      * @return a policy or an error in a response format
342      */
343     public PolicyDefinition deletePolicy(ComponentTypeEnum componentType, String componentId, String policyId, String userId, boolean shouldLock) {
344         PolicyDefinition result = null;
345         log.trace("#deletePolicy - starting to update the policy {} on the component {}. ", policyId, componentId);
346         Component component = null;
347         boolean failed= false;
348         try {
349             component = validateAndLockComponentAndUserBeforeWriteOperation(componentType, componentId, userId, shouldLock);
350             return deletePolicy(component, policyId);
351         } catch (ComponentException e) {
352             failed = true;
353             log.error("#deletePolicy - the exception occurred upon update of a policy of the type {} for the component {}: ", policyId, componentId, e);
354             throw e;
355         } finally {
356             unlockComponent(shouldLock, failed, component);
357         }
358     }
359
360
361     /*public Either<PolicyDefinition, ResponseFormat> deletePolicy(ComponentTypeEnum componentType, String componentId, String policyId, String userId, boolean shouldLock) {
362         Either<PolicyDefinition, ResponseFormat> result = null;
363         log.trace("#deletePolicy - starting to update the policy {} on the component {}. ", policyId, componentId);
364         Wrapper<Component> component = new Wrapper<>();
365         try {
366             Either<Component, ResponseFormat> componentEither =
367                     validateAndLockComponentAndUserBeforeWriteOperation(componentType, componentId, userId, shouldLock);
368             if (componentEither.isRight()) {
369                 return Either.right(componentEither.right().value());
370             }
371
372             ComponentParametersView componentParametersView = new ComponentParametersView();
373             componentParametersView.disableAll();
374             componentParametersView.setIgnoreComponentInstances(false);
375             componentParametersView.setIgnoreComponentInstancesProperties(false);
376             componentParametersView.setIgnorePolicies(false);
377             componentParametersView.setIgnoreProperties(false);
378
379             Either<Component, StorageOperationStatus> componentWithFilters =
380                     toscaOperationFacade.getToscaElement(componentId, componentParametersView);
381             if (componentWithFilters.isRight()) {
382                 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(componentWithFilters.right().value())));
383             }
384
385             Component containerComponent = componentWithFilters.left().value();
386             component.setInnerElement(containerComponent);
387             result = deletePolicy(containerComponent, policyId);
388
389             if(result.isRight()) {
390                 log.error("#deletePolicy - could not delete policy of the type {} for the component {}: ", policyId, componentId);
391                 return result;
392             }
393
394             PolicyDefinition policyToDelete = result.left().value();
395
396             StorageOperationStatus storageOperationStatus = propertyDeclarationOrchestrator.unDeclarePropertiesAsPolicies(
397                     containerComponent, policyToDelete);
398             if (storageOperationStatus != StorageOperationStatus.OK) {
399                 log.debug("Component id: {} update properties declared as policy for policy id: {} failed", componentId, policyId);
400                 return Either.right(componentsUtils.getResponseFormat(componentsUtils
401                                                                                       .convertFromStorageResponse(storageOperationStatus), containerComponent.getName()));
402             }
403
404             return result;
405         } catch (Exception e) {
406             log.error("#deletePolicy - the exception occurred upon update of a policy of the type {} for the component {}: ", policyId, componentId, e);
407             return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR, e.getMessage()));
408         } finally {
409             unlockComponent(shouldLock, result, component);
410         }
411     }*/
412
413     public Either<PolicyDefinition, ResponseFormat> undeclarePolicy(ComponentTypeEnum componentType, String componentId, String policyId, String userId, boolean shouldLock) {
414         Either<PolicyDefinition, ResponseFormat> result = null;
415         log.trace("#undeclarePolicy - starting to undeclare policy {} on component {}. ", policyId, componentId);
416         Wrapper<Component> component = new Wrapper<>();
417         try {
418             validateAndLockComponentAndUserBeforeWriteOperation(componentType, componentId, userId, shouldLock);
419
420             ComponentParametersView componentParametersView = new ComponentParametersView();
421             componentParametersView.disableAll();
422             componentParametersView.setIgnoreComponentInstances(false);
423             componentParametersView.setIgnoreComponentInstancesProperties(false);
424             componentParametersView.setIgnorePolicies(false);
425
426             Either<Component, StorageOperationStatus> componentWithFilters =
427                     toscaOperationFacade.getToscaElement(componentId, componentParametersView);
428             if (componentWithFilters.isRight()) {
429                 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(componentWithFilters.right().value())));
430             }
431
432             Component containerComponent = componentWithFilters.left().value();
433
434             Optional<PolicyDefinition> policyCandidate = getPolicyForUndeclaration(policyId, containerComponent);
435             if(policyCandidate.isPresent()) {
436                 result = undeclarePolicy(policyCandidate.get(), containerComponent);
437             }
438
439             return result;
440     }catch (Exception e) {
441             log.error("#undeclarePolicy - the exception occurred upon update of a policy of type {} for component {}: ", policyId, componentId, e);
442             return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR, e.getMessage()));
443         } finally {
444             if (result == null || result.isRight()){
445                 unlockComponent(shouldLock, true, component);
446             } else {
447                 unlockComponent(shouldLock, false, component);
448             }
449         }
450     }
451
452         private Either<PolicyDefinition, ResponseFormat> undeclarePolicy(PolicyDefinition policyDefinition, Component containerComponent) {
453             StorageOperationStatus undeclareStatus = propertyDeclarationOrchestrator
454                     .unDeclarePropertiesAsPolicies(containerComponent, policyDefinition);
455             if(undeclareStatus != StorageOperationStatus.OK){
456                 return Either.right(componentsUtils.getResponseFormat(undeclareStatus));
457             } else {
458                 return Either.left(policyDefinition);
459             }
460         }
461
462
463         private Optional<PolicyDefinition> getPolicyForUndeclaration(String policyId, Component component) {
464             Map<String, PolicyDefinition> policies = component.getPolicies();
465             if(MapUtils.isNotEmpty(policies) && policies.containsKey(policyId)) {
466                 return Optional.of(policies.get(policyId));
467             }
468
469             Map<String, List<ComponentInstanceProperty>> componentInstancesProperties =
470                     MapUtils.isEmpty(component.getComponentInstancesProperties()) ? new HashMap<>() : component.getComponentInstancesProperties();
471
472             for(Map.Entry<String, List<ComponentInstanceProperty>> instancePropertyEntry : componentInstancesProperties.entrySet()) {
473                 Optional<ComponentInstanceProperty> propertyCandidate = getPropertyForDeclaredPolicy(policyId, instancePropertyEntry.getValue());
474
475                 if(propertyCandidate.isPresent()) {
476                     return Optional.of(
477                             PolicyUtils.getDeclaredPolicyDefinition(instancePropertyEntry.getKey(), propertyCandidate.get()));
478                 }
479             }
480
481             return Optional.empty();
482         }
483
484         private Optional<ComponentInstanceProperty> getPropertyForDeclaredPolicy(String policyId, List<ComponentInstanceProperty> componentInstanceProperties) {
485             for(ComponentInstanceProperty property : componentInstanceProperties) {
486                 Optional<GetPolicyValueDataDefinition> getPolicyCandidate = property.safeGetGetPolicyValues().stream()
487                         .filter(getPolicyValue -> getPolicyValue.getPolicyId()
488                                 .equals(policyId))
489                         .findAny();
490
491                 if(getPolicyCandidate.isPresent()) {
492                     return Optional.of(property);
493                 }
494             }
495
496             return Optional.empty();
497         }
498
499
500         public PolicyDefinition updatePolicyTargets(ComponentTypeEnum componentTypeEnum, String componentId, String policyId, Map<PolicyTargetType, List<String>> targets, String userId) {
501
502         Either<PolicyDefinition, ResponseFormat> result = null;
503         log.debug("updating the policy id {} targets with the components {}. ", policyId, componentId);
504         boolean failed = false;
505         try {
506             //not right error response
507             Component component = validateAndLockComponentAndUserBeforeWriteOperation(componentTypeEnum, componentId, userId, true);
508             return validateAndUpdatePolicyTargets(component, policyId, targets);
509         }catch (ComponentException e){
510             failed = true;
511             throw e;
512         }finally {
513             unlockComponentById(failed, componentId);
514         }
515     }
516
517     private PolicyDefinition validateAndUpdatePolicyTargets(Component component, String policyId, Map<PolicyTargetType, List<String>> targets) {
518         validateTargetsExistAndTypesCorrect(component.getUniqueId(), targets);
519         return updateTargets(component.getUniqueId(), component.getPolicyById(policyId), targets, policyId);
520     }
521
522     private Component validateTargetsExistAndTypesCorrect(String componentId, Map<PolicyTargetType, List<String>> targets) {
523         Either<Component, StorageOperationStatus> componentEither = toscaOperationFacade.getToscaFullElement(componentId);
524         if (componentEither.isRight()) {
525             throw new ByActionStatusComponentException(componentsUtils.convertFromStorageResponse(componentEither.right().value()));
526         }
527         Component parentComponent = componentEither.left().value();
528         return validateTargetExists(parentComponent, targets.entrySet());
529     }
530
531
532     private Component validateTargetExists(Component parentComponent, Set<Map.Entry<PolicyTargetType, List<String>>> entries) {
533         for (Map.Entry<PolicyTargetType, List<String>> entry : entries) {
534             checkTargetNotExistOnComponentByType(parentComponent, entry);
535         }
536         return parentComponent;
537     }
538
539     private Component checkTargetNotExistOnComponentByType(Component parentComponent, Map.Entry<PolicyTargetType, List<String>> targetEntry) {
540
541         for (String id : targetEntry.getValue()) {
542             if (checkNotPresenceInComponentByType(parentComponent, id, targetEntry.getKey().getName())) {
543                 throw new ByActionStatusComponentException(ActionStatus.POLICY_TARGET_DOES_NOT_EXIST, id);
544             }
545         }
546         return parentComponent;
547     }
548
549     private boolean checkNotPresenceInComponentByType(Component parentComponent, String uniqueId, String type) {
550         if (type.equalsIgnoreCase(PolicyTargetType.GROUPS.getName()) && parentComponent.getGroups() != null) {
551             return !parentComponent.getGroupById(uniqueId).isPresent();
552         } else if (type.equalsIgnoreCase(PolicyTargetType.COMPONENT_INSTANCES.getName()) && parentComponent.getComponentInstances() != null) {
553             return !parentComponent.getComponentInstanceById(uniqueId).isPresent();
554         }
555         return true;
556     }
557
558     private PolicyDefinition setPolicyTargets(PolicyDefinition policyDefinition, Map<PolicyTargetType, List<String>> targets) {
559         policyDefinition.setTargets(targets);
560         return policyDefinition;
561     }
562
563
564     /**
565      * @param componentType the type of the component
566      * @param componentId   the id of the component which the policy resides under
567      * @param policyId      the id of the policy which its properties to return
568      * @param userId        the user id
569      * @return a list of policy properties or an error in a response format
570      */
571     public List<PropertyDataDefinition> getPolicyProperties(ComponentTypeEnum componentType, String componentId, String policyId, String userId) {
572         log.debug("#getPolicyProperties - fetching policy properties for component {} and policy {}", componentId, policyId);
573         try {
574             Component component = validateContainerComponentAndUserBeforeReadOperation(componentType, componentId, userId);
575             return getPolicyById(component, policyId).getProperties();
576         } finally {
577             janusGraphDao.commit();
578         }
579     }
580
581     /*public Either<List<PropertyDataDefinition>, ResponseFormat> getPolicyProperties(ComponentTypeEnum componentType, String componentId, String policyId, String userId) {
582         log.debug("#getPolicyProperties - fetching policy properties for component {} and policy {}", componentId, policyId);
583         try {
584             return validateContainerComponentAndUserBeforeReadOperation(componentType, componentId, userId)
585                     .left()
586                     .bind(cmpt -> getPolicyById(cmpt, policyId)).left().map(PolicyDataDefinition::getProperties);
587         } finally {
588             janusGraphDao.commit();
589         }
590     }*/
591
592     /**
593      * Updates the policy properties of the component
594      *
595      * @param componentType the type of the component
596      * @param componentId   the id of the component which the policy resides under
597      * @param policyId      the id of the policy which its properties to return
598      * @param properties    a list of policy properties containing updated values
599      * @param userId        the user modifier id
600      * @param shouldLock    the flag defining if the component should be locked
601      * @return a list of policy properties or anerrorin a response format
602      */
603     public List<PropertyDataDefinition> updatePolicyProperties(ComponentTypeEnum componentType, String componentId, String policyId, PropertyDataDefinition[] properties, String userId, boolean shouldLock) {
604         List<PropertyDataDefinition> result;
605         Component component = null;
606         log.trace("#updatePolicyProperties - starting to update properties of the policy {} on the component {}. ", policyId, componentId);
607         boolean failed = true;
608         try {
609             component = validateAndLockComponentAndUserBeforeWriteOperation(componentType, componentId, userId, shouldLock);
610             failed = false;
611             result = setComponentValidateUpdatePolicyProperties(policyId, properties, component);
612         } finally {
613             if (shouldLock && !failed) {
614                 unlockComponent(failed, component);
615             }
616         }
617         return result;
618     }
619
620     @Override
621     public  Either<List<PolicyDefinition>, ResponseFormat> declareProperties(String userId, String componentId,
622             ComponentTypeEnum componentTypeEnum, ComponentInstInputsMap componentInstInputsMap) {
623         return declarePropertiesToPolicies(userId, componentId, componentTypeEnum, componentInstInputsMap, true, false);
624
625     }
626
627     private Either<List<PolicyDefinition>, ResponseFormat> declarePropertiesToPolicies(String userId, String componentId,
628             ComponentTypeEnum componentTypeEnum, ComponentInstInputsMap componentInstInputsMap, boolean shouldLock,
629             boolean inTransaction) {
630         Either<List<PolicyDefinition>, ResponseFormat> result = null;
631         org.openecomp.sdc.be.model.Component component = null;
632
633         try {
634             validateUserExists(userId);
635
636             ComponentParametersView componentParametersView = new ComponentParametersView();
637             componentParametersView.disableAll();
638             componentParametersView.setIgnoreComponentInstances(false);
639             componentParametersView.setIgnoreComponentInstancesProperties(false);
640             componentParametersView.setIgnorePolicies(false);
641             componentParametersView.setIgnoreUsers(false);
642
643             component = validateComponentExists(componentId, componentTypeEnum, componentParametersView);
644
645             if (shouldLock) {
646                 lockComponent(component, DECLARE_PROPERTIES_TO_POLICIES);
647             }
648
649             validateCanWorkOnComponent(component, userId);
650
651             Either<List<PolicyDefinition>, StorageOperationStatus> declarePropertiesEither =
652                     propertyDeclarationOrchestrator.declarePropertiesToPolicies(component, componentInstInputsMap);
653
654             if(declarePropertiesEither.isRight()) {
655                 return Either.right(componentsUtils.getResponseFormat(declarePropertiesEither.right().value()));
656             }
657
658             result = Either.left(declarePropertiesEither.left().value());
659             return result;
660         } finally {
661             if(!inTransaction) {
662                 commitOrRollback(result);
663             }
664             // unlock resource
665             if (shouldLock && component != null) {
666                 graphLockOperation.unlockComponent(componentId, componentTypeEnum.getNodeType());
667             }
668         }
669     }
670
671     private List<PropertyDataDefinition> setComponentValidateUpdatePolicyProperties(String policyId, PropertyDataDefinition[] properties, Component component) {
672         Set<String> updatedPropertyNames = Arrays.stream(properties).map(PropertyDataDefinition::getName).collect(Collectors.toSet());
673
674         PolicyDefinition policyDefinition = validateAndUpdatePolicyProperties(component, policyId, properties);
675         return getFilteredProperties(policyDefinition.getProperties(), updatedPropertyNames);
676     }
677
678     private List<PropertyDataDefinition> getFilteredProperties(List<PropertyDataDefinition> all, Set<String> filtered) {
679         return all.stream().filter(pd -> filtered.contains(pd.getName())).collect(Collectors.toList());
680     }
681
682     private void unlockComponent(boolean shouldLock, boolean result, Component component) {
683         if (shouldLock && component != null) {
684             unlockComponent(result, component);
685         }
686     }
687
688
689     private void unlockComponent(boolean shouldLock, boolean result, Wrapper<Component> component) {
690         if (shouldLock && !component.isEmpty()) {
691             unlockComponent(result, component.getInnerElement());
692         }
693     }
694
695     private PolicyDefinition getPolicyById(Component component, String policyId) {
696         PolicyDefinition policyById = component.getPolicyById(policyId);
697         if (policyById == null) {
698             String cmptId = component.getUniqueId();
699             log.debug("#getPolicyById - policy with id {} does not exist on component with id {}", policyId, cmptId);
700             throw new ByActionStatusComponentException(ActionStatus.POLICY_NOT_FOUND_ON_CONTAINER, policyId, cmptId);
701         }
702         return policyById;
703     }
704
705     private PolicyDefinition createPolicy(String policyTypeName, Component component) {
706         PolicyTypeDefinition policyTypeDefinition = validatePolicyTypeOnCreatePolicy(policyTypeName, component);
707         return addPolicyToComponent(policyTypeDefinition, component);
708     }
709
710     /*private Either<PolicyDefinition, ResponseFormat> createPolicy(String policyTypeName, Component component) {
711         return validatePolicyTypeOnCreatePolicy(policyTypeName, component).left().bind(type -> addPolicyToComponent(type, component));
712     }*/
713
714     private PolicyDefinition addPolicyToComponent(PolicyTypeDefinition policyType, Component component) {
715         Either<PolicyDefinition, StorageOperationStatus> associatePolicyToComponent =
716                 toscaOperationFacade.associatePolicyToComponent(component.getUniqueId(), new PolicyDefinition(policyType), getNextPolicyCounter(component.getPolicies()));
717         if(associatePolicyToComponent.isRight()){
718             throw new ByActionStatusComponentException(componentsUtils.convertFromStorageResponse(associatePolicyToComponent.right().value()));
719         }
720         return associatePolicyToComponent.left().value();
721     }
722
723     /*private Either<PolicyDefinition, ResponseFormat> addPolicyToComponent(PolicyTypeDefinition policyType, Component component) {
724         return toscaOperationFacade.associatePolicyToComponent(component.getUniqueId(), new PolicyDefinition(policyType), getNextPolicyCounter(component.getPolicies()))
725                 .either(Either::left, r -> Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(r))));
726     }*/
727
728     private PolicyTypeDefinition validatePolicyTypeOnCreatePolicy(String policyTypeName, Component component) {
729         Either<PolicyTypeDefinition, StorageOperationStatus> latestPolicyTypeByType = policyTypeOperation.getLatestPolicyTypeByType(policyTypeName);
730         if(latestPolicyTypeByType.isRight()){
731             throw new ByActionStatusComponentException(componentsUtils.convertFromStorageResponse(latestPolicyTypeByType.right().value()));
732         }
733         return validatePolicyTypeNotExcluded(latestPolicyTypeByType.left().value(), component);
734     }
735
736     /*private Either<PolicyTypeDefinition, ResponseFormat> validatePolicyTypeOnCreatePolicy(String policyTypeName, Component component) {
737         return policyTypeOperation.getLatestPolicyTypeByType(policyTypeName)
738                 .either(l -> validatePolicyTypeNotExcluded(l, component), r -> Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(r))));
739     }*/
740
741     private PolicyTypeDefinition validatePolicyTypeNotExcluded(PolicyTypeDefinition policyType, Component component) {
742         if (getExcludedPolicyTypesByComponent(component).contains(policyType.getType())) {
743             throw new ByActionStatusComponentException(ActionStatus.EXCLUDED_POLICY_TYPE, policyType.getType(), getComponentOrResourceTypeName(component));
744         }
745         return policyType;
746     }
747
748     private String getComponentOrResourceTypeName(Component component) {
749         return component.getComponentType() == ComponentTypeEnum.SERVICE ? ComponentTypeEnum.SERVICE.name() : ((Resource) component).getResourceType().name();
750     }
751
752     private Component validateAndLockComponentAndUserBeforeWriteOperation(ComponentTypeEnum componentType, String componentId, String userId, boolean shouldLock) {
753         Component component = validateContainerComponentAndUserBeforeReadOperation(componentType, componentId, userId);
754         validateComponentIsTopologyTemplate(component);
755         validateCanWorkOnComponent(component, userId);
756         lockComponent(component, shouldLock, "policyWritingOperation");
757         return component;
758     }
759
760     /*private Either<Component, ResponseFormat> validateAndLockComponentAndUserBeforeWriteOperation(ComponentTypeEnum componentType, String componentId, String userId, boolean shouldLock) {
761         Wrapper<Component> component = new Wrapper<>();
762         return validateContainerComponentAndUserBeforeReadOperation(componentType, componentId, userId)
763                 .left()
764                 .bind(this::validateComponentIsTopologyTemplate)
765                 .left()
766                 .bind(c -> {
767                     component.setInnerElement(c);
768                     validateCanWorkOnComponent(c, userId);
769                     return Either.left(component);
770                 })
771                 .left()
772                 .bind(l -> lockComponent(component.getInnerElement(), shouldLock, "policyWritingOperation"))
773                 .either(l -> Either.left(component.getInnerElement()), r -> {
774                     log.error(FAILED_TO_VALIDATE_COMPONENT, componentId);
775                     return Either.right(r);
776                 });
777     }*/
778
779     private Component validateComponentIsTopologyTemplate(Component component) {
780         if (!component.isTopologyTemplate()) {
781             log.error("#validateComponentIsTopologyTemplate - policy association to a component of Tosca type {} is not allowed. ",
782                     component.getToscaType());
783             throw new ByActionStatusComponentException(ActionStatus.RESOURCE_CANNOT_CONTAIN_POLICIES,
784                     "#validateAndLockComponentAndUserBeforeWriteOperation", component.getUniqueId(), component.getToscaType());
785         }
786         return component;
787     }
788
789     /*private Either<Component, ResponseFormat> validateComponentIsTopologyTemplate(Component component) {
790         if (!component.isTopologyTemplate()) {
791             log.error("#validateComponentIsTopologyTemplate - policy association to a component of Tosca type {} is not allowed. ", component.getToscaType());
792             return Either.right(componentsUtils.getResponseFormat(ActionStatus.RESOURCE_CANNOT_CONTAIN_POLICIES, "#validateAndLockComponentAndUserBeforeWriteOperation", component.getUniqueId(), component.getToscaType()));
793         }
794         return Either.left(component);
795     }*/
796     private Component validateContainerComponentAndUserBeforeReadOperation(ComponentTypeEnum componentType, String componentId, String userId) {
797         log.trace("#validateContainerComponentAndUserBeforeReadOperation - starting to validate the user {} before policy processing. ", userId);
798         validateUserExists(userId);
799         return validateComponentExists(componentType, componentId);
800     }
801
802     private Component validateComponentExists(ComponentTypeEnum componentType, String componentId) {
803
804         ComponentParametersView filter = new ComponentParametersView(true);
805         filter.setIgnorePolicies(false);
806         filter.setIgnoreUsers(false);
807         filter.setIgnoreComponentInstances(false);
808         filter.setIgnoreGroups(false);
809         return validateComponentExists(componentId, componentType, filter);
810     }
811
812
813     private PolicyDefinition validateAndUpdatePolicy(Component component, PolicyDefinition policy) {
814         PolicyDefinition policyById = getPolicyById(component, policy.getUniqueId());
815         PolicyDefinition policyDefinition = validateUpdatePolicyBeforeUpdate(policy, policyById, component.getPolicies());
816         return updatePolicyOfComponent(component, policyDefinition);
817     }
818
819     /*private Either<PolicyDefinition, ResponseFormat> validateAndUpdatePolicy(Component component, PolicyDefinition policy) {
820         return getPolicyById(component, policy.getUniqueId())
821                 .left()
822                 .bind(np -> validateUpdatePolicyBeforeUpdate(policy, np, component.getPolicies()))
823                 .left()
824                 .bind(p -> updatePolicyOfComponent(component, p));
825     }*/
826
827     private PolicyDefinition validateAndUpdatePolicyProperties(Component component, String policyId, PropertyDataDefinition[] properties) {
828
829         PolicyDefinition policyById = getPolicyById(component, policyId);
830         policyById = validateUpdatePolicyPropertiesBeforeUpdate(policyById, properties);
831         return updatePolicyOfComponent(component.getUniqueId(), policyById);
832     }
833
834     private PolicyDefinition updatePolicyOfComponent(String componentId, PolicyDefinition policy) {
835         return toscaOperationFacade.updatePolicyOfComponent(componentId, policy, PromoteVersionEnum.MINOR)
836                 .left()
837                 .on(ce->componentExceptionPolicyDefinition(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(ce))));
838     }
839
840     private PolicyDefinition validateUpdatePolicyPropertiesBeforeUpdate(PolicyDefinition policy, PropertyDataDefinition[] newProperties) {
841         if (CollectionUtils.isEmpty(policy.getProperties())) {
842             log.error("#validateUpdatePolicyPropertiesBeforeUpdate - failed to update properites of the policy. Properties were not found on the policy. ");
843             throw new ByActionStatusComponentException(ActionStatus.PROPERTY_NOT_FOUND);
844         }
845         return updatePropertyValues(policy, newProperties);
846     }
847
848     private PolicyDefinition updatePropertyValues(PolicyDefinition policy, PropertyDataDefinition[] newProperties) {
849
850         Map<String, PropertyDataDefinition> oldProperties = policy.getProperties().stream().collect(toMap(PropertyDataDefinition::getName, Function.identity()));
851         for (PropertyDataDefinition newProperty : newProperties) {
852             if (!oldProperties.containsKey(newProperty.getName())) {
853                 log.error("#updatePropertyValues - failed to update properites of the policy {}. Properties were not found on the policy. ", policy.getName());
854                 throw new ByActionStatusComponentException(ActionStatus.PROPERTY_NOT_FOUND, newProperty.getName());
855             }
856             String newPropertyValueEither = updateInputPropertyObjectValue(newProperty);
857             oldProperties.get(newProperty.getName()).setValue(newPropertyValueEither);
858         }
859         return policy;
860     }
861
862     private PolicyDefinition deletePolicy(Component component, String policyId) {
863         PolicyDefinition policyById = getPolicyById(component, policyId);
864         return removePolicyFromComponent(component, policyById);
865     }
866
867     private PolicyDefinition updatePolicyOfComponent(Component component, PolicyDefinition policy) {
868
869         Either<PolicyDefinition, StorageOperationStatus> updatePolicyRes = toscaOperationFacade.updatePolicyOfComponent(component.getUniqueId(), policy, PromoteVersionEnum.MINOR);
870         if (updatePolicyRes.isRight()) {
871             log.error("#updatePolicyOfComponent - failed to update policy {} of the component {}. The status is {}. ", policy.getUniqueId(), component.getName(), updatePolicyRes.right().value());
872             throw new ByActionStatusComponentException(componentsUtils.convertFromStorageResponse(updatePolicyRes.right().value()));
873         } else {
874             log.trace("#updatePolicyOfComponent - the policy with the name {} was updated. ", updatePolicyRes.left().value().getName());
875             return updatePolicyRes.left().value();
876         }
877     }
878
879     private PolicyDefinition removePolicyFromComponent(Component component, PolicyDefinition policy) {
880         StorageOperationStatus updatePolicyStatus = toscaOperationFacade.removePolicyFromComponent(component.getUniqueId(), policy.getUniqueId());
881         if (updatePolicyStatus != StorageOperationStatus.OK) {
882             log.error("#removePolicyFromComponent - failed to remove policy {} from the component {}. The status is {}. ", policy.getUniqueId(), component.getName(), updatePolicyStatus);
883             throw new ByActionStatusComponentException(componentsUtils.convertFromStorageResponse(updatePolicyStatus));
884         } else {
885             log.trace("#removePolicyFromComponent - the policy with the name {} was deleted. ", updatePolicyStatus);
886             return policy;
887         }
888     }
889
890     private PolicyDefinition validateUpdatePolicyBeforeUpdate(PolicyDefinition recievedPolicy, PolicyDefinition oldPolicy, Map<String, PolicyDefinition> policies) {
891
892         Either<PolicyDefinition, ActionStatus> policyDefinitionActionStatusEither = validatePolicyFields(recievedPolicy, new PolicyDefinition(oldPolicy), policies);
893         if(policyDefinitionActionStatusEither.isRight()){
894             throw new ByActionStatusComponentException(policyDefinitionActionStatusEither.right().value(), recievedPolicy.getName());
895         }
896         return policyDefinitionActionStatusEither.left().value();
897     }
898
899     /*private Either<PolicyDefinition, ResponseFormat> validateUpdatePolicyBeforeUpdate(PolicyDefinition recievedPolicy, PolicyDefinition oldPolicy, Map<String, PolicyDefinition> policies) {
900         return validatePolicyFields(recievedPolicy, new PolicyDefinition(oldPolicy), policies)
901                 .right()
902                 .bind(r -> Either.right(componentsUtils.getResponseFormat(r, recievedPolicy.getName())));
903     }*/
904
905     private PolicyDefinition updateTargets(String componentId, PolicyDefinition policy, Map<PolicyTargetType, List<String>> targets, String policyId) {
906         if (policy == null) {
907             throw new ByActionStatusComponentException(ActionStatus.POLICY_NOT_FOUND_ON_CONTAINER, policyId, componentId);
908         }
909         PolicyDefinition updatedPolicy = setPolicyTargets(policy, targets);
910         return updatePolicyOfComponent(componentId, updatedPolicy);
911     }
912
913 }