2 * ============LICENSE_START=======================================================
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
11 * http://www.apache.org/licenses/LICENSE-2.0
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=========================================================
21 package org.openecomp.sdc.be.components.impl;
23 import com.google.common.annotations.VisibleForTesting;
24 import com.google.common.base.Strings;
25 import com.google.gson.Gson;
26 import com.google.gson.GsonBuilder;
27 import fj.data.Either;
28 import org.apache.commons.collections.CollectionUtils;
29 import org.apache.commons.collections.MapUtils;
30 import org.apache.commons.lang3.StringUtils;
31 import org.apache.commons.lang3.tuple.ImmutablePair;
32 import org.openecomp.sdc.be.components.distribution.engine.IDistributionEngine;
33 import org.openecomp.sdc.be.components.distribution.engine.INotificationData;
34 import org.openecomp.sdc.be.components.distribution.engine.VfModuleArtifactPayload;
35 import org.openecomp.sdc.be.components.health.HealthCheckBusinessLogic;
36 import org.openecomp.sdc.be.components.impl.exceptions.ComponentException;
37 import org.openecomp.sdc.be.components.impl.utils.NodeFilterConstraintAction;
38 import org.openecomp.sdc.be.components.lifecycle.LifecycleChangeInfoWithAction;
39 import org.openecomp.sdc.be.components.path.ForwardingPathValidator;
40 import org.openecomp.sdc.be.components.utils.InterfaceOperationUtils;
41 import org.openecomp.sdc.be.components.validation.NodeFilterValidator;
42 import org.openecomp.sdc.be.components.validation.ServiceDistributionValidation;
43 import org.openecomp.sdc.be.config.BeEcompErrorManager;
44 import org.openecomp.sdc.be.config.ConfigurationManager;
45 import org.openecomp.sdc.be.dao.api.ActionStatus;
46 import org.openecomp.sdc.be.dao.cassandra.AuditCassandraDao;
47 import org.openecomp.sdc.be.dao.jsongraph.types.JsonParseFlagEnum;
48 import org.openecomp.sdc.be.datamodel.ServiceRelations;
49 import org.openecomp.sdc.be.datamodel.utils.UiComponentDataConverter;
50 import org.openecomp.sdc.be.datatypes.elements.CINodeFilterDataDefinition;
51 import org.openecomp.sdc.be.datatypes.elements.ForwardingPathDataDefinition;
52 import org.openecomp.sdc.be.datatypes.elements.InterfaceDataDefinition;
53 import org.openecomp.sdc.be.datatypes.elements.ListDataDefinition;
54 import org.openecomp.sdc.be.datatypes.elements.OperationInputDefinition;
55 import org.openecomp.sdc.be.datatypes.elements.OperationOutputDefinition;
56 import org.openecomp.sdc.be.datatypes.elements.RequirementNodeFilterPropertyDataDefinition;
57 import org.openecomp.sdc.be.datatypes.enums.ComponentTypeEnum;
58 import org.openecomp.sdc.be.datatypes.enums.InstantiationTypes;
59 import org.openecomp.sdc.be.datatypes.enums.JsonPresentationFields;
60 import org.openecomp.sdc.be.datatypes.enums.NodeTypeEnum;
61 import org.openecomp.sdc.be.datatypes.enums.OriginTypeEnum;
62 import org.openecomp.sdc.be.externalapi.servlet.representation.ServiceDistributionReqInfo;
63 import org.openecomp.sdc.be.impl.ForwardingPathUtils;
64 import org.openecomp.sdc.be.impl.WebAppContextWrapper;
65 import org.openecomp.sdc.be.model.*;
66 import org.openecomp.sdc.be.model.category.CategoryDefinition;
67 import org.openecomp.sdc.be.model.jsontitan.operations.ForwardingPathOperation;
68 import org.openecomp.sdc.be.model.jsontitan.operations.NodeFilterOperation;
69 import org.openecomp.sdc.be.model.jsontitan.operations.ToscaOperationFacade;
70 import org.openecomp.sdc.be.model.operations.api.ICacheMangerOperation;
71 import org.openecomp.sdc.be.model.operations.api.IElementOperation;
72 import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus;
73 import org.openecomp.sdc.be.model.operations.impl.UniqueIdBuilder;
74 import org.openecomp.sdc.be.model.operations.utils.ComponentValidationUtils;
75 import org.openecomp.sdc.be.model.tosca.ToscaFunctions;
76 import org.openecomp.sdc.be.model.tosca.ToscaPropertyType;
77 import org.openecomp.sdc.be.model.tosca.validators.PropertyTypeValidator;
78 import org.openecomp.sdc.be.resources.data.ComponentInstanceData;
79 import org.openecomp.sdc.be.resources.data.ComponentMetadataData;
80 import org.openecomp.sdc.be.resources.data.auditing.*;
81 import org.openecomp.sdc.be.resources.data.auditing.model.ResourceCommonInfo;
82 import org.openecomp.sdc.be.resources.data.auditing.model.ResourceVersionInfo;
83 import org.openecomp.sdc.be.types.ServiceConsumptionData;
84 import org.openecomp.sdc.be.types.ServiceConsumptionSource;
85 import org.openecomp.sdc.be.ui.model.UiComponentDataTransfer;
86 import org.openecomp.sdc.be.user.Role;
87 import org.openecomp.sdc.common.api.ArtifactGroupTypeEnum;
88 import org.openecomp.sdc.common.api.ArtifactTypeEnum;
89 import org.openecomp.sdc.common.api.Constants;
90 import org.openecomp.sdc.common.datastructure.Wrapper;
91 import org.openecomp.sdc.common.kpi.api.ASDCKpiApi;
92 import org.openecomp.sdc.common.log.wrappers.Logger;
93 import org.openecomp.sdc.common.util.GeneralUtility;
94 import org.openecomp.sdc.common.util.ThreadLocalsHolder;
95 import org.openecomp.sdc.common.util.ValidationUtils;
96 import org.openecomp.sdc.exception.ResponseFormat;
97 import org.springframework.beans.factory.annotation.Autowired;
98 import org.springframework.http.HttpStatus;
99 import org.springframework.web.context.WebApplicationContext;
101 import javax.servlet.ServletContext;
102 import javax.servlet.http.HttpServletRequest;
103 import java.nio.charset.StandardCharsets;
105 import java.util.concurrent.Callable;
106 import java.util.function.Function;
107 import java.util.stream.Collectors;
109 import static org.apache.commons.collections.CollectionUtils.isEmpty;
110 import static org.apache.commons.collections.CollectionUtils.isNotEmpty;
111 import static org.openecomp.sdc.be.components.utils.InterfaceOperationUtils.getOperationOutputName;
112 import static org.openecomp.sdc.be.components.utils.InterfaceOperationUtils.isOperationInputMappedToOtherOperationOutput;
113 import static org.openecomp.sdc.be.resources.data.auditing.AuditingActionEnum.UPDATE_SERVICE_METADATA;
114 import static org.openecomp.sdc.be.tosca.utils.InterfacesOperationsToscaUtil.SELF;
115 import static org.openecomp.sdc.be.types.ServiceConsumptionSource.SERVICE_INPUT;
116 import static org.openecomp.sdc.be.types.ServiceConsumptionSource.STATIC;
118 @org.springframework.stereotype.Component("serviceBusinessLogic")
119 public class ServiceBusinessLogic extends ComponentBusinessLogic {
121 private static final String CHANGE_SERVICE_DISTRIBUTION = "Change Service Distribution";
122 private static final String THE_SERVICE_WITH_SYSTEM_NAME_LOCKED = "The service with system name {} locked. ";
123 private static final String FAILED_TO_LOCK_SERVICE_RESPONSE_IS = "Failed to lock service {}. Response is {}. ";
124 private static final String AUDIT_BEFORE_SENDING_RESPONSE = "audit before sending response";
125 private static final Logger log = Logger.getLogger(ServiceBusinessLogic.class);
126 private static final String INITIAL_VERSION = "0.1";
127 private static final String STATUS_SUCCESS_200 = "200";
128 private static final String STATUS_DEPLOYED = "DEPLOYED";
130 private IDistributionEngine distributionEngine;
132 private AuditCassandraDao auditCassandraDao;
134 private ComponentInstanceBusinessLogic componentInstanceBusinessLogic;
136 private ICacheMangerOperation cacheManagerOperation;
138 private ServiceDistributionValidation serviceDistributionValidation;
141 private ForwardingPathOperation forwardingPathOperation;
143 private ForwardingPathValidator forwardingPathValidator;
145 private UiComponentDataConverter uiComponentDataConverter;
147 private NodeFilterOperation serviceFilterOperation;
149 private NodeFilterValidator serviceFilterValidator;
151 public Either<Service, ResponseFormat> changeServiceDistributionState(String serviceId, String state, LifecycleChangeInfoWithAction commentObj, User user) {
153 validateUserExists(user.getUserId(), "change Service Distribution State", false);
155 log.debug("check request state");
156 Either<DistributionTransitionEnum, ResponseFormat> validateEnum = validateTransitionEnum(state);
157 if (validateEnum.isRight()) {
158 return Either.right(validateEnum.right().value());
160 DistributionTransitionEnum distributionTransition = validateEnum.left().value();
161 AuditingActionEnum auditAction = distributionTransition == DistributionTransitionEnum.APPROVE ? AuditingActionEnum.DISTRIBUTION_STATE_CHANGE_APPROV : AuditingActionEnum.DISTRIBUTION_STATE_CHANGE_REJECT;
162 Either<String, ResponseFormat> commentResponse = validateComment(commentObj);
163 if (commentResponse.isRight()) {
164 return Either.right(commentResponse.right().value());
166 String comment = commentResponse.left().value();
168 Either<Service, ResponseFormat> validateService = validateServiceDistributionChange(user, serviceId, auditAction, comment);
169 if (validateService.isRight()) {
170 return Either.right(validateService.right().value());
172 Service service = validateService.left().value();
173 Either<User, ResponseFormat> validateUser = validateUserDistributionChange(user, service, auditAction, comment);
174 if (validateUser.isRight()) {
175 return Either.right(validateUser.right().value());
177 user = validateUser.left().value();
181 Either<Boolean, ResponseFormat> lockResult = lockComponent(serviceId, service, "ChangeServiceDistributionState");
182 if (lockResult.isRight()) {
183 ResponseFormat responseFormat = lockResult.right().value();
184 createAudit(user, auditAction, comment, service, responseFormat);
185 return Either.right(responseFormat);
190 DistributionStatusEnum newState;
191 if (distributionTransition == DistributionTransitionEnum.APPROVE) {
192 newState = DistributionStatusEnum.DISTRIBUTION_APPROVED;
194 newState = DistributionStatusEnum.DISTRIBUTION_REJECTED;
196 Either<Service, StorageOperationStatus> result = toscaOperationFacade.updateDistributionStatus(service, user, newState);
197 if (result.isRight()) {
199 BeEcompErrorManager.getInstance().logBeSystemError("ChangeServiceDistributionState");
200 log.debug("service {} is change destribuation status failed", service.getUniqueId());
201 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR, service.getVersion(), service.getName());
202 createAudit(user, auditAction, comment, service, responseFormat);
203 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
206 Service updatedService = result.left().value();
207 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.OK);
208 log.debug(AUDIT_BEFORE_SENDING_RESPONSE);
209 componentsUtils.auditComponent(responseFormat, user, updatedService, auditAction, new ResourceCommonInfo(ComponentTypeEnum.SERVICE.getValue()), ResourceVersionInfo.newBuilder().build(), comment);
210 return Either.left(result.left().value());
212 graphLockOperation.unlockComponent(serviceId, NodeTypeEnum.Service);
217 public Either<List<Map<String, Object>>, ResponseFormat> getComponentAuditRecords(String componentVersion, String componentUUID, String userId) {
218 validateUserExists(userId, "get Component Audit Records", false);
219 Either<List<Map<String, Object>>, ActionStatus> result;
223 if (componentVersion.endsWith(".0")) {
224 Either<List<ResourceAdminEvent>, ActionStatus> eitherAuditingForCertified = auditCassandraDao.getByServiceInstanceId(componentUUID);
225 if (eitherAuditingForCertified.isLeft()) {
226 result = Either.left(getAuditingFieldsList(eitherAuditingForCertified.left().value()));
228 result = Either.right(eitherAuditingForCertified.right().value());
231 // Uncertified Version
233 result = getAuditRecordsForUncertifiedComponent(componentUUID, componentVersion);
235 } catch (Exception e) {
236 log.debug("get Audit Records failed with exception {}", e);
237 result = Either.right(ActionStatus.GENERAL_ERROR);
240 if (result.isRight()) {
241 return Either.right(componentsUtils.getResponseFormat(result.right().value()));
243 return Either.left(result.left().value());
248 public Either<List<Operation>, ResponseFormat> addServiceConsumptionData(String serviceId,
249 String serviceInstanceId,
251 List<ServiceConsumptionData> serviceConsumptionDataList,
253 List<Operation> operationList = new ArrayList<>();
255 Either<Service, StorageOperationStatus> serviceEither =
256 toscaOperationFacade.getToscaElement(serviceId);
257 if(serviceEither.isRight()) {
258 return Either.right(componentsUtils.getResponseFormat
259 (serviceEither.right().value()));
262 Service service = serviceEither.left().value();
265 StorageOperationStatus storageOperationStatus =
266 graphLockOperation.lockComponent(service.getUniqueId(), NodeTypeEnum.Service);
267 if (storageOperationStatus != StorageOperationStatus.OK) {
268 return Either.right(componentsUtils.getResponseFormat(storageOperationStatus));
272 for (ServiceConsumptionData serviceConsumptionData : serviceConsumptionDataList) {
273 Either<Operation, ResponseFormat> operationEither =
274 addPropertyServiceConsumption(serviceId, serviceInstanceId, operationId,
275 userId, serviceConsumptionData);
277 if (operationEither.isRight()) {
278 return Either.right(operationEither.right().value());
281 operationList.add(operationEither.left().value());
285 return Either.left(operationList);
286 } catch (Exception e) {
288 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
291 graphLockOperation.unlockComponent(service.getUniqueId(), NodeTypeEnum.Service);
296 public Either <Operation, ResponseFormat> addPropertyServiceConsumption(String serviceId,
297 String serviceInstanceId,
300 ServiceConsumptionData serviceConsumptionData) {
301 validateUserExists(userId, "create Property", false);
303 Either<Service, StorageOperationStatus> serviceEither =
304 toscaOperationFacade.getToscaElement(serviceId);
305 if(serviceEither.isRight()) {
306 return Either.right(componentsUtils.getResponseFormat(serviceEither.right
310 Service parentService = serviceEither.left().value();
312 List<ComponentInstance> componentInstances = parentService.getComponentInstances();
313 if(CollectionUtils.isEmpty(componentInstances)) {
314 return Either.right(componentsUtils.getResponseFormat(ActionStatus
315 .INTERFACE_OPERATION_NOT_FOUND, serviceInstanceId));
318 Optional<ComponentInstance> serviceInstanceCandidate =
319 componentInstances.stream().filter(instance -> instance.getUniqueId().equals
320 (serviceInstanceId)).findAny();
322 if(!serviceInstanceCandidate.isPresent()) {
323 return Either.right(componentsUtils.getResponseFormat(ActionStatus
324 .INTERFACE_OPERATION_NOT_FOUND, serviceInstanceId));
327 Map<String, List<ComponentInstanceInterface>> componentInstancesInterfaces =
328 parentService.getComponentInstancesInterfaces();
329 if(MapUtils.isEmpty(componentInstancesInterfaces)) {
330 return Either.right(componentsUtils.getResponseFormat(ActionStatus
331 .INTERFACE_OPERATION_NOT_FOUND, serviceInstanceId));
334 List<InterfaceDefinition> interfaces = new ArrayList<>();
335 for(ComponentInstanceInterface componentInstanceInterface :
336 componentInstancesInterfaces.get(serviceInstanceId)) {
337 interfaces.add(componentInstanceInterface);
340 ComponentInstance serviceInstance = serviceInstanceCandidate.get();
341 Optional<InterfaceDefinition> interfaceCandidate = InterfaceOperationUtils
342 .getInterfaceDefinitionFromOperationId(interfaces, operationId);
344 if(!interfaceCandidate.isPresent()) {
345 return Either.right(componentsUtils.getResponseFormat(ActionStatus
346 .INTERFACE_OPERATION_NOT_FOUND, serviceInstanceId));
349 InterfaceDefinition interfaceDefinition = interfaceCandidate.get();
350 Map<String, Operation> operations = interfaceDefinition.getOperationsMap();
351 if(MapUtils.isEmpty(operations)) {
352 return Either.right(componentsUtils.getResponseFormat(ActionStatus
353 .INTERFACE_OPERATION_NOT_FOUND, serviceInstanceId));
356 Operation operation = operations.get(operationId);
357 Either<Operation, ResponseFormat> operationEither = Either.left(operation);
359 ListDataDefinition<OperationInputDefinition> inputs = operation.getInputs();
360 Optional<OperationInputDefinition> inputCandidate =
361 getOperationInputByInputId(serviceConsumptionData, inputs);
363 if(!inputCandidate.isPresent()) {
364 return Either.right(new ResponseFormat(HttpStatus.NOT_FOUND.value()));
367 OperationInputDefinition operationInputDefinition = inputCandidate.get();
369 // add data to operation
371 if(Objects.nonNull(serviceConsumptionData.getValue())) {
373 handleConsumptionValue(parentService, serviceInstanceId, serviceConsumptionData, operation,
374 operationInputDefinition);
377 if(operationEither.isRight()) {
378 return Either.right(operationEither.right().value());
381 Operation updatedOperation = operationEither.left().value();
382 operations.remove(operationId);
383 operations.put(operationId, updatedOperation);
384 interfaceDefinition.setOperationsMap(operations);
386 parentService.getComponentInstances().remove(serviceInstance);
387 if(CollectionUtils.isEmpty(parentService.getComponentInstances())) {
388 parentService.setComponentInstances(new ArrayList<>());
391 Map<String, Object> instanceInterfaces =
392 MapUtils.isEmpty(serviceInstance.getInterfaces())? new HashMap<>() : serviceInstance.getInterfaces();
393 instanceInterfaces.remove(interfaceDefinition.getUniqueId());
394 instanceInterfaces.put(interfaceDefinition.getUniqueId(), interfaceDefinition);
395 serviceInstance.setInterfaces(instanceInterfaces);
397 removeComponentInstanceInterfaceByInterfaceId(interfaceDefinition.getUniqueId(), componentInstancesInterfaces.get(serviceInstanceId));
398 componentInstancesInterfaces.get(serviceInstanceId).add(new ComponentInstanceInterface(interfaceDefinition.getUniqueId(), interfaceDefinition));
400 parentService.getComponentInstances().add(serviceInstance);
402 StorageOperationStatus status = toscaOperationFacade.updateComponentInstanceInterfaces(parentService, serviceInstanceId);
404 if(status != StorageOperationStatus.OK) {
405 return Either.right(componentsUtils.getResponseFormat(ActionStatus
406 .INTERFACE_OPERATION_NOT_FOUND, serviceInstanceId));
409 return Either.left(operation);
412 private void removeComponentInstanceInterfaceByInterfaceId(String interfaceIdToRemove,
413 List<ComponentInstanceInterface> instanceInterfaces) {
414 if(CollectionUtils.isEmpty(instanceInterfaces)) {
418 Optional<ComponentInstanceInterface> interfaceToRemove =
419 instanceInterfaces.stream().filter(instInterface -> instInterface.getUniqueId().equals
420 (interfaceIdToRemove)).findAny();
422 if(interfaceToRemove.isPresent()) {
423 instanceInterfaces.remove(interfaceToRemove.get());
428 private Either<Operation, ResponseFormat> handleConsumptionValue(Service containerService,
429 String serviceInstanceId,
430 ServiceConsumptionData serviceConsumptionData,
432 OperationInputDefinition
433 operationInputDefinition) {
434 String source = serviceConsumptionData.getSource();
435 String consumptionValue = serviceConsumptionData.getValue();
436 String type = serviceConsumptionData.getType();
437 String operationIdentifier = consumptionValue.contains(".")
438 ? consumptionValue.substring(0, consumptionValue.lastIndexOf('.'))
441 ServiceConsumptionSource sourceValue = ServiceConsumptionSource.getSourceValue(source);
443 if(STATIC.equals(sourceValue)) {
444 return handleConsumptionStaticValue(consumptionValue, type, operation,
445 operationInputDefinition);
448 if (Objects.isNull(sourceValue)) {
449 List<PropertyDefinition> propertyDefinitions;
450 String componentName;
451 List<OperationOutputDefinition> outputs = null;
452 if (source.equals(containerService.getUniqueId())) {
453 Either<Service, StorageOperationStatus> serviceToTakePropEither =
454 toscaOperationFacade.getToscaElement(source);
455 if (serviceToTakePropEither.isRight()) {
456 return Either.right(componentsUtils.getResponseFormat(serviceToTakePropEither.right().value()));
458 Service service = serviceToTakePropEither.left().value();
459 operationInputDefinition.setSource(service.getUniqueId());
460 sourceValue = SERVICE_INPUT;
461 propertyDefinitions = service.getProperties();
462 componentName = service.getName();
463 outputs = InterfaceOperationUtils.getOtherOperationOutputsOfComponent(operationIdentifier,
464 service.getInterfaces()).getListToscaDataDefinition();
466 Optional<ComponentInstance> getComponentInstance = containerService.getComponentInstanceById(source);
467 if(!getComponentInstance.isPresent()){
468 return Either.right(componentsUtils.getResponseFormat(
469 ActionStatus.COMPONENT_INSTANCE_NOT_FOUND_ON_CONTAINER, source));
471 ComponentInstance componentInstance = getComponentInstance.get();
472 operationInputDefinition.setSource(componentInstance.getUniqueId());
473 propertyDefinitions = componentInstance.getProperties();
474 componentName = source.equals(serviceInstanceId) ? SELF : componentInstance.getName();
475 if (MapUtils.isNotEmpty(componentInstance.getInterfaces())) {
476 Map<String, InterfaceDataDefinition> componentInstanceInterfaces =
477 componentInstance.getInterfaces().entrySet().stream()
478 .collect(Collectors.toMap((Map.Entry::getKey),
479 (interfaceEntry -> (InterfaceDataDefinition) interfaceEntry.getValue())));
480 outputs = InterfaceOperationUtils.getOtherOperationOutputsOfComponent(operationIdentifier,
481 componentInstanceInterfaces).getListToscaDataDefinition();
485 if(sourceValue == ServiceConsumptionSource.SERVICE_INPUT) {
486 //The operation input in service consumption has been mapped to an input in the parent service
487 return handleConsumptionInputValue(consumptionValue, containerService, operation,
488 operationInputDefinition);
490 return handleConsumptionPropertyValue(operation, operationInputDefinition,
491 serviceConsumptionData, propertyDefinitions, outputs, consumptionValue, componentName);
494 operationInputDefinition.setToscaPresentationValue(JsonPresentationFields.SOURCE, source);
495 operationInputDefinition.setSource(source);
497 return Either.left(operation);
500 private Optional<OperationInputDefinition> getOperationInputByInputId(ServiceConsumptionData serviceConsumptionData,
501 ListDataDefinition<OperationInputDefinition> inputs) {
503 if(CollectionUtils.isEmpty(inputs.getListToscaDataDefinition())) {
504 return Optional.empty();
507 return inputs.getListToscaDataDefinition().stream().filter(operationInput -> operationInput.getInputId().equals
508 (serviceConsumptionData.getInputId()))
512 private Either<Operation, ResponseFormat> handleConsumptionPropertyValue(
513 Operation operation, OperationInputDefinition operationInputDefinition,
514 ServiceConsumptionData serviceConsumptionData, List<PropertyDefinition> properties,
515 List<OperationOutputDefinition> outputs, String consumptionValue, String componentName) {
517 if (CollectionUtils.isEmpty(properties) && CollectionUtils.isEmpty(outputs)) {
518 return Either.left(operation);
521 if (CollectionUtils.isNotEmpty(outputs)
522 && isOperationInputMappedToOtherOperationOutput(getOperationOutputName(consumptionValue), outputs)) {
523 return handleConsumptionInputMappedToOperationOutput(operation, operationInputDefinition, outputs,
524 consumptionValue, componentName);
527 if (CollectionUtils.isNotEmpty(properties)) {
528 return handleConsumptionInputMappedToProperty(operation, operationInputDefinition, serviceConsumptionData,
529 properties, componentName);
531 return Either.left(operation);
534 private Either<Operation, ResponseFormat> handleConsumptionInputMappedToProperty(Operation operation,
535 OperationInputDefinition operationInputDefinition, ServiceConsumptionData serviceConsumptionData,
536 List<PropertyDefinition> properties, String componentName) {
537 Optional<PropertyDefinition> servicePropertyCandidate =
538 properties.stream().filter(property -> property.getName()
539 .equals(serviceConsumptionData.getValue())).findAny();
541 if (servicePropertyCandidate.isPresent()) {
542 boolean isInputTypeSimilarToOperation =
543 isAssignedValueFromValidType(operationInputDefinition.getType(),
544 servicePropertyCandidate.get());
546 if (!isInputTypeSimilarToOperation) {
547 return Either.right(componentsUtils.getResponseFormat(
548 ActionStatus.INVALID_CONSUMPTION_TYPE, operationInputDefinition.getType()));
551 addPropertyToInputValue(componentName, operation, operationInputDefinition,
552 servicePropertyCandidate.get());
554 return Either.left(operation);
557 private Either<Operation, ResponseFormat> handleConsumptionInputMappedToOperationOutput(Operation operation,
558 OperationInputDefinition operationInputDefinition, List<OperationOutputDefinition> outputs,
559 String consumptionValue, String componentName) {
560 String outputName = getOperationOutputName(consumptionValue);
561 Optional<OperationOutputDefinition> servicePropertyOutputCandidate = outputs.stream()
562 .filter(output -> output.getName().equals(outputName)).findAny();
563 if (servicePropertyOutputCandidate.isPresent()) {
564 boolean isInputTypeSimilarToOperation =
565 isAssignedValueFromValidType(operationInputDefinition.getType(),
566 servicePropertyOutputCandidate.get());
567 if (!isInputTypeSimilarToOperation) {
568 return Either.right(componentsUtils.getResponseFormat(
569 ActionStatus.INVALID_CONSUMPTION_TYPE, operationInputDefinition.getType()));
571 addOutputToInputValue(componentName, consumptionValue, operation, operationInputDefinition);
573 return Either.left(operation);
576 private void addPropertyToInputValue(String componentName, Operation operation,
577 OperationInputDefinition operationInputDefinition,
578 PropertyDefinition serviceProperty) {
579 Map<String, List<String>> getProperty = new HashMap<>();
580 List<String> getPropertyValues = new ArrayList<>();
581 getPropertyValues.add(componentName);
582 getPropertyValues.add(serviceProperty.getName());
583 getProperty.put(ToscaFunctions.GET_PROPERTY.getFunctionName(), getPropertyValues);
585 operationInputDefinition.setSourceProperty(serviceProperty.getUniqueId());
586 operation.getInputs().delete(operationInputDefinition);
587 operationInputDefinition.setToscaPresentationValue(JsonPresentationFields.GET_PROPERTY,
589 operationInputDefinition.setValue((new Gson()).toJson(getProperty));
590 operation.getInputs().add(operationInputDefinition);
593 private void addOutputToInputValue(String componentName, String consumptionValue,
594 Operation operation, OperationInputDefinition operationInputDefinition) {
595 Map<String, List<String>> getOperationOutput =
596 InterfaceOperationUtils.createMappedOutputDefaultValue(componentName, consumptionValue);
597 operation.getInputs().delete(operationInputDefinition);
598 operationInputDefinition.setToscaPresentationValue(JsonPresentationFields.GET_OPERATION_OUTPUT,
600 operationInputDefinition.setValue((new Gson()).toJson(getOperationOutput));
601 operation.getInputs().add(operationInputDefinition);
604 public Either<Operation, ResponseFormat> handleConsumptionStaticValue(String value, String type,
606 OperationInputDefinition
607 operationInputDefinition) {
608 boolean isInputTypeSimilarToOperation =
609 isAssignedValueFromValidType(type, value);
611 if(!isInputTypeSimilarToOperation) {
612 return Either.right(componentsUtils.getResponseFormat(
613 ActionStatus.INVALID_CONSUMPTION_TYPE, type));
615 addStaticValueToInputOperation(value, operation, operationInputDefinition);
617 return Either.left(operation);
620 private void addStaticValueToInputOperation(String value, Operation operation,
621 OperationInputDefinition operationInputDefinition) {
622 operation.getInputs().delete(operationInputDefinition);
623 operationInputDefinition.setSource(STATIC.getSource());
624 operationInputDefinition.setSourceProperty(null);
625 operationInputDefinition.setValue(value);
626 operation.getInputs().add(operationInputDefinition);
629 private Either<Operation, ResponseFormat> handleConsumptionInputValue(String inputId,
632 OperationInputDefinition
633 operationInputDefinition) {
634 List<InputDefinition> serviceInputs = service.getInputs();
635 Optional<InputDefinition> inputForValue =
636 serviceInputs.stream().filter(input -> input.getUniqueId().contains(inputId)).findAny();
638 if(inputForValue.isPresent()) {
639 boolean isInputTypeSimilarToOperation =
640 isAssignedValueFromValidType(operationInputDefinition.getType(), inputForValue.get());
642 if(!isInputTypeSimilarToOperation) {
643 return Either.right(componentsUtils.getResponseFormat(
644 ActionStatus.INVALID_CONSUMPTION_TYPE, operationInputDefinition.getType()));
646 addGetInputValueToOperationInput(operation, operationInputDefinition, inputForValue.get());
649 return Either.left(operation);
653 private boolean isAssignedValueFromValidType(String operationInputType, Object actualValue) {
654 if (actualValue instanceof String) {
655 // validate static value
656 ToscaPropertyType actualType = ToscaPropertyType.isValidType(operationInputType);
657 PropertyTypeValidator validator = actualType.getValidator();
658 return validator.isValid((String)actualValue, operationInputType);
659 } else if (actualValue instanceof PropertyDefinition) {
660 // validate input / property value
661 String actualType = ((PropertyDefinition) actualValue).getType();
662 return actualType.equalsIgnoreCase(operationInputType);
663 } else if (actualValue instanceof OperationOutputDefinition) {
664 // validate input / output value
665 String actualType = ((OperationOutputDefinition) actualValue).getType();
666 return actualType.equalsIgnoreCase(operationInputType);
671 private void addGetInputValueToOperationInput(Operation operation,
672 OperationInputDefinition operationInputDefinition,
673 InputDefinition inputForValue) {
674 operation.getInputs().delete(operationInputDefinition);
675 Map<String, String> getInputMap = new HashMap<>();
676 getInputMap.put(ToscaFunctions.GET_INPUT.getFunctionName(), inputForValue.getName());
677 operationInputDefinition.setSourceProperty(inputForValue.getUniqueId());
678 operationInputDefinition.setToscaPresentationValue(JsonPresentationFields.GET_INPUT, getInputMap);
679 operationInputDefinition.setValue(new Gson().toJson(getInputMap));
680 operation.getInputs().add(operationInputDefinition);
683 private Either<List<Map<String, Object>>, ActionStatus> getAuditRecordsForUncertifiedComponent(String componentUUID, String componentVersion) {
685 Either<List<ResourceAdminEvent>, ActionStatus> eitherprevVerAudit = auditCassandraDao.getAuditByServiceIdAndPrevVersion(componentUUID, componentVersion);
687 if (eitherprevVerAudit.isRight()) {
688 return Either.right(eitherprevVerAudit.right().value());
692 Either<List<ResourceAdminEvent>, ActionStatus> eitherCurrVerAudit = auditCassandraDao.getAuditByServiceIdAndCurrVersion(componentUUID, componentVersion);
693 if (eitherCurrVerAudit.isRight()) {
694 return Either.right(eitherCurrVerAudit.right().value());
698 Either<List<ResourceAdminEvent>, ActionStatus> eitherArchiveRestoreList = getArchiveRestoreEventList(componentUUID);
699 if (eitherArchiveRestoreList.isRight()) {
700 return Either.right(eitherArchiveRestoreList.right().value());
703 List<Map<String, Object>> prevVerAuditList = getAuditingFieldsList(eitherprevVerAudit.left().value());
704 List<Map<String, Object>> currVerAuditList = getAuditingFieldsList(eitherCurrVerAudit.left().value());
706 List<Map<String, Object>> duplicateElements = new ArrayList<>();
707 duplicateElements.addAll(prevVerAuditList);
708 duplicateElements.retainAll(currVerAuditList);
710 List<Map<String, Object>> joinedNonDuplicatedList = new ArrayList<>();
711 joinedNonDuplicatedList.addAll(prevVerAuditList);
712 joinedNonDuplicatedList.removeAll(duplicateElements);
713 joinedNonDuplicatedList.addAll(currVerAuditList);
714 joinedNonDuplicatedList.addAll(getAuditingFieldsList(eitherArchiveRestoreList.left().value()));
717 return Either.left(joinedNonDuplicatedList);
720 private Either<List<ResourceAdminEvent>, ActionStatus> getArchiveRestoreEventList(String componentUUID) {
722 Either<List<ResourceAdminEvent>, ActionStatus> eitherArchiveAudit = auditCassandraDao.getArchiveAuditByServiceInstanceId(componentUUID);
723 if (eitherArchiveAudit.isRight()) {
724 return Either.right(eitherArchiveAudit.right().value());
728 Either<List<ResourceAdminEvent>, ActionStatus> eitherRestoreAudit = auditCassandraDao.getRestoreAuditByServiceInstanceId(componentUUID);
729 if (eitherRestoreAudit.isRight()) {
730 return Either.right(eitherRestoreAudit.right().value());
733 List<ResourceAdminEvent> archiveAudit = new ArrayList<>();
734 archiveAudit.addAll(eitherArchiveAudit.left().value());
735 archiveAudit.addAll(eitherRestoreAudit.left().value());
737 return Either.left(archiveAudit);
740 private List<Map<String, Object>> getAuditingFieldsList(List<? extends AuditingGenericEvent> prevVerAuditList) {
742 List<Map<String, Object>> prevVerAudit = new ArrayList<>();
743 for (AuditingGenericEvent auditEvent : prevVerAuditList) {
744 auditEvent.fillFields();
745 prevVerAudit.add(auditEvent.getFields());
756 * - modifier data (userId)
757 * @return Either<Service, responseFormat>
759 public Either<Service, ResponseFormat> createService(Service service, User user) {
762 user = validateUser(user, "Create Service", service, AuditingActionEnum.CREATE_RESOURCE, false);
763 // validate user role
764 validateUserRole(user, service, new ArrayList<>(), AuditingActionEnum.CREATE_RESOURCE, null);
765 service.setCreatorUserId(user.getUserId());
766 // warn on overridden fields
767 checkFieldsForOverideAttampt(service);
769 log.debug("enrich service with version and state");
770 service.setState(LifecycleStateEnum.NOT_CERTIFIED_CHECKOUT);
771 service.setVersion(INITIAL_VERSION);
772 service.setConformanceLevel(ConfigurationManager.getConfigurationManager().getConfiguration().getToscaConformanceLevel());
773 service.setDistributionStatus(DistributionStatusEnum.DISTRIBUTION_NOT_APPROVED);
775 Either<Service, ResponseFormat> createServiceResponse = validateServiceBeforeCreate(service, user, AuditingActionEnum.CREATE_RESOURCE);
776 if (createServiceResponse.isRight()) {
777 return createServiceResponse;
779 return createServiceByDao(service, AuditingActionEnum.CREATE_RESOURCE, user);
782 private void checkFieldsForOverideAttampt(Service service) {
783 checkComponentFieldsForOverrideAttempt(service);
784 if (service.getDistributionStatus() != null) {
785 log.info("Distribution Status cannot be defined by user. This field will be overridden by the application");
789 private Either<Service, ResponseFormat> createServiceByDao(Service service, AuditingActionEnum actionEnum, User user) {
790 log.debug("send service {} to dao for create", service.getComponentMetadataDefinition().getMetadataDataDefinition().getName());
792 Either<Boolean, ResponseFormat> lockResult = lockComponentByName(service.getSystemName(), service, "Create Service");
793 if (lockResult.isRight()) {
794 ResponseFormat responseFormat = lockResult.right().value();
795 componentsUtils.auditComponentAdmin(responseFormat, user, service, actionEnum, ComponentTypeEnum.SERVICE);
796 return Either.right(responseFormat);
799 log.debug("System name locked is {}, status = {}", service.getSystemName(), lockResult);
803 createMandatoryArtifactsData(service, user);
804 createServiceApiArtifactsData(service, user);
805 setToscaArtifactsPlaceHolders(service, user);
806 generateAndAddInputsFromGenericTypeProperties(service, fetchAndSetDerivedFromGenericType(service));
808 Either<Service, StorageOperationStatus> dataModelResponse = toscaOperationFacade.createToscaComponent(service);
810 // service created successfully!!!
811 if (dataModelResponse.isLeft()) {
812 log.debug("Service created successfully!!!");
813 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.CREATED);
814 componentsUtils.auditComponentAdmin(responseFormat, user, service, actionEnum, ComponentTypeEnum.SERVICE);
815 ASDCKpiApi.countCreatedServicesKPI();
816 return Either.left(dataModelResponse.left().value());
819 ResponseFormat responseFormat = componentsUtils.getResponseFormatByComponent(componentsUtils.convertFromStorageResponse(dataModelResponse.right().value()), service, ComponentTypeEnum.SERVICE);
820 log.debug(AUDIT_BEFORE_SENDING_RESPONSE);
821 componentsUtils.auditComponentAdmin(responseFormat, user, service, actionEnum, ComponentTypeEnum.SERVICE);
822 return Either.right(responseFormat);
825 graphLockOperation.unlockComponentByName(service.getSystemName(), service.getUniqueId(), NodeTypeEnum.Service);
829 @SuppressWarnings("unchecked")
830 private void createServiceApiArtifactsData(Service service, User user) {
831 // create mandatory artifacts
833 // TODO it must be removed after that artifact uniqueId creation will be
834 // moved to ArtifactOperation
835 String serviceUniqueId = service.getUniqueId();
836 Map<String, ArtifactDefinition> artifactMap = service.getServiceApiArtifacts();
837 if (artifactMap == null)
838 artifactMap = new HashMap<>();
840 Map<String, Object> serviceApiArtifacts = ConfigurationManager.getConfigurationManager().getConfiguration().getServiceApiArtifacts();
841 List<String> exludeServiceCategory = ConfigurationManager.getConfigurationManager().getConfiguration().getExcludeServiceCategory();
843 List<CategoryDefinition> categories = service.getCategories();
844 boolean isCreateArtifact = true;
845 if (categories != null && exludeServiceCategory != null && !exludeServiceCategory.isEmpty()) {
846 for (String exlude : exludeServiceCategory) {
847 if (exlude.equalsIgnoreCase(categories.get(0).getName())) {
848 isCreateArtifact = false;
855 if (serviceApiArtifacts != null && isCreateArtifact) {
856 Set<String> keys = serviceApiArtifacts.keySet();
857 for (String serviceApiArtifactName : keys) {
858 Map<String, Object> artifactInfoMap = (Map<String, Object>) serviceApiArtifacts.get(serviceApiArtifactName);
859 ArtifactDefinition artifactDefinition = createArtifactDefinition(serviceUniqueId, serviceApiArtifactName, artifactInfoMap, user, true);
860 artifactDefinition.setArtifactGroupType(ArtifactGroupTypeEnum.SERVICE_API);
861 artifactMap.put(artifactDefinition.getArtifactLabel(), artifactDefinition);
864 service.setServiceApiArtifacts(artifactMap);
868 private Either<Service, ResponseFormat> validateServiceBeforeCreate(Service service, User user, AuditingActionEnum actionEnum) {
870 Either<Boolean, ResponseFormat> validationResponse = validateServiceFieldsBeforeCreate(user, service, actionEnum);
871 if (validationResponse.isRight()) {
872 return Either.right(validationResponse.right().value());
874 service.setCreatorFullName(user.getFirstName() + " " + user.getLastName());
875 service.setContactId(service.getContactId().toLowerCase());
877 // Generate invariant UUID - must be here and not in operation since it
878 // should stay constant during clone
879 String invariantUUID = UniqueIdBuilder.buildInvariantUUID();
880 service.setInvariantUUID(invariantUUID);
882 return Either.left(service);
887 private Either<Boolean, ResponseFormat> validateServiceFieldsBeforeCreate(User user, Service service, AuditingActionEnum actionEnum) {
889 validateComponentFieldsBeforeCreate(user, service, actionEnum);
891 Either<Boolean, ResponseFormat> serviceNameUniquenessValidation = validateComponentNameUnique(user, service, actionEnum);
892 if (serviceNameUniquenessValidation.isRight()) {
893 throw new ComponentException(serviceNameUniquenessValidation.right().value());
895 Either<Boolean, ResponseFormat> categoryValidation = validateServiceCategory(user, service, actionEnum);
896 if (categoryValidation.isRight()) {
897 return categoryValidation;
899 Either<Boolean, ResponseFormat> projectCodeValidation = validateProjectCode(user, service, actionEnum);
900 if (projectCodeValidation.isRight()) {
901 return projectCodeValidation;
903 validateServiceTypeAndCleanup(service);
905 Either<Boolean, ResponseFormat> serviceRoleValidation = validateServiceRoleAndCleanup(user, service, actionEnum);
906 if (serviceRoleValidation.isRight()) {
907 return serviceRoleValidation;
909 return validateInstantiationTypeValue(user, service, actionEnum);
910 } catch (ComponentException exception) {
911 ResponseFormat responseFormat = componentsUtils.getResponseFormat(exception);
912 componentsUtils.auditComponentAdmin(responseFormat, user, service,
913 AuditingActionEnum.CREATE_SERVICE, ComponentTypeEnum.SERVICE);
914 return Either.right(responseFormat);
918 private Either<Boolean, ResponseFormat> validateServiceCategory(User user, Service service, AuditingActionEnum actionEnum) {
919 log.debug("validate Service category");
920 if (isEmpty(service.getCategories())) {
921 ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.COMPONENT_MISSING_CATEGORY, ComponentTypeEnum.SERVICE.getValue());
922 componentsUtils.auditComponentAdmin(errorResponse, user, service, actionEnum, ComponentTypeEnum.SERVICE);
923 return Either.right(errorResponse);
925 Either<Boolean, ResponseFormat> validatCategory = validateServiceCategory(service.getCategories());
926 if (validatCategory.isRight()) {
927 ResponseFormat responseFormat = validatCategory.right().value();
928 componentsUtils.auditComponentAdmin(responseFormat, user, service, actionEnum, ComponentTypeEnum.SERVICE);
929 return Either.right(responseFormat);
931 return Either.left(true);
934 public Either<Map<String, Boolean>, ResponseFormat> validateServiceNameExists(String serviceName, String userId) {
935 validateUserExists(userId, "validate Service Name Exists", false);
937 Either<Boolean, StorageOperationStatus> dataModelResponse = toscaOperationFacade.validateComponentNameUniqueness(serviceName, null, ComponentTypeEnum.SERVICE);
941 if (dataModelResponse.isLeft()) {
942 Map<String, Boolean> result = new HashMap<>();
943 result.put("isValid", dataModelResponse.left().value());
944 log.debug("validation was successfully performed.");
945 return Either.left(result);
947 ResponseFormat responseFormat = componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(dataModelResponse.right().value()));
948 return Either.right(responseFormat);
951 public void setElementDao(IElementOperation elementDao) {
952 this.elementDao = elementDao;
955 public void setCassandraAuditingDao(AuditCassandraDao auditingDao) {
956 this.auditCassandraDao = auditingDao;
959 public ArtifactsBusinessLogic getArtifactBl() {
960 return artifactsBusinessLogic;
963 public void setArtifactBl(ArtifactsBusinessLogic artifactBl) {
964 this.artifactsBusinessLogic = artifactBl;
967 public Either<Service, ResponseFormat> updateServiceMetadata(String serviceId, Service serviceUpdate, User user) {
968 user = validateUser(user, "updateServiceMetadata", serviceUpdate, null, false);
969 // validate user role
970 validateUserRole(user, serviceUpdate, new ArrayList<>(), null, null);
972 Either<Service, StorageOperationStatus> storageStatus = toscaOperationFacade.getToscaElement(serviceId);
973 if (storageStatus.isRight()) {
974 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE), ""));
977 Service currentService = storageStatus.left().value();
979 if (!ComponentValidationUtils.canWorkOnComponent(currentService, user.getUserId())) {
980 log.info("Restricted operation for user: {}, on service: {}", user.getUserId(), currentService.getCreatorUserId());
981 return Either.right(componentsUtils.getResponseFormat(ActionStatus.RESTRICTED_OPERATION));
984 Either<Service, ResponseFormat> validationRsponse = validateAndUpdateServiceMetadata(user, currentService, serviceUpdate);
985 if (validationRsponse.isRight()) {
986 log.info("service update metadata: validations field.");
987 return validationRsponse;
989 Service serviceToUpdate = validationRsponse.left().value();
992 Either<Boolean, ResponseFormat> lockResult = lockComponent(serviceId, currentService, "Update Service Metadata");
993 if (lockResult.isRight()) {
994 return Either.right(lockResult.right().value());
997 Either<Service, StorageOperationStatus> updateResponse = toscaOperationFacade.updateToscaElement(serviceToUpdate);
998 if (updateResponse.isRight()) {
1000 BeEcompErrorManager.getInstance().logBeSystemError("Update Service Metadata");
1001 log.debug("failed to update sevice {}", serviceToUpdate.getUniqueId());
1002 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
1005 return Either.left(updateResponse.left().value());
1007 graphLockOperation.unlockComponent(serviceId, NodeTypeEnum.Service);
1011 public Either<Set<String>, ResponseFormat> deleteForwardingPaths(String serviceId, Set<String> pathIdsToDelete, User user, boolean lock) {
1012 Service serviceToDelete = initServiceToDeletePaths(serviceId, pathIdsToDelete);
1013 user = validateUser(user, "deleteForwardingPaths", serviceToDelete, null, false);
1014 // validate user role
1015 validateUserRole(user, serviceToDelete, new ArrayList<>(), null, null);
1016 Either<Service, StorageOperationStatus> storageStatus = toscaOperationFacade.getToscaElement(serviceId);
1017 if (storageStatus.isRight()) {
1018 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE), ""));
1020 Service service = storageStatus.left().value();
1021 Either<Set<String>, StorageOperationStatus> result = null;
1023 Either<Boolean, ResponseFormat> lockResult = lockComponent(service.getUniqueId(), service, "Delete Forwarding Path on Service");
1024 if (lockResult.isRight()) {
1025 titanDao.rollback();
1026 return Either.right(componentsUtils.getResponseFormat(componentsUtils
1027 .convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE), ""));
1031 result = forwardingPathOperation.deleteForwardingPath(service ,pathIdsToDelete);
1032 if (result.isRight()) {
1033 log.debug(FAILED_TO_LOCK_SERVICE_RESPONSE_IS, service.getName(), result.right().value());
1034 titanDao.rollback();
1035 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE)));
1038 log.debug(THE_SERVICE_WITH_SYSTEM_NAME_LOCKED, service.getSystemName());
1040 } catch (Exception e){
1041 log.error("Exception occurred during delete forwarding path : {}", e.getMessage(), e);
1042 titanDao.rollback();
1043 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
1045 graphLockOperation.unlockComponent(service.getUniqueId(), NodeTypeEnum.Service);
1047 return Either.left(result.left().value());
1050 private Service initServiceToDeletePaths(String serviceId, Collection<String> pathIdsToDelete) {
1051 Service serviceToDelete = new Service();
1052 serviceToDelete.setUniqueId(serviceId);
1053 serviceToDelete.setForwardingPaths(new HashMap<>());
1054 pathIdsToDelete.forEach(pathIdToDelete -> serviceToDelete.getForwardingPaths().put(pathIdToDelete, new ForwardingPathDataDefinition()));
1055 return serviceToDelete;
1058 public Either<Service, ResponseFormat> updateForwardingPath(String serviceId, Service serviceUpdate, User user, boolean lock) {
1059 return createOrUpdateForwardingPath(serviceId, serviceUpdate, user, true,"updateForwardingPath", lock);
1062 public Either<Service, ResponseFormat> createForwardingPath(String serviceId, Service serviceUpdate, User user, boolean lock) {
1063 return createOrUpdateForwardingPath(serviceId, serviceUpdate, user, false, "createForwardingPath", lock);
1066 private ForwardingPathDataDefinition getTrimmedValues(ForwardingPathDataDefinition path){
1067 ForwardingPathDataDefinition dataDefinition = new ForwardingPathDataDefinition(path.getName());
1068 dataDefinition.setName(Strings.nullToEmpty(path.getName()).trim());
1069 dataDefinition.setProtocol(Strings.nullToEmpty(path.getProtocol()).trim());
1070 dataDefinition.setDestinationPortNumber(Strings.nullToEmpty(path.getDestinationPortNumber()).trim());
1071 dataDefinition.setUniqueId(path.getUniqueId());
1072 dataDefinition.setPathElements(path.getPathElements());
1073 dataDefinition.setDescription(path.getDescription());
1074 dataDefinition.setToscaResourceName(path.getToscaResourceName());
1075 return dataDefinition;
1078 private Either<Service, ResponseFormat> createOrUpdateForwardingPath(String serviceId, Service serviceUpdate, User user, boolean isUpdate, String errorContext, boolean lock) {
1079 validateUserAndRole(serviceUpdate, user, errorContext);
1081 Map<String, ForwardingPathDataDefinition> forwardingPaths = serviceUpdate.getForwardingPaths();
1083 Map<String, ForwardingPathDataDefinition> trimmedForwardingPaths =
1084 forwardingPaths.entrySet().stream().collect(Collectors.toMap(Map.Entry::getKey,
1085 entry -> new ForwardingPathDataDefinition(getTrimmedValues(entry.getValue()))));
1087 Either<Boolean, ResponseFormat> booleanResponseFormatEither = forwardingPathValidator.validateForwardingPaths(trimmedForwardingPaths.values(),
1088 serviceId, isUpdate);
1089 if(booleanResponseFormatEither.isRight()){
1090 return Either.right(booleanResponseFormatEither.right().value());
1093 Either<Service, StorageOperationStatus> serviceStorageOperationStatusEither = toscaOperationFacade.getToscaElement(serviceId);
1095 if(serviceStorageOperationStatusEither.isRight()){
1096 StorageOperationStatus errorStatus = serviceStorageOperationStatusEither.right().value();
1097 log.debug("Failed to fetch service information by service id, error {}", errorStatus);
1098 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(errorStatus)));
1100 Service storedService = serviceStorageOperationStatusEither.left().value();
1102 Either<ForwardingPathDataDefinition, StorageOperationStatus> result;
1103 Either<Component, StorageOperationStatus> forwardingPathOrigin = toscaOperationFacade.getLatestByName(ForwardingPathUtils.FORWARDING_PATH_NODE_NAME);
1104 if (forwardingPathOrigin.isRight()) {
1105 StorageOperationStatus errorStatus = forwardingPathOrigin.right().value();
1106 log.debug("Failed to fetch normative forwarding path resource by tosca name, error {}", errorStatus);
1107 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(errorStatus)));
1109 Component component = forwardingPathOrigin.left().value();
1110 final String toscaResourceName;
1111 if ( component.getComponentType() == ComponentTypeEnum.RESOURCE) {
1112 toscaResourceName = ((Resource) component).getToscaResourceName();
1114 toscaResourceName = "";
1116 Either<Boolean, ResponseFormat> lockResult = null;
1119 lockComponent(storedService.getUniqueId(), storedService, "Add or Update Forwarding Path on Service");
1120 if (lockResult.isRight()) {
1121 log.debug(FAILED_TO_LOCK_SERVICE_RESPONSE_IS, storedService.getName(),
1122 lockResult.right().value().getFormattedMessage());
1123 return Either.right(lockResult.right().value());
1125 log.debug(THE_SERVICE_WITH_SYSTEM_NAME_LOCKED, storedService.getSystemName());
1128 Map<String, ForwardingPathDataDefinition> resultMap = new HashMap<>();
1130 trimmedForwardingPaths.values().forEach(fp -> fp.setToscaResourceName(toscaResourceName));
1133 for (ForwardingPathDataDefinition forwardingPathDataDefinition : trimmedForwardingPaths.values()) {
1135 result = forwardingPathOperation.updateForwardingPath(serviceId, forwardingPathDataDefinition);
1137 result = forwardingPathOperation.addForwardingPath(serviceId, forwardingPathDataDefinition);
1139 if (result.isRight()) {
1140 titanDao.rollback();
1141 return Either.right(componentsUtils.getResponseFormat(
1142 componentsUtils.convertFromStorageResponse(result.right().value(), ComponentTypeEnum.SERVICE),
1145 ForwardingPathDataDefinition fpDataDefinition = result.left().value();
1146 resultMap.put(fpDataDefinition.getUniqueId(), forwardingPathDataDefinition);
1150 } catch (Exception e) {
1151 titanDao.rollback();
1152 log.error("Exception occurred during add or update forwarding path property values: {}", e.getMessage(),
1154 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
1158 if (lockResult != null && lockResult.isLeft() && lockResult.left().value()) {
1159 graphLockOperation.unlockComponent(storedService.getUniqueId(), NodeTypeEnum.Service);
1162 Service service = createServiceWithForwardingPathForResponse(serviceId, resultMap);
1163 return Either.left(service);
1166 private Service createServiceWithForwardingPathForResponse(String serviceId, Map<String,ForwardingPathDataDefinition> forwardingPathDataDefinitionMap) {
1167 Service service = new Service();
1168 service.setUniqueId(serviceId);
1169 service.setForwardingPaths(forwardingPathDataDefinitionMap);
1173 private void validateUserAndRole(Service serviceUpdate, User user, String errorContext) {
1174 user = validateUser(user, errorContext, serviceUpdate, null, false);
1175 validateUserRole(user, serviceUpdate, new ArrayList<>(), null, null);
1180 Either<Service, ResponseFormat> validateAndUpdateServiceMetadata(User user, Service currentService, Service serviceUpdate) {
1183 boolean hasBeenCertified = ValidationUtils.hasBeenCertified(currentService.getVersion());
1184 Either<Boolean, ResponseFormat> response = validateAndUpdateCategory(user, currentService, serviceUpdate, hasBeenCertified, UPDATE_SERVICE_METADATA);
1185 if (response.isRight()) {
1186 ResponseFormat errorResponse = response.right().value();
1187 return Either.right(errorResponse);
1190 verifyValuesAreIdentical(serviceUpdate.getCreatorUserId(), currentService.getCreatorUserId(), "creatorUserId");
1191 verifyValuesAreIdentical(serviceUpdate.getCreatorFullName(), currentService.getCreatorFullName(), "creatorFullName");
1192 verifyValuesAreIdentical(serviceUpdate.getLastUpdaterUserId(), currentService.getLastUpdaterUserId(), "lastUpdaterUserId");
1193 verifyValuesAreIdentical(serviceUpdate.getLastUpdaterFullName(), currentService.getLastUpdaterFullName(), "lastUpdaterFullName");
1195 response = validateAndUpdateServiceName(user, currentService, serviceUpdate, hasBeenCertified, null);
1196 if (response.isRight()) {
1197 return Either.right(response.right().value());
1200 verifyValuesAreIdentical(serviceUpdate.getDistributionStatus(), currentService.getDistributionStatus(), "distributionStatus");
1202 if (serviceUpdate.getProjectCode() != null) {
1203 response = validateAndUpdateProjectCode(user, currentService, serviceUpdate, UPDATE_SERVICE_METADATA);
1204 if (response.isRight()) {
1205 return Either.right(response.right().value());
1209 response = validateAndUpdateIcon(user, currentService, serviceUpdate, hasBeenCertified, UPDATE_SERVICE_METADATA);
1210 if (response.isRight()) {
1211 return Either.right(response.right().value());
1214 verifyValuesAreIdentical(serviceUpdate.getCreationDate(), currentService.getCreationDate(), "creationDate");
1215 verifyValuesAreIdentical(serviceUpdate.getVersion(), currentService.getVersion(), "version");
1217 response = validateAndUpdateDescription(user, currentService, serviceUpdate, UPDATE_SERVICE_METADATA);
1218 if (response.isRight()) {
1219 return Either.right(response.right().value());
1222 response = validateAndUpdateTags(user, currentService, serviceUpdate, UPDATE_SERVICE_METADATA);
1223 if (response.isRight()) {
1224 return Either.right(response.right().value());
1227 response = validateAndUpdateContactId(user, currentService, serviceUpdate, UPDATE_SERVICE_METADATA);
1228 if (response.isRight()) {
1229 return Either.right(response.right().value());
1232 verifyValuesAreIdentical(serviceUpdate.getLastUpdateDate(), currentService.getLastUpdateDate(), "lastUpdateDate");
1233 verifyValuesAreIdentical(serviceUpdate.getLifecycleState(), currentService.getLifecycleState(), "lifecycleState");
1234 verifyValuesAreIdentical(serviceUpdate.isHighestVersion(), currentService.isHighestVersion(), "isHighestVersion");
1235 verifyValuesAreIdentical(serviceUpdate.getUUID(), currentService.getUUID(), "uuid");
1237 validateAndUpdateServiceType(currentService, serviceUpdate);
1239 response = validateAndUpdateServiceRole(user, currentService, serviceUpdate, UPDATE_SERVICE_METADATA);
1240 if (response.isRight()) {
1241 return Either.right(response.right().value());
1244 response = validateAndUpdateInstantiationTypeValue(user, currentService, serviceUpdate, UPDATE_SERVICE_METADATA);
1245 if (response.isRight()) {
1246 return Either.right(response.right().value());
1249 verifyValuesAreIdentical(serviceUpdate.getInvariantUUID(), currentService.getInvariantUUID(), "invariantUUID");
1251 validateAndUpdateEcompNaming(currentService, serviceUpdate);
1253 currentService.setEnvironmentContext(serviceUpdate.getEnvironmentContext());
1254 return Either.left(currentService);
1256 } catch (ComponentException exception) {
1257 ResponseFormat responseFormat = componentsUtils.getResponseFormat(exception);
1258 componentsUtils.auditComponentAdmin(responseFormat, user, serviceUpdate,
1259 AuditingActionEnum.UPDATE_SERVICE_METADATA, ComponentTypeEnum.SERVICE);
1260 return Either.right(responseFormat);
1264 private void verifyValuesAreIdentical(Object updatedValue, Object originalValue, String fieldName) {
1265 if (updatedValue != null && !updatedValue.equals(originalValue)) {
1266 log.info("update service: received request to update {} to {} the field is not updatable ignoring.", fieldName, updatedValue);
1270 private void validateAndUpdateEcompNaming(Service currentService, Service serviceUpdate) {
1271 Boolean isEcompGeneratedCurr = currentService.isEcompGeneratedNaming();
1272 Boolean isEcompGeneratedUpdate = serviceUpdate.isEcompGeneratedNaming();
1273 if (isEcompGeneratedUpdate != null && !isEcompGeneratedUpdate.equals(isEcompGeneratedCurr)) {
1274 currentService.setEcompGeneratedNaming(isEcompGeneratedUpdate);
1276 String namingPolicyUpdate = serviceUpdate.getNamingPolicy();
1277 if (currentService.isEcompGeneratedNaming()) {
1278 currentService.setNamingPolicy(namingPolicyUpdate);
1280 if (!StringUtils.isEmpty(namingPolicyUpdate)) {
1281 log.warn("NamingPolicy must be empty for EcompGeneratedNaming=false");
1283 currentService.setNamingPolicy("");
1287 private Either<Boolean, ResponseFormat> validateAndUpdateContactId(User user, Service currentService, Service serviceUpdate, AuditingActionEnum audatingAction) {
1288 String contactIdUpdated = serviceUpdate.getContactId();
1289 String contactIdCurrent = currentService.getContactId();
1290 if (!contactIdCurrent.equals(contactIdUpdated)) {
1291 validateContactId(user, serviceUpdate, audatingAction);
1292 currentService.setContactId(contactIdUpdated.toLowerCase());
1294 return Either.left(true);
1297 private Either<Boolean, ResponseFormat> validateAndUpdateTags(User user, Service currentService, Service serviceUpdate, AuditingActionEnum audatingAction) {
1298 List<String> tagsUpdated = serviceUpdate.getTags();
1299 List<String> tagsCurrent = currentService.getTags();
1300 if (tagsUpdated == null || tagsUpdated.isEmpty()) {
1301 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.COMPONENT_MISSING_TAGS);
1302 componentsUtils.auditComponentAdmin(responseFormat, user, serviceUpdate, audatingAction, ComponentTypeEnum.SERVICE);
1303 return Either.right(responseFormat);
1306 if (!(tagsCurrent.containsAll(tagsUpdated) && tagsUpdated.containsAll(tagsCurrent))) {
1307 validateTagsListAndRemoveDuplicates(user, serviceUpdate, audatingAction);
1308 currentService.setTags(tagsUpdated);
1310 return Either.left(true);
1313 private Either<Boolean, ResponseFormat> validateAndUpdateDescription(User user, Service currentService, Service serviceUpdate, AuditingActionEnum audatingAction) {
1314 String descriptionUpdated = serviceUpdate.getDescription();
1315 String descriptionCurrent = currentService.getDescription();
1316 if (!descriptionCurrent.equals(descriptionUpdated)) {
1317 validateDescriptionAndCleanup(user, serviceUpdate, audatingAction);
1318 currentService.setDescription(serviceUpdate.getDescription());
1320 return Either.left(true);
1323 private Either<Boolean, ResponseFormat> validateAndUpdateProjectCode(User user, Service currentService, Service serviceUpdate, AuditingActionEnum audatingAction) {
1324 String projectCodeUpdated = serviceUpdate.getProjectCode();
1325 String projectCodeCurrent = currentService.getProjectCode();
1326 if (!projectCodeCurrent.equals(projectCodeUpdated)) {
1328 Either<Boolean, ResponseFormat> validatProjectCodeResponse = validateProjectCode(user, serviceUpdate, audatingAction);
1329 if (validatProjectCodeResponse.isRight()) {
1330 ResponseFormat errorRespons = validatProjectCodeResponse.right().value();
1331 return Either.right(errorRespons);
1333 currentService.setProjectCode(projectCodeUpdated);
1336 return Either.left(true);
1339 private Either<Boolean, ResponseFormat> validateAndUpdateIcon(User user, Service currentService, Service serviceUpdate, boolean hasBeenCertified, AuditingActionEnum audatingAction) {
1340 String iconUpdated = serviceUpdate.getIcon();
1341 String iconCurrent = currentService.getIcon();
1342 if (!iconCurrent.equals(iconUpdated)) {
1343 if (!hasBeenCertified) {
1344 validateIcon(user, serviceUpdate, audatingAction);
1345 currentService.setIcon(iconUpdated);
1347 log.info("icon {} cannot be updated once the service has been certified once.", iconUpdated);
1348 ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.SERVICE_ICON_CANNOT_BE_CHANGED);
1349 return Either.right(errorResponse);
1352 return Either.left(true);
1355 private Either<Boolean, ResponseFormat> validateAndUpdateServiceName(User user, Service currentService, Service serviceUpdate, boolean hasBeenCertified, AuditingActionEnum auditingAction) {
1356 String serviceNameUpdated = serviceUpdate.getName();
1357 String serviceNameCurrent = currentService.getName();
1358 if (!serviceNameCurrent.equals(serviceNameUpdated)) {
1359 if (!hasBeenCertified) {
1360 validateComponentName(user, serviceUpdate, auditingAction);
1361 Either<Boolean, ResponseFormat> serviceNameUniquenessValidation = validateComponentNameUnique(user, serviceUpdate, auditingAction);
1362 if (serviceNameUniquenessValidation.isRight()) {
1363 return serviceNameUniquenessValidation;
1365 currentService.setName(serviceNameUpdated);
1366 currentService.getComponentMetadataDefinition().getMetadataDataDefinition().setNormalizedName(ValidationUtils.normaliseComponentName(serviceNameUpdated));
1367 currentService.getComponentMetadataDefinition().getMetadataDataDefinition().setSystemName(ValidationUtils.convertToSystemName(serviceNameUpdated));
1370 log.info("service name {} cannot be updated once the service has been certified once.", serviceNameUpdated);
1371 ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.SERVICE_NAME_CANNOT_BE_CHANGED);
1372 return Either.right(errorResponse);
1375 return Either.left(true);
1378 private void validateAndUpdateServiceType(Service currentService, Service updatedService) {
1379 String updatedServiceType = updatedService.getServiceType();
1380 String currentServiceType = currentService.getServiceType();
1381 if (!currentServiceType.equals(updatedServiceType)) {
1382 validateServiceTypeAndCleanup(updatedService);
1383 currentService.setServiceType(updatedServiceType);
1387 private void validateServiceTypeAndCleanup(Component component) {
1388 log.debug("validate service type");
1389 String serviceType = ((Service)component).getServiceType();
1390 if (serviceType == null) {
1391 log.info("service type is not valid.");
1392 throw new ComponentException(ActionStatus.INVALID_SERVICE_TYPE);
1394 serviceType = cleanUpText(serviceType);
1395 validateServiceType(serviceType);
1399 private void validateServiceType(String serviceType) {
1400 if (serviceType.isEmpty()) {
1403 if (!ValidationUtils.validateServiceTypeLength(serviceType)) {
1404 log.info("service type exceeds limit.");
1405 throw new ComponentException(ActionStatus.SERVICE_TYPE_EXCEEDS_LIMIT, "" + ValidationUtils.SERVICE_TYPE_MAX_LENGTH);
1407 if (!ValidationUtils.validateIsEnglish(serviceType)) {
1408 log.info("service type is not valid.");
1409 throw new ComponentException(ActionStatus.INVALID_SERVICE_TYPE);
1413 private Either<Boolean, ResponseFormat> validateAndUpdateServiceRole(User user, Service currentService, Service updatedService, AuditingActionEnum auditingAction) {
1414 String updatedServiceRole = updatedService.getServiceRole();
1415 String currentServiceRole = currentService.getServiceRole();
1416 if (!currentServiceRole.equals(updatedServiceRole)) {
1417 Either<Boolean, ResponseFormat> validateServiceRole = validateServiceRoleAndCleanup(user, updatedService , auditingAction);
1418 if (validateServiceRole.isRight()) {
1419 ResponseFormat errorResponse = validateServiceRole.right().value();
1420 componentsUtils.auditComponentAdmin(errorResponse, user, updatedService, auditingAction, ComponentTypeEnum.SERVICE);
1421 return Either.right(errorResponse);
1423 currentService.setServiceRole(updatedServiceRole);
1425 return Either.left(true);
1428 protected Either<Boolean, ResponseFormat> validateServiceRoleAndCleanup(User user, Component component, AuditingActionEnum actionEnum) {
1429 log.debug("validate service role");
1430 String serviceRole = ((Service)component).getServiceRole();
1431 if (serviceRole != null){
1432 serviceRole = cleanUpText(serviceRole);
1434 Either<Boolean, ResponseFormat> validateServiceRole = validateServiceRole(serviceRole);
1435 if (validateServiceRole.isRight()) {
1436 ResponseFormat responseFormat = validateServiceRole.right().value();
1437 componentsUtils.auditComponentAdmin(responseFormat, user, component, actionEnum, ComponentTypeEnum.SERVICE);
1438 return Either.right(responseFormat);
1440 return Either.left(true);
1442 return Either.left(false);
1446 private Either<Boolean, ResponseFormat> validateAndUpdateInstantiationTypeValue(User user, Service currentService, Service updatedService, AuditingActionEnum auditingAction) {
1447 String updatedInstaType= updatedService.getInstantiationType();
1448 String currentInstaType = currentService.getInstantiationType();
1449 if (!currentInstaType.equals(updatedInstaType)) {
1450 Either<Boolean, ResponseFormat> validateInstantiationType = validateInstantiationTypeValue(user, updatedService , auditingAction);
1451 if (validateInstantiationType.isRight()) {
1452 ResponseFormat errorResponse = validateInstantiationType.right().value();
1453 componentsUtils.auditComponentAdmin(errorResponse, user, updatedService, auditingAction, ComponentTypeEnum.SERVICE);
1454 return Either.right(errorResponse);
1456 currentService.setInstantiationType(updatedInstaType);
1458 return Either.left(true);
1461 private Either<Boolean, ResponseFormat> validateInstantiationTypeValue(User user, Service service, AuditingActionEnum actionEnum) {
1462 log.debug("validate instantiation type");
1463 String instantiationType = service.getInstantiationType();
1464 if (!InstantiationTypes.containsName(instantiationType) || instantiationType == null){
1465 log.error("Recieved Instantiation type {} is not valid.", instantiationType);
1466 ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.INVALID_INSTANTIATION_TYPE);
1467 componentsUtils.auditComponentAdmin(errorResponse, user, service, actionEnum, ComponentTypeEnum.SERVICE);
1468 return Either.right(errorResponse);
1470 return Either.left(true);
1473 private Either<Boolean, ResponseFormat> validateServiceRole(String serviceRole) {
1474 if (serviceRole.equals("")){
1475 return Either.left(true);
1477 if (!ValidationUtils.validateServiceRoleLength(serviceRole)) {
1478 log.info("service role exceeds limit.");
1479 ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.SERVICE_ROLE_EXCEEDS_LIMIT, "" + ValidationUtils.SERVICE_ROLE_MAX_LENGTH);
1480 return Either.right(errorResponse);
1483 if (!ValidationUtils.validateIsEnglish(serviceRole)) {
1484 log.info("service role is not valid.");
1485 ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.INVALID_SERVICE_ROLE);
1486 return Either.right(errorResponse);
1488 return Either.left(true);
1492 private Either<Boolean, ResponseFormat> validateAndUpdateCategory(User user, Service currentService, Service serviceUpdate, boolean hasBeenCertified, AuditingActionEnum audatingAction) {
1493 List<CategoryDefinition> categoryUpdated = serviceUpdate.getCategories();
1494 List<CategoryDefinition> categoryCurrent = currentService.getCategories();
1495 Either<Boolean, ResponseFormat> validateCategoryResponse = validateServiceCategory(user, serviceUpdate, audatingAction);
1496 if (validateCategoryResponse.isRight()) {
1497 return Either.right(validateCategoryResponse.right().value());
1499 if (!categoryCurrent.get(0).getName().equals(categoryUpdated.get(0).getName())) {
1500 if (!hasBeenCertified) {
1501 currentService.setCategories(categoryUpdated);
1503 log.info("category {} cannot be updated once the service has been certified once.", categoryUpdated);
1504 ResponseFormat errorResponse = componentsUtils.getResponseFormat(ActionStatus.SERVICE_CATEGORY_CANNOT_BE_CHANGED);
1505 return Either.right(errorResponse);
1508 return Either.left(true);
1512 private Either<Boolean, ResponseFormat> validateServiceCategory(List<CategoryDefinition> list) {
1514 if (list.size() > 1) {
1515 log.debug("Must be only one category for service");
1516 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.COMPONENT_TOO_MUCH_CATEGORIES, ComponentTypeEnum.SERVICE.getValue());
1517 return Either.right(responseFormat);
1519 CategoryDefinition category = list.get(0);
1520 if (category.getSubcategories() != null) {
1521 log.debug("Subcategories cannot be defined for service");
1522 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.SERVICE_CANNOT_CONTAIN_SUBCATEGORY);
1523 return Either.right(responseFormat);
1525 if (!ValidationUtils.validateStringNotEmpty(category.getName())) {
1526 log.debug("Resource category is empty");
1527 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.COMPONENT_MISSING_CATEGORY, ComponentTypeEnum.SERVICE.getValue());
1528 return Either.right(responseFormat);
1531 log.debug("validating service category {} against valid categories list", list);
1532 Either<List<CategoryDefinition>, ActionStatus> categorys = elementDao.getAllServiceCategories();
1533 if (categorys.isRight()) {
1534 log.debug("failed to retrieve service categories from Titan");
1535 ResponseFormat responseFormat = componentsUtils.getResponseFormat(categorys.right().value());
1536 return Either.right(responseFormat);
1538 List<CategoryDefinition> categoryList = categorys.left().value();
1539 for (CategoryDefinition value : categoryList) {
1540 if (value.getName().equals(category.getName())) {
1541 return Either.left(true);
1544 log.debug("Category {} is not part of service category group. Service category valid values are {}", list, categoryList);
1545 return Either.right(componentsUtils.getResponseFormat(ActionStatus.COMPONENT_INVALID_CATEGORY, ComponentTypeEnum.SERVICE.getValue()));
1547 return Either.left(false);
1550 public Either<ServiceRelations, ResponseFormat> getServiceComponentsRelations(String serviceId, User user) {
1551 Either<Service, ResponseFormat> serviceResponseFormatEither = getService(serviceId, user);
1552 if (serviceResponseFormatEither.isRight()){
1553 return Either.right(serviceResponseFormatEither.right().value());
1555 final ServiceRelations serviceRelations = new ForwardingPathUtils().convertServiceToServiceRelations(serviceResponseFormatEither.left().value());
1556 return Either.left(serviceRelations);
1561 public ResponseFormat deleteService(String serviceId, User user) {
1562 ResponseFormat responseFormat;
1563 String ecompErrorContext = "delete service";
1565 validateUserExists(user, ecompErrorContext, false);
1566 Either<Service, StorageOperationStatus> serviceStatus = toscaOperationFacade.getToscaElement(serviceId);
1567 if (serviceStatus.isRight()) {
1568 log.debug("failed to get service {}", serviceId);
1569 return componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(serviceStatus.right().value()), "");
1572 Service service = serviceStatus.left().value();
1574 StorageOperationStatus result = StorageOperationStatus.OK;
1575 Either<Boolean, ResponseFormat> lockResult = lockComponent(service, "Mark service to delete");
1576 if (lockResult.isRight()) {
1577 return lockResult.right().value();
1580 result = markComponentToDelete(service);
1581 if (result.equals(StorageOperationStatus.OK)) {
1582 responseFormat = componentsUtils.getResponseFormat(ActionStatus.NO_CONTENT);
1584 ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(result);
1585 responseFormat = componentsUtils.getResponseFormatByResource(actionStatus, service.getName());
1587 return responseFormat;
1589 if (result == null || !result.equals(StorageOperationStatus.OK)) {
1590 log.warn("operation failed. do rollback");
1591 BeEcompErrorManager.getInstance().logBeSystemError("Delete Service");
1592 titanDao.rollback();
1594 log.debug("operation success. do commit");
1597 graphLockOperation.unlockComponent(serviceId, NodeTypeEnum.Service);
1601 public ResponseFormat deleteServiceByNameAndVersion(String serviceName, String version, User user) {
1602 ResponseFormat responseFormat;
1603 String ecompErrorContext = "delete service";
1604 validateUserNotEmpty(user, ecompErrorContext);
1605 user = validateUserExists(user, ecompErrorContext, false);
1607 Either<Service, ResponseFormat> getResult = getServiceByNameAndVersion(serviceName, version, user.getUserId());
1608 if (getResult.isRight()) {
1609 return getResult.right().value();
1611 Service service = getResult.left().value();
1613 StorageOperationStatus result = StorageOperationStatus.OK;
1614 Either<Boolean, ResponseFormat> lockResult = lockComponent(service, "Mark service to delete");
1615 if (lockResult.isRight()) {
1616 result = StorageOperationStatus.GENERAL_ERROR;
1617 return componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR);
1621 result = markComponentToDelete(service);
1622 if (result.equals(StorageOperationStatus.OK)) {
1623 responseFormat = componentsUtils.getResponseFormat(ActionStatus.NO_CONTENT);
1625 ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(result);
1626 responseFormat = componentsUtils.getResponseFormatByResource(actionStatus, service.getName());
1628 return responseFormat;
1631 if (result == null || !result.equals(StorageOperationStatus.OK)) {
1632 log.warn("operation failed. do rollback");
1633 BeEcompErrorManager.getInstance().logBeSystemError("Delete Service");
1634 titanDao.rollback();
1636 log.debug("operation success. do commit");
1639 graphLockOperation.unlockComponent(service.getUniqueId(), NodeTypeEnum.Service);
1643 public Either<Service, ResponseFormat> getService(String serviceId, User user) {
1644 String ecompErrorContext = "Get service";
1645 validateUserNotEmpty(user, ecompErrorContext);
1646 validateUserExists(user, ecompErrorContext, false);
1648 Either<Service, StorageOperationStatus> storageStatus = toscaOperationFacade.getToscaElement(serviceId);
1649 if (storageStatus.isRight()) {
1650 log.debug("failed to get service by id {}", serviceId);
1651 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE), serviceId));
1654 if(!(storageStatus.left().value() instanceof Service)){
1655 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(StorageOperationStatus.NOT_FOUND), serviceId));
1657 Service service = storageStatus.left().value();
1658 return Either.left(service);
1665 public Either<Service, ResponseFormat> getServiceByNameAndVersion(String serviceName, String serviceVersion, String userId) {
1666 validateUserExists(userId, "get Service By Name And Version", false);
1667 Either<Service, StorageOperationStatus> storageStatus = toscaOperationFacade.getComponentByNameAndVersion(ComponentTypeEnum.SERVICE, serviceName, serviceVersion);
1668 if (storageStatus.isRight()) {
1669 log.debug("failed to get service by name {} and version {}", serviceName, serviceVersion);
1670 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE), serviceName));
1672 Service service = storageStatus.left().value();
1673 return Either.left(service);
1676 @SuppressWarnings("unchecked")
1677 private void createMandatoryArtifactsData(Service service, User user) {
1678 // create mandatory artifacts
1680 // TODO it must be removed after that artifact uniqueId creation will be
1681 // moved to ArtifactOperation
1682 String serviceUniqueId = service.getUniqueId();
1683 Map<String, ArtifactDefinition> artifactMap = service.getArtifacts();
1684 if (artifactMap == null)
1685 artifactMap = new HashMap<>();
1687 Map<String, Object> informationalServiceArtifacts = ConfigurationManager.getConfigurationManager().getConfiguration().getInformationalServiceArtifacts();
1688 List<String> exludeServiceCategory = ConfigurationManager.getConfigurationManager().getConfiguration().getExcludeServiceCategory();
1690 String category = service.getCategories().get(0).getName();
1691 boolean isCreateArtifact = true;
1692 if (category != null && exludeServiceCategory != null && !exludeServiceCategory.isEmpty()) {
1693 for (String exlude : exludeServiceCategory) {
1694 if (exlude.equalsIgnoreCase(category)) {
1695 isCreateArtifact = false;
1702 if (informationalServiceArtifacts != null && isCreateArtifact) {
1703 Set<String> keys = informationalServiceArtifacts.keySet();
1704 for (String informationalServiceArtifactName : keys) {
1705 Map<String, Object> artifactInfoMap = (Map<String, Object>) informationalServiceArtifacts.get(informationalServiceArtifactName);
1706 ArtifactDefinition artifactDefinition = createArtifactDefinition(serviceUniqueId, informationalServiceArtifactName, artifactInfoMap, user, false);
1707 artifactMap.put(artifactDefinition.getArtifactLabel(), artifactDefinition);
1711 service.setArtifacts(artifactMap);
1715 private ArtifactDefinition createArtifactDefinition(String serviceId, String logicalName, Map<String, Object> artifactInfoMap, User user, Boolean isServiceApi) {
1717 ArtifactDefinition artifactInfo = artifactsBusinessLogic.createArtifactPlaceHolderInfo(serviceId, logicalName, artifactInfoMap, user, ArtifactGroupTypeEnum.INFORMATIONAL);
1720 artifactInfo.setMandatory(false);
1721 artifactInfo.setServiceApi(true);
1723 return artifactInfo;
1726 private Either<DistributionTransitionEnum, ResponseFormat> validateTransitionEnum(String distributionTransition) {
1727 DistributionTransitionEnum transitionEnum = null;
1729 transitionEnum = DistributionTransitionEnum.getFromDisplayName(distributionTransition);
1730 if (transitionEnum == null) {
1731 BeEcompErrorManager.getInstance().logBeSystemError(CHANGE_SERVICE_DISTRIBUTION);
1732 log.info("state operation is not valid. operations allowed are: {}", DistributionTransitionEnum.valuesAsString());
1733 ResponseFormat error = componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR);
1734 return Either.right(error);
1737 return Either.left(transitionEnum);
1740 private Either<String, ResponseFormat> validateComment(LifecycleChangeInfoWithAction comment) {
1741 String data = comment.getUserRemarks();
1743 if (data == null || data.trim().isEmpty()) {
1744 BeEcompErrorManager.getInstance().logBeInvalidJsonInput(CHANGE_SERVICE_DISTRIBUTION);
1745 log.debug("user comment cannot be empty or null.");
1746 return Either.right(componentsUtils.getResponseFormat(ActionStatus.INVALID_CONTENT));
1748 data = ValidationUtils.removeNoneUtf8Chars(data);
1749 data = ValidationUtils.removeHtmlTags(data);
1750 data = ValidationUtils.normaliseWhitespace(data);
1751 data = ValidationUtils.stripOctets(data);
1753 if (!ValidationUtils.validateLength(data, ValidationUtils.COMMENT_MAX_LENGTH)) {
1754 BeEcompErrorManager.getInstance().logBeInvalidJsonInput(CHANGE_SERVICE_DISTRIBUTION);
1755 log.debug("user comment exceeds limit.");
1756 return Either.right(componentsUtils.getResponseFormat(ActionStatus.EXCEEDS_LIMIT, "comment", String.valueOf(ValidationUtils.COMMENT_MAX_LENGTH)));
1758 if (!ValidationUtils.validateIsEnglish(data)) {
1759 return Either.right(componentsUtils.getResponseFormat(ActionStatus.INVALID_CONTENT));
1761 return Either.left(data);
1764 private Either<Service, ResponseFormat> validateServiceDistributionChange(User user, String serviceId, AuditingActionEnum auditAction, String comment) {
1765 Either<Service, StorageOperationStatus> storageStatus = toscaOperationFacade.getToscaElement(serviceId);
1766 if (storageStatus.isRight()) {
1767 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.SERVICE_NOT_FOUND, serviceId);
1768 log.debug(AUDIT_BEFORE_SENDING_RESPONSE);
1769 componentsUtils.auditComponent(responseFormat, user, auditAction, new ResourceCommonInfo(serviceId, ComponentTypeEnum.SERVICE.getValue()), comment);
1770 return Either.right(responseFormat);
1772 Service service = storageStatus.left().value();
1774 if (service.getLifecycleState() != LifecycleStateEnum.CERTIFIED) {
1775 log.info("service {} is not available for distribution. Should be in certified state", service.getUniqueId());
1776 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.SERVICE_NOT_AVAILABLE_FOR_DISTRIBUTION, service.getVersion(), service.getName());
1777 createAudit(user, auditAction, comment, service, responseFormat);
1778 return Either.right(responseFormat);
1780 return Either.left(service);
1783 private Either<User, ResponseFormat> validateUserDistributionChange(User user, Service service, AuditingActionEnum auditAction, String comment) {
1784 log.debug("get user from DB");
1787 user = validateUser(user, "Activate Distribution", service, auditAction, false);
1788 // validate user role
1789 List<Role> roles = new ArrayList<>();
1790 roles.add(Role.ADMIN);
1791 roles.add(Role.GOVERNOR);
1792 roles.add(Role.OPS);
1793 validateUserRole(user, service, roles, auditAction, comment);
1794 return Either.left(user);
1797 private void createAudit(User user, AuditingActionEnum auditAction, String comment, Service component, ResponseFormat responseFormat) {
1798 log.debug(AUDIT_BEFORE_SENDING_RESPONSE);
1799 componentsUtils.auditComponent(responseFormat, user, component, auditAction, new ResourceCommonInfo(ComponentTypeEnum.SERVICE.getValue()),
1800 ResourceVersionInfo.newBuilder()
1801 .state(component.getLifecycleState().name())
1802 .version(component.getVersion())
1807 private String getEnvNameFromConfiguration() {
1808 String configuredEnvName = ConfigurationManager.getConfigurationManager().getDistributionEngineConfiguration().getEnvironments().get(0);
1809 log.trace("Update environment name to be {}", configuredEnvName);
1810 return configuredEnvName;
1813 public Either<String, ResponseFormat> activateServiceOnTenantEnvironment(String serviceId, String envId, User modifier, ServiceDistributionReqInfo data) {
1815 Either<ActivationRequestInformation, ResponseFormat> activationRequestInformationEither = serviceDistributionValidation.validateActivateServiceRequest(serviceId, envId, modifier, data);
1816 if (activationRequestInformationEither.isRight()) {
1817 return Either.right(activationRequestInformationEither.right().value());
1820 ActivationRequestInformation activationRequestInformation = activationRequestInformationEither.left().value();
1822 Either<String, ResponseFormat> result = null;
1823 String did = ThreadLocalsHolder.getUuid();
1824 Service service = activationRequestInformation.getServiceToActivate();
1825 result = buildAndSendServiceNotification(service, envId, did, activationRequestInformation.getWorkloadContext(), modifier);
1829 public Either<String, ResponseFormat> buildAndSendServiceNotification(Service service, String envId, String did, String workloadContext, User modifier) {
1830 String envName = getEnvNameFromConfiguration();
1831 INotificationData notificationData = distributionEngine.buildServiceForDistribution(service, did, workloadContext);
1832 ActionStatus notifyServiceResponse = distributionEngine.notifyService(did, service, notificationData, envId, envName, modifier);
1833 if (notifyServiceResponse == ActionStatus.OK) {
1834 return Either.left(did);
1836 BeEcompErrorManager.getInstance().logBeSystemError("Activate Distribution - send notification");
1837 log.debug("distributionEngine.notifyService response is: {}", notifyServiceResponse);
1838 ResponseFormat error = componentsUtils.getResponseFormat(ActionStatus.INVALID_RESPONSE_FROM_PROXY);
1839 return Either.right(error);
1843 public Either<Service, ResponseFormat> activateDistribution(String serviceId, String envName, User modifier, HttpServletRequest request) {
1845 User user = validateUserExists(modifier.getUserId(), "activate Distribution", false);
1846 Either<Service, ResponseFormat> result = null;
1847 ResponseFormat response = null;
1848 Service updatedService = null;
1849 String did = ThreadLocalsHolder.getUuid();
1851 String configuredEnvName = ConfigurationManager.getConfigurationManager().getDistributionEngineConfiguration().getEnvironments().get(0);
1852 if (configuredEnvName != null && !configuredEnvName.equals(envName)) {
1853 log.trace("Update environment name to be {} instead of {}", configuredEnvName, envName);
1854 envName = configuredEnvName;
1858 ServletContext servletContext = request.getSession().getServletContext();
1859 boolean isDistributionEngineUp = getHealthCheckBL(servletContext).isDistributionEngineUp(); // DE
1860 if (!isDistributionEngineUp) {
1861 BeEcompErrorManager.getInstance().logBeSystemError("Distribution Engine is DOWN");
1862 log.debug("Distribution Engine is DOWN");
1863 response = componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR);
1864 return Either.right(response);
1867 Either<Service, StorageOperationStatus> serviceRes = toscaOperationFacade.getToscaElement(serviceId);
1868 if (serviceRes.isRight()) {
1869 log.debug("failed retrieving service");
1870 response = componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(serviceRes.right().value(), ComponentTypeEnum.SERVICE), serviceId);
1871 componentsUtils.auditComponent(response, user, null, AuditingActionEnum.DISTRIBUTION_STATE_CHANGE_REQUEST,
1872 new ResourceCommonInfo(ComponentTypeEnum.SERVICE.getValue()),
1873 ResourceVersionInfo.newBuilder()
1876 return Either.right(response);
1878 Service service = serviceRes.left().value();
1879 String dcurrStatus = service.getDistributionStatus().name();
1880 String updatedStatus = dcurrStatus;
1881 StorageOperationStatus readyForDistribution = distributionEngine.isReadyForDistribution(envName);
1882 if (readyForDistribution.equals(StorageOperationStatus.OK)) {
1883 INotificationData notificationData = distributionEngine.buildServiceForDistribution(service, did, null);
1884 ActionStatus notifyServiceResponse = distributionEngine.notifyService(did, service, notificationData, envName, user);
1885 if (notifyServiceResponse == ActionStatus.OK) {
1886 Either<Service, ResponseFormat> updateStateRes = updateDistributionStatusForActivation(service, user, DistributionStatusEnum.DISTRIBUTED);
1887 if (updateStateRes.isLeft() && updateStateRes.left().value() != null) {
1888 updatedService = updateStateRes.left().value();
1889 updatedStatus = updatedService.getDistributionStatus().name();
1891 // The response is not relevant
1892 updatedService = service;
1894 ASDCKpiApi.countActivatedDistribution();
1895 response = componentsUtils.getResponseFormat(ActionStatus.OK);
1896 result = Either.left(updatedService);
1898 BeEcompErrorManager.getInstance().logBeSystemError("Activate Distribution - send notification");
1899 log.debug("distributionEngine.notifyService response is: {}", notifyServiceResponse);
1900 response = componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR);
1901 result = Either.right(response);
1904 response = componentsUtils.getResponseFormatByDE(componentsUtils.convertFromStorageResponse(readyForDistribution), envName);
1905 result = Either.right(response);
1907 componentsUtils.auditComponent(response, user, service, AuditingActionEnum.DISTRIBUTION_STATE_CHANGE_REQUEST,
1908 new ResourceCommonInfo(service.getName(),ComponentTypeEnum.SERVICE.getValue()),
1909 ResourceVersionInfo.newBuilder()
1910 .distributionStatus(dcurrStatus)
1912 ResourceVersionInfo.newBuilder()
1913 .distributionStatus(updatedStatus)
1919 // convert to private after deletion of temp url
1920 public Either<Service, ResponseFormat> updateDistributionStatusForActivation(Service service, User user, DistributionStatusEnum state) {
1922 validateUserExists(user.getUserId(), "update Distribution Status For Activation", false);
1924 String serviceId = service.getUniqueId();
1925 Either<Boolean, ResponseFormat> lockResult = lockComponent(serviceId, service, "updateDistributionStatusForActivation");
1926 if (lockResult.isRight()) {
1927 return Either.right(lockResult.right().value());
1930 Either<Service, StorageOperationStatus> result = toscaOperationFacade.updateDistributionStatus(service, user, state);
1931 if (result.isRight()) {
1932 titanDao.rollback();
1933 BeEcompErrorManager.getInstance().logBeSystemError("updateDistributionStatusForActivation");
1934 log.debug("service {} change distribution status failed", serviceId);
1935 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
1938 return Either.left(result.left().value());
1940 graphLockOperation.unlockComponent(serviceId, NodeTypeEnum.Service);
1944 public Either<Service, ResponseFormat> markDistributionAsDeployed(String serviceId, String did, User user) {
1946 validateUserExists(user.getUserId(), "mark Distribution As Deployed", false);
1947 log.debug("mark distribution deployed");
1949 AuditingActionEnum auditAction = AuditingActionEnum.DISTRIBUTION_DEPLOY;
1950 Either<Service, StorageOperationStatus> getServiceResponse = toscaOperationFacade.getToscaElement(serviceId);
1951 if (getServiceResponse.isRight()) {
1952 BeEcompErrorManager.getInstance().logBeComponentMissingError("markDistributionAsDeployed", ComponentTypeEnum.SERVICE.getValue(), serviceId);
1953 log.debug("service {} not found", serviceId);
1954 ResponseFormat responseFormat = auditDeployError(did, user, auditAction, null, componentsUtils.convertFromStorageResponse(getServiceResponse.right().value(), ComponentTypeEnum.SERVICE), "");
1956 return Either.right(responseFormat);
1959 Service service = getServiceResponse.left().value();
1960 user = validateRoleForDeploy(did, user, auditAction, service);
1961 return checkDistributionAndDeploy(did, user, auditAction, service);
1965 public Either<Service, ResponseFormat> generateVfModuleArtifacts(Service service, User modifier, boolean shouldLock, boolean inTransaction) {
1966 Function<ComponentInstance, List<ArtifactGenerator<ArtifactDefinition>>> artifactTaskGeneratorCreator = ri ->
1967 // Only one VF Module Artifact per instance - add it to a list of one
1968 buildArtifactGenList(service, modifier, shouldLock, inTransaction, ri);
1970 return generateDeploymentArtifacts(service, artifactTaskGeneratorCreator);
1974 private List<ArtifactGenerator<ArtifactDefinition>> buildArtifactGenList(Service service, User modifier, boolean shouldLock, boolean inTransaction, ComponentInstance ri) {
1975 List<ArtifactGenerator<ArtifactDefinition>> asList = new ArrayList<>();
1977 if (ri.getOriginType() == OriginTypeEnum.VF) {
1978 asList = Arrays.asList(new VfModuleArtifactGenerator(modifier, ri, service, shouldLock, inTransaction));
1983 private List<GroupInstance> collectGroupsInstanceForCompInstance(ComponentInstance currVF) {
1984 Map<String, ArtifactDefinition> deploymentArtifacts = currVF.getDeploymentArtifacts();
1985 if(currVF.getGroupInstances() != null){
1986 currVF.getGroupInstances().forEach(gi -> gi.alignArtifactsUuid(deploymentArtifacts));
1988 return currVF.getGroupInstances();
1991 private ArtifactDefinition getVfModuleInstArtifactForCompInstance(ComponentInstance currVF, Service service, Wrapper<String> payloadWrapper, Wrapper<ResponseFormat> responseWrapper) {
1992 ArtifactDefinition vfModuleAertifact = null;
1993 if (MapUtils.isNotEmpty(currVF.getDeploymentArtifacts())) {
1994 Optional<ArtifactDefinition> optionalVfModuleArtifact = currVF.getDeploymentArtifacts().values().stream().filter(p -> p.getArtifactType().equals(ArtifactTypeEnum.VF_MODULES_METADATA.name())).findAny();
1995 if (optionalVfModuleArtifact.isPresent()) {
1996 vfModuleAertifact = optionalVfModuleArtifact.get();
1999 if (vfModuleAertifact == null) {
2000 Either<ArtifactDefinition, ResponseFormat> createVfModuleArtifact = createVfModuleArtifact(currVF, service, payloadWrapper.getInnerElement());
2001 if (createVfModuleArtifact.isLeft()) {
2002 vfModuleAertifact = createVfModuleArtifact.left().value();
2004 responseWrapper.setInnerElement(createVfModuleArtifact.right().value());
2007 return vfModuleAertifact;
2010 private void fillVfModuleInstHeatEnvPayload(List<GroupInstance> groupsForCurrVF, Wrapper<String> payloadWrapper) {
2011 List<VfModuleArtifactPayload> vfModulePayloads = new ArrayList<>();
2012 if (groupsForCurrVF != null) {
2013 for (GroupInstance groupInstance : groupsForCurrVF) {
2014 VfModuleArtifactPayload modulePayload = new VfModuleArtifactPayload(groupInstance);
2015 vfModulePayloads.add(modulePayload);
2017 vfModulePayloads.sort(VfModuleArtifactPayload::compareByGroupName);
2019 final Gson gson = new GsonBuilder().setPrettyPrinting().create();
2021 String vfModulePayloadString = gson.toJson(vfModulePayloads);
2022 payloadWrapper.setInnerElement(vfModulePayloadString);
2027 private Either<ArtifactDefinition, ResponseFormat> generateVfModuleInstanceArtifact(User modifier, ComponentInstance currVFInstance, Service service, boolean shouldLock, boolean inTransaction) {
2028 ArtifactDefinition vfModuleArtifact = null;
2029 Wrapper<ResponseFormat> responseWrapper = new Wrapper<>();
2030 Wrapper<String> payloadWrapper = new Wrapper<>();
2031 List<GroupInstance> groupsForCurrVF = collectGroupsInstanceForCompInstance(currVFInstance);
2032 if (responseWrapper.isEmpty()) {
2033 fillVfModuleInstHeatEnvPayload(groupsForCurrVF, payloadWrapper);
2035 if (responseWrapper.isEmpty() && payloadWrapper.getInnerElement() != null) {
2036 vfModuleArtifact = getVfModuleInstArtifactForCompInstance(currVFInstance, service, payloadWrapper, responseWrapper);
2038 if (responseWrapper.isEmpty() && vfModuleArtifact != null) {
2039 vfModuleArtifact = fillVfModulePayload(modifier, currVFInstance, vfModuleArtifact, shouldLock, inTransaction, payloadWrapper, responseWrapper, service);
2042 Either<ArtifactDefinition, ResponseFormat> result;
2043 if (responseWrapper.isEmpty()) {
2044 result = Either.left(vfModuleArtifact);
2046 result = Either.right(responseWrapper.getInnerElement());
2052 private ArtifactDefinition fillVfModulePayload(User modifier, ComponentInstance currVF, ArtifactDefinition vfModuleArtifact, boolean shouldLock, boolean inTransaction, Wrapper<String> payloadWrapper, Wrapper<ResponseFormat> responseWrapper, Service service) {
2053 ArtifactDefinition result = null;
2054 Either<ArtifactDefinition, ResponseFormat> eitherPayload = artifactsBusinessLogic.generateArtifactPayload(vfModuleArtifact, ComponentTypeEnum.RESOURCE_INSTANCE, service, currVF.getName(), modifier, shouldLock, inTransaction, System::currentTimeMillis,
2055 () -> Either.left(artifactsBusinessLogic.createEsArtifactData(vfModuleArtifact, payloadWrapper.getInnerElement().getBytes(StandardCharsets.UTF_8))), currVF.getUniqueId());
2056 if (eitherPayload.isLeft()) {
2057 result = eitherPayload.left().value();
2059 responseWrapper.setInnerElement(eitherPayload.right().value());
2061 if (result == null) {
2062 result = vfModuleArtifact;
2068 private Either<ArtifactDefinition, ResponseFormat> createVfModuleArtifact(ComponentInstance currVF, Service service, String vfModulePayloadString) {
2070 ArtifactDefinition vfModuleArtifactDefinition = new ArtifactDefinition();
2071 String newCheckSum = null;
2073 vfModuleArtifactDefinition.setDescription("Auto-generated VF Modules information artifact");
2074 vfModuleArtifactDefinition.setArtifactDisplayName("Vf Modules Metadata");
2075 vfModuleArtifactDefinition.setArtifactType(ArtifactTypeEnum.VF_MODULES_METADATA.getType());
2076 vfModuleArtifactDefinition.setArtifactGroupType(ArtifactGroupTypeEnum.DEPLOYMENT);
2077 vfModuleArtifactDefinition.setArtifactLabel("vfModulesMetadata");
2078 vfModuleArtifactDefinition.setTimeout(0);
2079 vfModuleArtifactDefinition.setArtifactName(currVF.getNormalizedName() + "_modules.json");
2080 vfModuleArtifactDefinition.setPayloadData(vfModulePayloadString);
2081 if (vfModulePayloadString != null) {
2082 newCheckSum = GeneralUtility.calculateMD5Base64EncodedByByteArray(vfModulePayloadString.getBytes());
2084 vfModuleArtifactDefinition.setArtifactChecksum(newCheckSum);
2086 Either<ArtifactDefinition, StorageOperationStatus> addArifactToComponent = artifactToscaOperation.addArifactToComponent(vfModuleArtifactDefinition, service.getUniqueId(), NodeTypeEnum.ResourceInstance, true, currVF.getUniqueId());
2088 Either<ArtifactDefinition, ResponseFormat> result;
2089 if (addArifactToComponent.isLeft()) {
2090 result = Either.left(addArifactToComponent.left().value());
2092 result = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(addArifactToComponent.right().value())));
2098 public Either<Service, ResponseFormat> generateHeatEnvArtifacts(Service service, User modifier, boolean shouldLock, boolean inTransaction) {
2100 Function<ComponentInstance, List<ArtifactGenerator<ArtifactDefinition>>> artifactTaskGeneratorCreator = resourceInstance ->
2101 // Get All Deployment Artifacts
2102 service.getComponentInstances().stream().filter(ri -> ri != null && ri == resourceInstance).filter(ri -> ri.getDeploymentArtifacts() != null).flatMap(ri -> ri.getDeploymentArtifacts().values().stream()).
2103 // Filter in Only Heat Env
2104 filter(depArtifact -> ArtifactTypeEnum.HEAT_ENV.getType().equals(depArtifact.getArtifactType())).
2105 // Create ArtifactGenerator from those Artifacts
2106 map(depArtifact -> new HeatEnvArtifactGenerator(depArtifact, service, resourceInstance.getName(), modifier, shouldLock, inTransaction, resourceInstance.getUniqueId())).collect(Collectors.toList());
2108 return generateDeploymentArtifacts(service, artifactTaskGeneratorCreator);
2112 private <CallVal> Either<Service, ResponseFormat> generateDeploymentArtifacts(Service service, Function<ComponentInstance, List<ArtifactGenerator<CallVal>>> artifactTaskGeneratorCreator) {
2114 // Get Flat List of (Callable) ArtifactGenerator for all the RI in the
2116 if (service.getComponentInstances() != null) {
2117 List<ArtifactGenerator<CallVal>> artifactGenList = service.getComponentInstances().stream().flatMap(ri -> artifactTaskGeneratorCreator.apply(ri).stream()).collect(Collectors.toList());
2118 if (artifactGenList != null && !artifactGenList.isEmpty()) {
2119 for (ArtifactGenerator<CallVal> entry : artifactGenList) {
2120 Either<CallVal, ResponseFormat> callRes;
2122 callRes = entry.call();
2123 if (callRes.isRight()) {
2124 log.debug("Failed to generate artifact error : {}", callRes.right().value());
2125 return Either.right(callRes.right().value());
2127 } catch (Exception e) {
2128 log.debug("Failed to generate artifact exception : {}", e);
2129 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
2134 Either<Service, StorageOperationStatus> storageStatus = toscaOperationFacade.getToscaFullElement(service.getUniqueId());
2135 if (storageStatus.isRight()) {
2136 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE), ""));
2139 Service currentService = storageStatus.left().value();
2141 return Either.left(currentService);
2145 abstract class ArtifactGenerator<CallVal> implements Callable<Either<CallVal, ResponseFormat>> {
2149 class HeatEnvArtifactGenerator extends ArtifactGenerator<ArtifactDefinition> {
2150 ArtifactDefinition artifactDefinition;
2152 String resourceInstanceName;
2156 boolean inTransaction;
2158 HeatEnvArtifactGenerator(ArtifactDefinition artifactDefinition, Service service, String resourceInstanceName, User modifier, boolean shouldLock, boolean inTransaction, String instanceId) {
2159 this.artifactDefinition = artifactDefinition;
2160 this.service = service;
2161 this.resourceInstanceName = resourceInstanceName;
2162 this.modifier = modifier;
2163 this.shouldLock = shouldLock;
2164 this.instanceId = instanceId;
2165 this.inTransaction = inTransaction;
2169 public Either<ArtifactDefinition, ResponseFormat> call() throws Exception {
2170 return artifactsBusinessLogic.forceGenerateHeatEnvArtifact(artifactDefinition, ComponentTypeEnum.RESOURCE_INSTANCE, service, resourceInstanceName, modifier, shouldLock, inTransaction, instanceId);
2173 public ArtifactDefinition getArtifactDefinition() {
2174 return artifactDefinition;
2179 class VfModuleArtifactGenerator extends ArtifactGenerator<ArtifactDefinition> {
2181 private ComponentInstance componentInstance;
2182 private Service service;
2184 boolean inTransaction;
2187 public Either<ArtifactDefinition, ResponseFormat> call() throws Exception {
2188 return generateVfModuleInstanceArtifact(user, componentInstance, service, shouldLock, inTransaction);
2191 private VfModuleArtifactGenerator(User user, ComponentInstance componentInstance, Service service, boolean shouldLock, boolean inTransaction) {
2194 this.componentInstance = componentInstance;
2195 this.service = service;
2196 this.shouldLock = shouldLock;
2197 this.inTransaction = inTransaction;
2202 private synchronized Either<Service, ResponseFormat> checkDistributionAndDeploy(String distributionId, User user, AuditingActionEnum auditAction, Service service) {
2203 boolean isDeployed = isDistributionDeployed(distributionId);
2205 return Either.left(service);
2207 Either<Boolean, ResponseFormat> distributionSuccess = checkDistributionSuccess(distributionId, user, auditAction, service);
2208 if (distributionSuccess.isRight()) {
2209 return Either.right(distributionSuccess.right().value());
2212 log.debug("mark distribution {} as deployed - success", distributionId);
2213 componentsUtils.auditServiceDistributionDeployed(service.getName(), service.getVersion(), service.getUUID(), distributionId, STATUS_DEPLOYED, "OK", user);
2214 return Either.left(service);
2217 private boolean isDistributionDeployed(String distributionId) {
2218 Either<List<DistributionDeployEvent>, ActionStatus> alreadyDeployed = auditCassandraDao.getDistributionDeployByStatus(distributionId, AuditingActionEnum.DISTRIBUTION_DEPLOY.getName(), STATUS_DEPLOYED);
2220 boolean isDeployed = false;
2221 if (alreadyDeployed.isLeft() && !alreadyDeployed.left().value().isEmpty()) {
2223 log.debug("distribution {} is already deployed", distributionId);
2229 protected Either<Boolean, ResponseFormat> checkDistributionSuccess(String did, User user, AuditingActionEnum auditAction, Service service) {
2231 log.trace("checkDistributionSuccess");
2232 // get all "DRequest" records for this distribution
2234 Either<List<ResourceAdminEvent>, ActionStatus> distRequestsResponse = auditCassandraDao.getDistributionRequest(did, AuditingActionEnum.DISTRIBUTION_STATE_CHANGE_REQUEST.getName());
2235 if (distRequestsResponse.isRight()) {
2236 ResponseFormat error = auditDeployError(did, user, auditAction, service, distRequestsResponse.right().value());
2237 return Either.right(error);
2240 List<ResourceAdminEvent> distributionRequests = distRequestsResponse.left().value();
2241 if (distributionRequests.isEmpty()) {
2242 BeEcompErrorManager.getInstance().logBeDistributionMissingError("markDistributionAsDeployed", did);
2243 log.info("distribution {} is not found", did);
2244 ResponseFormat error = auditDeployError(did, user, auditAction, service, ActionStatus.DISTRIBUTION_REQUESTED_NOT_FOUND);
2245 return Either.right(error);
2247 boolean isRequestSucceeded = false;
2248 for (ResourceAdminEvent event : distributionRequests) {
2249 String eventStatus = event.getStatus();
2250 if (eventStatus != null && eventStatus.equals(STATUS_SUCCESS_200)) {
2251 isRequestSucceeded = true;
2256 // get all "DNotify" records for this distribution
2257 Either<List<DistributionNotificationEvent>, ActionStatus> distNotificationsResponse = auditCassandraDao.getDistributionNotify(did, AuditingActionEnum.DISTRIBUTION_NOTIFY.getName());
2258 if (distNotificationsResponse.isRight()) {
2259 ResponseFormat error = auditDeployError(did, user, auditAction, service, distNotificationsResponse.right().value());
2260 return Either.right(error);
2263 List<DistributionNotificationEvent> distributionNotifications = distNotificationsResponse.left().value();
2264 boolean isNotificationsSucceeded = false;
2265 for (DistributionNotificationEvent event : distributionNotifications) {
2266 String eventStatus = event.getStatus();
2267 if (eventStatus != null && eventStatus.equals(STATUS_SUCCESS_200)) {
2268 isNotificationsSucceeded = true;
2273 // if request failed OR there are notifications that failed
2274 if (!(isRequestSucceeded && isNotificationsSucceeded)) {
2276 log.info("distribution {} has failed", did);
2277 ResponseFormat error = componentsUtils.getResponseFormat(ActionStatus.DISTRIBUTION_REQUESTED_FAILED, did);
2278 auditDeployError(did, user, auditAction, service, ActionStatus.DISTRIBUTION_REQUESTED_FAILED, did);
2279 return Either.right(error);
2281 return Either.left(true);
2284 private ResponseFormat auditDeployError(String did, User user, AuditingActionEnum auditAction, Service service, ActionStatus status, String... params) {
2286 ResponseFormat error = componentsUtils.getResponseFormat(status, params);
2287 String message = "";
2288 if (error.getMessageId() != null) {
2289 message = error.getMessageId() + ": ";
2291 message += error.getFormattedMessage();
2293 if (service != null) {
2294 componentsUtils.auditServiceDistributionDeployed(service.getName(), service.getVersion(), service.getUUID(), did, error.getStatus().toString(), message, user);
2296 componentsUtils.auditServiceDistributionDeployed("", "", "", did, error.getStatus().toString(), message, user);
2301 private User validateRoleForDeploy(String did, User user, AuditingActionEnum auditAction, Service service) {
2302 Either<User, ActionStatus> eitherCreator = userAdmin.getUser(user.getUserId(), false);
2303 if (eitherCreator.isRight() || eitherCreator.left().value() == null) {
2304 BeEcompErrorManager.getInstance().logBeUserMissingError("Deploy Service", user.getUserId());
2305 log.debug("validateRoleForDeploy method - user is not listed. userId= {}", user.getUserId());
2306 ResponseFormat responseFormat = componentsUtils.getResponseFormat(ActionStatus.USER_NOT_FOUND, user.getUserId());
2307 auditDeployError(did, user, auditAction, service, ActionStatus.USER_NOT_FOUND);
2308 throw new ComponentException(ActionStatus.USER_NOT_FOUND, user.getUserId());
2310 user = eitherCreator.left().value();
2311 log.debug("validate user role");
2312 List<Role> roles = new ArrayList<>();
2313 roles.add(Role.ADMIN);
2314 roles.add(Role.OPS);
2316 validateUserRole(user, service, roles, auditAction, null);
2317 } catch (ComponentException e){
2318 log.info("role {} is not allowed to perform this action", user.getRole());
2319 auditDeployError(did, user, auditAction, service, e.getActionStatus());
2326 public void setDeploymentArtifactsPlaceHolder(Component component, User user) {
2327 Service service = (Service) component;
2328 Map<String, ArtifactDefinition> artifactMap = service.getDeploymentArtifacts();
2329 if (artifactMap == null) {
2330 artifactMap = new HashMap<>();
2332 service.setDeploymentArtifacts(artifactMap);
2336 public Either<List<String>, ResponseFormat> deleteMarkedComponents() {
2337 return deleteMarkedComponents(ComponentTypeEnum.SERVICE);
2340 private HealthCheckBusinessLogic getHealthCheckBL(ServletContext context) {
2341 WebAppContextWrapper webApplicationContextWrapper = (WebAppContextWrapper) context.getAttribute(Constants.WEB_APPLICATION_CONTEXT_WRAPPER_ATTR);
2342 WebApplicationContext webApplicationContext = webApplicationContextWrapper.getWebAppContext(context);
2343 return webApplicationContext.getBean(HealthCheckBusinessLogic.class);
2347 public ComponentInstanceBusinessLogic getComponentInstanceBL() {
2348 return componentInstanceBusinessLogic;
2352 public Either<List<ComponentInstance>, ResponseFormat> getComponentInstancesFilteredByPropertiesAndInputs(String componentId, String userId) {
2354 validateUserExists(userId, "Get Component Instances", false);
2355 Either<Component, StorageOperationStatus> getComponentRes = toscaOperationFacade.getToscaElement(componentId, JsonParseFlagEnum.ParseAll);
2356 if (getComponentRes.isRight()) {
2357 ResponseFormat responseFormat = componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(getComponentRes.right().value()));
2358 return Either.right(responseFormat);
2361 List<ComponentInstance> componentInstances = getComponentRes.left().value().getComponentInstances();
2363 return Either.left(componentInstances);
2366 public ICacheMangerOperation getCacheManagerOperation() {
2367 return cacheManagerOperation;
2370 public void setCacheManagerOperation(ICacheMangerOperation cacheManagerOperation) {
2371 this.cacheManagerOperation = cacheManagerOperation;
2374 public void setForwardingPathOperation(ForwardingPathOperation forwardingPathOperation) {
2375 this.forwardingPathOperation = forwardingPathOperation;
2379 public void setToscaOperationFacade(ToscaOperationFacade toscaOperationFacade) {
2380 this.toscaOperationFacade = toscaOperationFacade;
2382 * updates group instance with new property values in case of successful update of group instance related component instance will be updated with new modification time and related service will be updated with new last update date
2385 public Either<List<GroupInstanceProperty>, ResponseFormat> updateGroupInstancePropertyValues(User modifier, String serviceId, String componentInstanceId, String groupInstanceId, List<GroupInstanceProperty> newProperties) {
2387 Either<List<GroupInstanceProperty>, ResponseFormat> actionResult = null;
2388 Either<ImmutablePair<Component, User>, ResponseFormat> validateUserAndComponentRes;
2389 Component component = null;
2390 Either<Boolean, ResponseFormat> lockResult = null;
2391 log.debug("Going to update group instance {} of service {} with new property values. ", groupInstanceId, serviceId);
2393 validateUserAndComponentRes = validateUserAndComponent(serviceId, modifier);
2394 if (validateUserAndComponentRes.isRight()) {
2395 log.debug("Cannot update group instance {} of service {} with new property values. Validation failed. ", groupInstanceId, serviceId);
2396 actionResult = Either.right(validateUserAndComponentRes.right().value());
2398 if (actionResult == null) {
2399 component = validateUserAndComponentRes.left().value().getKey();
2400 lockResult = lockComponentByName(component.getSystemName(), component, "Update Group Instance on Service");
2401 if (lockResult.isRight()) {
2402 log.debug(FAILED_TO_LOCK_SERVICE_RESPONSE_IS, component.getName(), lockResult.right().value().getFormattedMessage());
2403 actionResult = Either.right(lockResult.right().value());
2405 log.debug(THE_SERVICE_WITH_SYSTEM_NAME_LOCKED, component.getSystemName());
2408 if (actionResult == null) {
2409 actionResult = validateAndUpdateGroupInstancePropertyValuesAndContainingParents(component, componentInstanceId, groupInstanceId, newProperties);
2410 if (actionResult.isRight()) {
2411 log.debug("Failed to validate and update group instance {} property values and containing parents. The message is {}. ", groupInstanceId, actionResult.right().value().getFormattedMessage());
2414 } catch (Exception e) {
2415 log.error("Exception occured during update Group Instance property values: {}", e.getMessage(), e);
2416 actionResult = Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
2418 if (lockResult != null && lockResult.isLeft() && lockResult.left().value()) {
2419 graphLockOperation.unlockComponentByName(component.getSystemName(), component.getUniqueId(), NodeTypeEnum.Service);
2422 return actionResult;
2425 private Either<List<GroupInstanceProperty>, ResponseFormat> validateAndUpdateGroupInstancePropertyValuesAndContainingParents(Component component, String componentInstanceId, String groupInstanceId, List<GroupInstanceProperty> newProperties) {
2427 Either<List<GroupInstanceProperty>, ResponseFormat> actionResult = null;
2428 Either<ImmutablePair<ComponentInstance, GroupInstance>, ResponseFormat> findGroupInstanceRes;
2429 Either<ImmutablePair<ComponentMetadataData, ComponentInstanceData>, ResponseFormat> updateParentsModificationTimeRes;
2430 ComponentInstance relatedComponentInstance = null;
2431 GroupInstance oldGroupInstance = null;
2432 Either<GroupInstance, ResponseFormat> updateGroupInstanceResult = null;
2433 GroupInstance updatedGroupInstance = null;
2434 boolean inTransaction = true;
2435 findGroupInstanceRes = findGroupInstanceOnRelatedComponentInstance(component, componentInstanceId, groupInstanceId);
2436 if (findGroupInstanceRes.isRight()) {
2437 log.debug("#validateAndUpdateGroupInstancePropertyValuesAndContainingParents - Group instance {} not found. ", groupInstanceId);
2438 actionResult = Either.right(findGroupInstanceRes.right().value());
2440 if (actionResult == null) {
2441 oldGroupInstance = findGroupInstanceRes.left().value().getValue();
2442 relatedComponentInstance = findGroupInstanceRes.left().value().getKey();
2443 updateGroupInstanceResult = groupBusinessLogic.validateAndUpdateGroupInstancePropertyValues(component.getUniqueId(), componentInstanceId, oldGroupInstance, newProperties);
2444 if (updateGroupInstanceResult.isRight()) {
2445 log.debug("#validateAndUpdateGroupInstancePropertyValuesAndContainingParents - Failed to update group instance {} property values. ", oldGroupInstance.getName());
2446 actionResult = Either.right(updateGroupInstanceResult.right().value());
2449 if (actionResult == null) {
2450 updatedGroupInstance = updateGroupInstanceResult.left().value();
2451 if (!oldGroupInstance.getModificationTime().equals(updatedGroupInstance.getModificationTime())) {
2452 updateParentsModificationTimeRes = updateParentsModificationTimeAndCustomizationUuid(component, relatedComponentInstance, updatedGroupInstance, inTransaction);
2453 if (updateParentsModificationTimeRes.isRight()) {
2454 log.debug("#validateAndUpdateGroupInstancePropertyValuesAndContainingParents - Failed to update modification time for group instance {}. ", oldGroupInstance.getName());
2455 actionResult = Either.right(updateParentsModificationTimeRes.right().value());
2459 if (actionResult == null) {
2460 actionResult = Either.left(updatedGroupInstance.convertToGroupInstancesProperties());
2462 return actionResult;
2465 private Either<ImmutablePair<ComponentMetadataData, ComponentInstanceData>, ResponseFormat> updateParentsModificationTimeAndCustomizationUuid(Component component, ComponentInstance relatedComponentInstance, GroupInstance updatedGroupInstance,
2466 boolean inTranscation) {
2468 Either<ImmutablePair<ComponentMetadataData, ComponentInstanceData>, ResponseFormat> actionResult;
2469 Either<ComponentMetadataData, StorageOperationStatus> serviceMetadataUpdateResult;
2470 Either<ComponentInstanceData, ResponseFormat> updateComponentInstanceRes = componentInstanceBusinessLogic.updateComponentInstanceModificationTimeAndCustomizationUuid(relatedComponentInstance, NodeTypeEnum.ResourceInstance,
2471 updatedGroupInstance.getModificationTime(), inTranscation);
2472 if (updateComponentInstanceRes.isRight()) {
2473 log.debug("Failed to update component instance {} after update of group instance {}. ", relatedComponentInstance.getName(), updatedGroupInstance.getName());
2474 actionResult = Either.right(updateComponentInstanceRes.right().value());
2476 serviceMetadataUpdateResult = toscaOperationFacade.updateComponentLastUpdateDateOnGraph(component);
2477 if (serviceMetadataUpdateResult.isRight()) {
2478 log.debug("Failed to update service {} after update of component instance {} with new property values of group instance {}. ", component.getName(), relatedComponentInstance.getName(), updatedGroupInstance.getName());
2479 actionResult = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(serviceMetadataUpdateResult.right().value())));
2481 actionResult = Either.left(new ImmutablePair<>(serviceMetadataUpdateResult.left().value(), updateComponentInstanceRes.left().value()));
2484 return actionResult;
2487 private Either<ImmutablePair<Component, User>, ResponseFormat> validateUserAndComponent(String serviceId, User modifier) {
2489 Either<ImmutablePair<Component, User>, ResponseFormat> result = null;
2490 Either<Component, ResponseFormat> validateComponentExistsRes = null;
2491 User currUser = null;
2492 Component component = null;
2493 Either<User, ResponseFormat> validationUserResult = validateUserIgnoreAudit(modifier, "updateGroupInstancePropertyValues");
2494 if (validationUserResult.isRight()) {
2495 log.debug("#validateUserAndComponent - Failed to validate user with userId {}, for update service {}. ", modifier.getUserId(), serviceId);
2496 result = Either.right(validationUserResult.right().value());
2498 if (result == null) {
2499 currUser = validationUserResult.left().value();
2500 validateComponentExistsRes = validateComponentExists(serviceId, ComponentTypeEnum.SERVICE, null);
2501 if (validateComponentExistsRes.isRight()) {
2502 log.debug("#validateUserAndComponent - Failed to validate service existing {}. ", serviceId);
2503 result = Either.right(validateComponentExistsRes.right().value());
2506 if (result == null) {
2507 component = validateComponentExistsRes.left().value();
2508 if (!ComponentValidationUtils.canWorkOnComponent(component, currUser.getUserId())) {
2509 log.info("#validateUserAndComponent - Restricted operation for user: {}, on service: {}", currUser.getUserId(), component.getCreatorUserId());
2510 return Either.right(componentsUtils.getResponseFormat(ActionStatus.RESTRICTED_OPERATION));
2513 if (result == null) {
2514 result = Either.left(new ImmutablePair<>(component, currUser));
2519 private Either<ImmutablePair<ComponentInstance, GroupInstance>, ResponseFormat> findGroupInstanceOnRelatedComponentInstance(Component component, String componentInstanceId, String groupInstanceId) {
2521 Either<ImmutablePair<ComponentInstance, GroupInstance>, ResponseFormat> actionResult = null;
2522 GroupInstance groupInstance = null;
2523 ComponentInstance foundComponentInstance = findRelatedComponentInstance(component, componentInstanceId);
2524 if (foundComponentInstance == null) {
2525 log.debug("Component instance {} not found on service {}. ", componentInstanceId, component.getName());
2526 actionResult = Either.right(componentsUtils.getResponseFormat(ActionStatus.COMPONENT_INSTANCE_NOT_FOUND_ON_CONTAINER, componentInstanceId, "resource instance", "service", component.getName()));
2528 else if (isNotEmpty(foundComponentInstance.getGroupInstances())) {
2529 groupInstance = foundComponentInstance.getGroupInstances().stream().filter(gi -> gi.getUniqueId().equals(groupInstanceId)).findFirst().orElse(null);
2530 if (groupInstance == null) {
2531 log.debug("Group instance {} not found on component instance {}. ", groupInstanceId, foundComponentInstance.getName());
2532 actionResult = Either.right(componentsUtils.getResponseFormat(ActionStatus.GROUP_INSTANCE_NOT_FOUND_ON_COMPONENT_INSTANCE, groupInstanceId, foundComponentInstance.getName()));
2535 if (actionResult == null) {
2536 actionResult = Either.left(new ImmutablePair<>(foundComponentInstance, groupInstance));
2538 return actionResult;
2541 private ComponentInstance findRelatedComponentInstance(Component component, String componentInstanceId) {
2542 ComponentInstance componentInstance = null;
2543 if (isNotEmpty(component.getComponentInstances())) {
2544 componentInstance = component.getComponentInstances().stream().filter(ci -> ci.getUniqueId().equals(componentInstanceId)).findFirst().orElse(null);
2546 return componentInstance;
2549 private Either<User, ResponseFormat> validateUserIgnoreAudit(User modifier, String ecompErrorContext) {
2550 User user = validateUser(modifier, ecompErrorContext, null, null, false);
2551 List<Role> roles = new ArrayList<>();
2552 roles.add(Role.ADMIN);
2553 roles.add(Role.DESIGNER);
2554 validateUserRole(user, roles);
2555 return Either.left(user);
2558 public Either<UiComponentDataTransfer, ResponseFormat> getUiComponentDataTransferByComponentId(String serviceId, List<String> dataParamsToReturn) {
2560 ComponentParametersView paramsToReturn = new ComponentParametersView(dataParamsToReturn);
2561 Either<Service, StorageOperationStatus> serviceResultEither = toscaOperationFacade.getToscaElement(serviceId, paramsToReturn);
2563 if (serviceResultEither.isRight()) {
2564 if(serviceResultEither.right().value().equals(StorageOperationStatus.NOT_FOUND)) {
2565 log.debug("#getUiComponentDataTransferByComponentId - Failed to find service with id {} ", serviceId);
2566 return Either.right(componentsUtils.getResponseFormat(ActionStatus.SERVICE_NOT_FOUND, serviceId));
2569 log.debug("#getUiComponentDataTransferByComponentId - failed to get service by id {} with filters {}", serviceId, dataParamsToReturn);
2570 return Either.right(componentsUtils.getResponseFormatByResource(componentsUtils.convertFromStorageResponse(serviceResultEither.right().value()), ""));
2573 Service service = serviceResultEither.left().value();
2574 UiComponentDataTransfer dataTransfer = uiComponentDataConverter.getUiDataTransferFromServiceByParams(service, dataParamsToReturn);
2575 return Either.left(dataTransfer);
2578 public Either<String, ResponseFormat> deleteIfNotAlreadyDeletedServiceFilter(String serviceId, String resourceId, String userId, boolean lock) {
2579 Service serviceToDelete = initServiceToDeleteServiceFilter(serviceId);
2580 User user = validateUserExists(userId, "Create service Filter", false);
2583 validateUser(user, "deleteIfNotAlreadyDeletedServiceFilter", serviceToDelete, null, false);
2585 Either<Service, StorageOperationStatus> storageStatus = toscaOperationFacade.getToscaElement(serviceId);
2586 if (storageStatus.isRight()) {
2587 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE), ""));
2589 Service service = storageStatus.left().value();
2591 Either<Boolean, ResponseFormat> response = serviceFilterValidator.validateComponentInstanceExist(service, resourceId);
2592 if (storageStatus.isRight()) {
2593 return Either.right(response.right().value());
2595 final Optional<ComponentInstance> optionalComponentInstance = service.getComponentInstanceById(resourceId);
2596 if (!optionalComponentInstance.isPresent() ){
2597 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
2599 CINodeFilterDataDefinition nodeFilter = optionalComponentInstance.get().getNodeFilter();
2600 if (nodeFilter == null){
2601 return Either.left(resourceId);
2604 Either<String, StorageOperationStatus> result;
2606 Either<Boolean, ResponseFormat> lockResult = lockComponent(service.getUniqueId(), service, "Delete Service Filter from service");
2607 if (lockResult.isRight()) {
2608 titanDao.rollback();
2609 return Either.right(componentsUtils.getResponseFormat(componentsUtils
2610 .convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE), ""));
2614 result = serviceFilterOperation.deleteNodeFilter(service , resourceId);
2615 if (result.isRight()) {
2616 log.debug("Failed to delete node filter in service {}. Response is {}. ", service.getName(), result.right().value());
2617 titanDao.rollback();
2618 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(storageStatus.right().value(), ComponentTypeEnum.SERVICE)));
2621 log.debug("Node filter successfully changed in service {} . ", service.getSystemName());
2623 } catch (Exception e){
2624 log.error("Exception occurred during delete forwarding path : {}", e.getMessage(), e);
2625 titanDao.rollback();
2626 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
2628 graphLockOperation.unlockComponent(service.getUniqueId(), NodeTypeEnum.Service);
2630 return Either.left(result.left().value());
2634 private Service initServiceToDeleteServiceFilter(String serviceId) {
2635 Service serviceToDelete = new Service();
2636 serviceToDelete.setUniqueId(serviceId);
2637 return serviceToDelete;
2641 public Either<CINodeFilterDataDefinition, ResponseFormat> createIfNotAlreadyExistServiceFilter(String serviceId, String componentInstanceId, String userId, boolean lock) {
2642 String errorContext = "createIfNotAlreadyExistServiceFilter";
2643 User user = validateUserExists(userId, "Create service Filter", false);
2645 Either<Service, StorageOperationStatus> serviceEither = toscaOperationFacade.getToscaElement(serviceId);
2646 if (serviceEither.isRight()) {
2647 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(serviceEither.right().value(), ComponentTypeEnum.SERVICE), ""));
2649 final Service service = serviceEither.left().value();
2650 validateUserAndRole(service, user, errorContext);
2652 Optional<ComponentInstance> optionalComponentInstance = service.getComponentInstanceById(componentInstanceId);
2653 if (!optionalComponentInstance.isPresent()){
2654 return Either.right(ResponseFormatManager.getInstance().getResponseFormat(ActionStatus.NODE_FILTER_NOT_FOUND));
2656 ComponentInstance componentInstance = optionalComponentInstance.get();
2657 CINodeFilterDataDefinition serviceFilter = componentInstance.getNodeFilter();
2658 if (serviceFilter != null){
2659 return Either.left(serviceFilter);
2662 Either<CINodeFilterDataDefinition, StorageOperationStatus> result;
2664 Either<Boolean, ResponseFormat> lockResult = null;
2667 lockComponent(service.getUniqueId(), service, "Create Service Filter");
2668 if (lockResult.isRight()) {
2669 log.debug("Failed to lock service {}. Response is {}. ", service.getName(),
2670 lockResult.right().value().getFormattedMessage());
2671 return Either.right(lockResult.right().value());
2673 log.debug("The service with system name {} locked. ", service.getSystemName());
2676 CINodeFilterDataDefinition serviceFilterResult;
2678 result = serviceFilterOperation.createNodeFilter(serviceId, componentInstanceId);
2679 if (result.isRight()) {
2680 titanDao.rollback();
2681 return Either.right(componentsUtils.getResponseFormat(
2682 componentsUtils.convertFromStorageResponse(result.right().value(), ComponentTypeEnum.SERVICE),
2685 serviceFilterResult = result.left().value();
2689 } catch (Exception e) {
2690 titanDao.rollback();
2691 log.error("Exception occurred during add or update service filter property values: {}", e.getMessage(),
2693 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
2696 if (lockResult != null && lockResult.isLeft() && lockResult.left().value()) {
2697 graphLockOperation.unlockComponent(service.getUniqueId(), NodeTypeEnum.Service);
2700 return Either.left(serviceFilterResult);
2704 public Either<CINodeFilterDataDefinition, ResponseFormat> updateServiceFilter(String serviceId, String componentInstanceId,
2705 List<String> constraints, User inUser, boolean lock) {
2706 String errorContext = "createIfNotAlreadyExistServiceFilter";
2707 User user = validateUserExists(inUser, errorContext, true);
2708 validateUserRole(user, Arrays.asList(Role.DESIGNER, Role.ADMIN));
2709 Either<Service, StorageOperationStatus> serviceStorageOperationStatusEither = toscaOperationFacade.getToscaElement(serviceId);
2711 if(serviceStorageOperationStatusEither.isRight()){
2712 StorageOperationStatus errorStatus = serviceStorageOperationStatusEither.right().value();
2713 log.debug("Failed to fetch service information by service id, error {}", errorStatus);
2714 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(errorStatus)));
2716 Service storedService = serviceStorageOperationStatusEither.left().value();
2718 Either<Boolean, ResponseFormat> booleanResponseFormatEither =
2719 serviceFilterValidator.validateNodeFilter(storedService, componentInstanceId, constraints,
2720 NodeFilterConstraintAction.UPDATE);
2721 if(booleanResponseFormatEither.isRight()){
2722 return Either.right(booleanResponseFormatEither.right().value());
2726 Either<Boolean, ResponseFormat> lockResult = null;
2729 lockComponent(storedService.getUniqueId(), storedService, "Add or Update Service Filter on Service");
2730 if (lockResult.isRight()) {
2731 log.debug("Failed to lock service {}. Response is {}. ", storedService.getName(),
2732 lockResult.right().value().getFormattedMessage());
2733 return Either.right(lockResult.right().value());
2735 log.debug("The service with system name {} locked. ", storedService.getSystemName());
2738 Optional<ComponentInstance> componentInstanceOptional = storedService.getComponentInstanceById(componentInstanceId);
2739 if (!componentInstanceOptional.isPresent()){
2740 return Either.right(ResponseFormatManager.getInstance().getResponseFormat(ActionStatus.NODE_FILTER_NOT_FOUND));
2742 CINodeFilterDataDefinition serviceFilter = componentInstanceOptional.get().getNodeFilter();
2743 if(serviceFilter == null){
2744 return Either.right(ResponseFormatManager.getInstance().getResponseFormat(ActionStatus.NODE_FILTER_NOT_FOUND));
2746 CINodeFilterDataDefinition serviceFilterResult;
2748 List<RequirementNodeFilterPropertyDataDefinition> properties = constraints.stream().map(this::getRequirementNodeFilterPropertyDataDefinition).collect(Collectors.toList());
2749 Either<CINodeFilterDataDefinition, StorageOperationStatus> result = serviceFilterOperation.updateProperties(serviceId, componentInstanceId, serviceFilter ,properties);
2751 if (result.isRight()) {
2752 titanDao.rollback();
2753 return Either.right(componentsUtils.getResponseFormat(
2754 componentsUtils.convertFromStorageResponse(result.right().value(), ComponentTypeEnum.SERVICE),
2757 serviceFilterResult = result.left().value();
2761 } catch (Exception e) {
2762 titanDao.rollback();
2763 log.error("Exception occurred during add or update service filter property values: {}", e.getMessage(),
2765 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
2768 if (lockResult != null && lockResult.isLeft() && lockResult.left().value()) {
2769 graphLockOperation.unlockComponent(storedService.getUniqueId(), NodeTypeEnum.Service);
2772 return Either.left(serviceFilterResult);
2775 private RequirementNodeFilterPropertyDataDefinition getRequirementNodeFilterPropertyDataDefinition(String constraint){
2776 RequirementNodeFilterPropertyDataDefinition pdd = new RequirementNodeFilterPropertyDataDefinition();
2777 pdd.setConstraints(Arrays.asList(constraint));
2781 public Either<CINodeFilterDataDefinition, ResponseFormat> addOrDeleteServiceFilter(String serviceId, String componentInstanceId,
2782 NodeFilterConstraintAction action, String constraint, int position, User inUser, boolean lock) {
2783 String errorContext = "createIfNotAlreadyExistServiceFilter";
2784 User user = validateUserExists(inUser, errorContext, true);
2785 validateUserRole(user, Arrays.asList(Role.DESIGNER, Role.ADMIN));
2787 Either<Service, StorageOperationStatus> serviceStorageOperationStatusEither = toscaOperationFacade.getToscaElement(serviceId);
2789 if(serviceStorageOperationStatusEither.isRight()){
2790 StorageOperationStatus errorStatus = serviceStorageOperationStatusEither.right().value();
2791 log.debug("Failed to fetch service information by service id, error {}", errorStatus);
2792 return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(errorStatus)));
2794 Service storedService = serviceStorageOperationStatusEither.left().value();
2796 Either<Boolean, ResponseFormat> booleanResponseFormatEither =
2797 serviceFilterValidator.validateNodeFilter(storedService, componentInstanceId,
2798 Collections.singletonList(constraint), action);
2799 if(booleanResponseFormatEither.isRight()){
2800 return Either.right(booleanResponseFormatEither.right().value());
2803 Either<CINodeFilterDataDefinition, StorageOperationStatus> result;
2805 Either<Boolean, ResponseFormat> lockResult = null;
2806 CINodeFilterDataDefinition serviceFilterResult = null;
2810 lockComponent(storedService.getUniqueId(), storedService, "Add or Update Service Filter on Service");
2811 if (lockResult.isRight()) {
2812 log.debug("Failed to lock service {}. Response is {}. ", storedService.getName(),
2813 lockResult.right().value().getFormattedMessage());
2814 return Either.right(lockResult.right().value());
2816 log.debug("The service with system name {} locked. ", storedService.getSystemName());
2820 Optional<ComponentInstance> componentInstanceOptional = storedService.getComponentInstanceById(componentInstanceId);
2821 if (!componentInstanceOptional.isPresent()){
2822 return Either.right(ResponseFormatManager.getInstance().getResponseFormat(ActionStatus.NODE_FILTER_NOT_FOUND));
2824 CINodeFilterDataDefinition serviceFilter = componentInstanceOptional.get().getNodeFilter();
2825 if(serviceFilter == null){
2826 return Either.right(ResponseFormatManager.getInstance().getResponseFormat(ActionStatus.NODE_FILTER_NOT_FOUND));
2832 RequirementNodeFilterPropertyDataDefinition newProperty = new RequirementNodeFilterPropertyDataDefinition();
2833 newProperty.setConstraints(Collections.singletonList(constraint));
2834 result = serviceFilterOperation.addNewProperty(serviceId, componentInstanceId,serviceFilter,newProperty);
2837 result = serviceFilterOperation.deleteConstraint(serviceId, componentInstanceId, serviceFilter, position);
2840 log.error("Unsupported operation "+action);
2841 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
2845 if (result.isRight()) {
2846 titanDao.rollback();
2847 return Either.right(componentsUtils.getResponseFormat(
2848 componentsUtils.convertFromStorageResponse(result.right().value(), ComponentTypeEnum.SERVICE),
2851 serviceFilterResult = result.left().value();
2855 } catch (Exception e) {
2856 titanDao.rollback();
2857 log.error("Exception occurred during add or update node filter property values: {}", e.getMessage(),
2859 return Either.right(componentsUtils.getResponseFormat(ActionStatus.GENERAL_ERROR));
2862 if (lockResult != null && lockResult.isLeft() && lockResult.left().value()) {
2863 graphLockOperation.unlockComponent(storedService.getUniqueId(), NodeTypeEnum.Service);
2866 return Either.left(serviceFilterResult);