diff options
author | Tal Gitelman <tg851x@intl.att.com> | 2017-06-29 19:30:00 +0300 |
---|---|---|
committer | Michael Lando <ml636r@att.com> | 2017-06-29 21:32:19 +0300 |
commit | ed7e1c3dfe332abc67ed943717db2ee94406f95e (patch) | |
tree | e0f2f39596656456272900f59aadc3dff6c6e828 /catalog-be/src | |
parent | 68ccc45de18f41cddb79de33a245bceb3b063ffb (diff) |
[SDC] rebase code
Change-Id: I456ec65a233d277e6bae35e140f2e3da5765bae6
Signed-off-by: Tal Gitelman <tg851x@intl.att.com>
Signed-off-by: Michael Lando <ml636r@att.com>
Diffstat (limited to 'catalog-be/src')
13 files changed, 950 insertions, 514 deletions
diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ArtifactsBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ArtifactsBusinessLogic.java index 003fe66d9d..e5d380a836 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ArtifactsBusinessLogic.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ArtifactsBusinessLogic.java @@ -23,7 +23,6 @@ package org.openecomp.sdc.be.components.impl; import java.io.ByteArrayInputStream; import java.io.IOException; import java.math.BigDecimal; -import java.rmi.activation.ActivationSystem; import java.util.ArrayList; import java.util.Comparator; import java.util.EnumMap; @@ -1335,7 +1334,7 @@ public class ArtifactsBusinessLogic extends BaseBusinessLogic { isUpdated = true; } if (CollectionUtils.isNotEmpty(group.getArtifactsUuid()) && group.getArtifactsUuid().contains(foundArtifact.getArtifactUUID())) { - group.getArtifacts().remove(foundArtifact.getArtifactUUID()); + group.getArtifactsUuid().remove(foundArtifact.getArtifactUUID()); isUpdated = true; } if (isUpdated) { @@ -4087,7 +4086,7 @@ public class ArtifactsBusinessLogic extends BaseBusinessLogic { Wrapper<ResponseFormat> errorWrapper = new Wrapper<>(); Either<byte[], ResponseFormat> result; byte[] downloadedArtifact = null; - Component component = getLatestComponentByUuid(componentType, componentUuid, errorWrapper); + Component component = getComponentByUuid(componentType, componentUuid, errorWrapper); if (errorWrapper.isEmpty()) { auditAdditionalParam.put(AuditingFieldsKeysEnum.AUDIT_RESOURCE_NAME, component.getName()); downloadedArtifact = downloadArtifact(component.getDeploymentArtifacts(), artifactUUID, errorWrapper, component.getName()); @@ -4686,7 +4685,7 @@ public class ArtifactsBusinessLogic extends BaseBusinessLogic { private ComponentInstance getRelatedComponentInstance(ComponentTypeEnum componentType, String componentUuid, String resourceInstanceName, Wrapper<ResponseFormat> errorWrapper) { ComponentInstance componentInstance = null; String normalizedName = ValidationUtils.normalizeComponentInstanceName(resourceInstanceName); - Component component = getLatestComponentByUuid(componentType, componentUuid, errorWrapper); + Component component = getComponentByUuid(componentType, componentUuid, errorWrapper); if (errorWrapper.isEmpty()) { componentInstance = component.getComponentInstances().stream().filter(ci -> ValidationUtils.normalizeComponentInstanceName(ci.getName()).equals(normalizedName)).findFirst().orElse(null); if (componentInstance == null) { @@ -4767,6 +4766,26 @@ public class ArtifactsBusinessLogic extends BaseBusinessLogic { } return component; } + + private Component getComponentByUuid(ComponentTypeEnum componentType, String componentUuid, Wrapper<ResponseFormat> errorWrapper) { + Component component = null; + Either<List<Component>, StorageOperationStatus> getComponentRes = toscaOperationFacade.getComponentListByUuid(componentUuid, null); + if (getComponentRes.isRight()) { + StorageOperationStatus status = getComponentRes.right().value(); + log.debug("Could not fetch component with type {} and uuid {}. Status is {}. ", componentType, componentUuid, status); + errorWrapper.setInnerElement(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(status))); + } else { + List<Component> value = getComponentRes.left().value(); + if (value.isEmpty()){ + log.debug("Could not fetch component with type {} and uuid {}.", componentType, componentUuid); + ActionStatus status = componentType == ComponentTypeEnum.RESOURCE ? ActionStatus.RESOURCE_NOT_FOUND : ActionStatus.SERVICE_NOT_FOUND; + errorWrapper.setInnerElement(componentsUtils.getResponseFormat(status)); + } else { + component = value.get(0); + } + } + return component; + } private String getLatestParentArtifactDataIdByArtifactUUID(String artifactUUID, Wrapper<ResponseFormat> errorWrapper, String parentId, ComponentTypeEnum componentType) { String artifactId = null; diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ComponentInstanceBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ComponentInstanceBusinessLogic.java index 203a63894b..f917d60553 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ComponentInstanceBusinessLogic.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ComponentInstanceBusinessLogic.java @@ -617,6 +617,7 @@ public abstract class ComponentInstanceBusinessLogic extends BaseBusinessLogic { Either<ComponentInstance, ResponseFormat> resultOp = null; Optional<ComponentInstance> componentInstanceOptional = null; Either<ImmutablePair<Component, String>, StorageOperationStatus> updateRes = null; + ComponentInstance oldComponentInstance = null; if (resultOp == null) { componentInstanceOptional = containerComponent.getComponentInstances().stream().filter(ci -> ci.getUniqueId().equals(componentInstance.getUniqueId())).findFirst(); @@ -626,7 +627,7 @@ public abstract class ComponentInstanceBusinessLogic extends BaseBusinessLogic { } } if (resultOp == null) { - ComponentInstance oldComponentInstance = componentInstanceOptional.get(); + oldComponentInstance = componentInstanceOptional.get(); String newInstanceName = componentInstance.getName(); Boolean isUniqueName = validateInstanceNameUniquenessUponUpdate(containerComponent, oldComponentInstance, newInstanceName); if (!isUniqueName) { @@ -635,7 +636,7 @@ public abstract class ComponentInstanceBusinessLogic extends BaseBusinessLogic { } } if (resultOp == null) { - updateRes = toscaOperationFacade.updateComponentInstanceMetadataOfTopologyTemplate(containerComponent, origComponent, componentInstance); + updateRes = toscaOperationFacade.updateComponentInstanceMetadataOfTopologyTemplate(containerComponent, origComponent, updateComponentInstanceMetadata(oldComponentInstance, componentInstance)); if (updateRes.isRight()) { CommonUtility.addRecordToLog(log, LogLevelEnum.DEBUG, "Failed to update metadata of component instance {} belonging to container component {}. Status is {}. ", componentInstance.getName(), containerComponent.getName(), updateRes.right().value()); @@ -660,6 +661,13 @@ public abstract class ComponentInstanceBusinessLogic extends BaseBusinessLogic { return resultOp; } + private ComponentInstance updateComponentInstanceMetadata(ComponentInstance oldComponentInstance, ComponentInstance newComponentInstance) { + oldComponentInstance.setName(newComponentInstance.getName()); + oldComponentInstance.setModificationTime(System.currentTimeMillis()); + oldComponentInstance.setCustomizationUUID(UUID.randomUUID().toString()); + return oldComponentInstance; + } + public Either<ComponentInstance, ResponseFormat> deleteComponentInstance(String containerComponentParam, String containerComponentId, String componentInstanceId, String userId) { Either<User, ResponseFormat> resp = validateUserExists(userId, "delete Component Instance", false); diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ElementBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ElementBusinessLogic.java index dbcc0aec68..669b84f229 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ElementBusinessLogic.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ElementBusinessLogic.java @@ -25,6 +25,7 @@ import java.util.ArrayList; import java.util.EnumMap; import java.util.HashMap; import java.util.HashSet; +import java.util.LinkedList; import java.util.List; import java.util.Map; import java.util.Optional; @@ -110,7 +111,11 @@ public class ElementBusinessLogic extends BaseBusinessLogic { * @return */ public Either<Map<String, List<? extends Component>>, ResponseFormat> getFollowed(User user) { - Either<Map<String, List<? extends Component>>, ResponseFormat> response = null; + // Used for not getting duplicated followed. Cheaper than checking ArrayList.contains + Either<Map<String, Set<? extends Component>>, ResponseFormat> response = null; + // Used for returning as the code requires. + Either<Map<String, List<? extends Component>>, ResponseFormat> arrayResponse = null; + // Getting the role String role = user.getRole(); String userId = null; @@ -155,12 +160,25 @@ public class ElementBusinessLogic extends BaseBusinessLogic { response = Either.right(componentsUtils.getResponseFormat(ActionStatus.RESTRICTED_OPERATION)); break; } - return response; + //converting the Set to List so the rest of the code will handle it normally (Was changed because the same element with the same uuid was returned twice) + return convertedToListResponse(response); } - private Either<Map<String, List<? extends Component>>, ResponseFormat> handleAdmin() { - Either<Map<String, List<? extends Component>>, ResponseFormat> response; + private Either<Map<String,List<? extends Component>>,ResponseFormat> convertedToListResponse(Either<Map<String, Set<? extends Component>>, ResponseFormat> setResponse) { + + Map<String, List<? extends Component>> arrayResponse = new HashMap<>(); + if (setResponse.isLeft()) { + for (Map.Entry<String, Set<? extends Component>> entry : setResponse.left().value().entrySet()) { + arrayResponse.put(entry.getKey(), (new ArrayList(new HashSet(entry.getValue())))); + } + return Either.left(arrayResponse); + } + return Either.right(setResponse.right().value()); + } + + private Either<Map<String, Set<? extends Component>>, ResponseFormat> handleAdmin() { + Either<Map<String, Set<? extends Component>>, ResponseFormat> response; // userId should stay null Set<LifecycleStateEnum> lifecycleStates = new HashSet<LifecycleStateEnum>(); Set<LifecycleStateEnum> lastStateStates = new HashSet<LifecycleStateEnum>(); @@ -169,10 +187,10 @@ public class ElementBusinessLogic extends BaseBusinessLogic { return response; } - private Either<Map<String, List<? extends Component>>, ResponseFormat> handleDesigner(String userId) { + private Either<Map<String, Set<? extends Component>>, ResponseFormat> handleDesigner(String userId) { Set<LifecycleStateEnum> lifecycleStates = new HashSet<LifecycleStateEnum>(); Set<LifecycleStateEnum> lastStateStates = new HashSet<LifecycleStateEnum>(); - Either<Map<String, List<? extends Component>>, ResponseFormat> response; + Either<Map<String, Set<? extends Component>>, ResponseFormat> response; lifecycleStates.add(LifecycleStateEnum.NOT_CERTIFIED_CHECKIN); lifecycleStates.add(LifecycleStateEnum.NOT_CERTIFIED_CHECKOUT); lifecycleStates.add(LifecycleStateEnum.READY_FOR_CERTIFICATION); @@ -184,22 +202,22 @@ public class ElementBusinessLogic extends BaseBusinessLogic { return response; } - private Either<Map<String, List<? extends Component>>, ResponseFormat> handleGovernor(String userId) { - Either<Map<String, List<? extends Component>>, ResponseFormat> result = handleFollowedCertifiedServices(null); + private Either<Map<String, Set<? extends Component>>, ResponseFormat> handleGovernor(String userId) { + Either<Map<String, Set<? extends Component>>, ResponseFormat> result = handleFollowedCertifiedServices(null); return result; } - private Either<Map<String, List<? extends Component>>, ResponseFormat> handleProductStrategist(String userId) { + private Either<Map<String, Set<? extends Component>>, ResponseFormat> handleProductStrategist(String userId) { // Should be empty list according to Ella, 13/03/16 - Map<String, List<? extends Component>> result = new HashMap<String, List<? extends Component>>(); - result.put("products", new ArrayList<>()); + Map<String, Set<? extends Component>> result = new HashMap<String, Set<? extends Component>>(); + result.put("products", new HashSet<>()); return Either.left(result); } - private Either<Map<String, List<? extends Component>>, ResponseFormat> handleProductManager(String userId) { + private Either<Map<String, Set<? extends Component>>, ResponseFormat> handleProductManager(String userId) { Set<LifecycleStateEnum> lifecycleStates = new HashSet<LifecycleStateEnum>(); Set<LifecycleStateEnum> lastStateStates = new HashSet<LifecycleStateEnum>(); - Either<Map<String, List<? extends Component>>, ResponseFormat> response; + Either<Map<String, Set<? extends Component>>, ResponseFormat> response; lifecycleStates.add(LifecycleStateEnum.NOT_CERTIFIED_CHECKIN); lifecycleStates.add(LifecycleStateEnum.NOT_CERTIFIED_CHECKOUT); lifecycleStates.add(LifecycleStateEnum.READY_FOR_CERTIFICATION); @@ -211,47 +229,47 @@ public class ElementBusinessLogic extends BaseBusinessLogic { return response; } - private Either<Map<String, List<? extends Component>>, ResponseFormat> handleOps(String userId) { + private Either<Map<String, Set<? extends Component>>, ResponseFormat> handleOps(String userId) { Set<DistributionStatusEnum> distStatus = new HashSet<DistributionStatusEnum>(); distStatus.add(DistributionStatusEnum.DISTRIBUTION_APPROVED); distStatus.add(DistributionStatusEnum.DISTRIBUTED); - Either<Map<String, List<? extends Component>>, ResponseFormat> result = handleFollowedCertifiedServices(distStatus); + Either<Map<String, Set<? extends Component>>, ResponseFormat> result = handleFollowedCertifiedServices(distStatus); return result; } - private Either<Map<String, List<? extends Component>>, ResponseFormat> handleFollowedCertifiedServices(Set<DistributionStatusEnum> distStatus) { + private Either<Map<String, Set<? extends Component>>, ResponseFormat> handleFollowedCertifiedServices(Set<DistributionStatusEnum> distStatus) { Either<List<Service>, StorageOperationStatus> services = toscaOperationFacade.getCertifiedServicesWithDistStatus(distStatus); if (services.isLeft()) { - Map<String, List<? extends Component>> result = new HashMap<String, List<? extends Component>>(); - List<Service> list = new ArrayList<>(); - list.addAll(services.left().value()); - result.put("services", list); + Map<String, Set<? extends Component>> result = new HashMap<>(); + Set<Service> set = new HashSet<>(); + set.addAll(services.left().value()); + result.put("services", set); return Either.left(result); } else { return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(services.right().value()))); } } - private Either<Map<String, List<? extends Component>>, ResponseFormat> handleTester(String userId) { + private Either<Map<String, Set<? extends Component>>, ResponseFormat> handleTester(String userId) { Set<LifecycleStateEnum> lifecycleStates = new HashSet<LifecycleStateEnum>(); lifecycleStates.add(LifecycleStateEnum.CERTIFICATION_IN_PROGRESS); lifecycleStates.add(LifecycleStateEnum.READY_FOR_CERTIFICATION); - Either<Map<String, List<? extends Component>>, ResponseFormat> result = getFollowedResourcesAndServices(null, lifecycleStates, null); + Either<Map<String, Set<? extends Component>>, ResponseFormat> result = getFollowedResourcesAndServices(null, lifecycleStates, null); return result; } - private Either<Map<String, List<? extends Component>>, ResponseFormat> getFollowedResourcesAndServices(String userId, Set<LifecycleStateEnum> lifecycleStates, Set<LifecycleStateEnum> lastStateStates) { + private Either<Map<String, Set<? extends Component>>, ResponseFormat> getFollowedResourcesAndServices(String userId, Set<LifecycleStateEnum> lifecycleStates, Set<LifecycleStateEnum> lastStateStates) { try { - Either<List<Resource>, StorageOperationStatus> resources = toscaOperationFacade.getFollowed(userId, lifecycleStates, lastStateStates, ComponentTypeEnum.RESOURCE); + Either<Set<Resource>, StorageOperationStatus> resources = toscaOperationFacade.getFollowed(userId, lifecycleStates, lastStateStates, ComponentTypeEnum.RESOURCE); if (resources.isLeft()) { - Either<List<Service>, StorageOperationStatus> services = toscaOperationFacade.getFollowed(userId, lifecycleStates, lastStateStates, ComponentTypeEnum.SERVICE); + Either<Set<Service>, StorageOperationStatus> services = toscaOperationFacade.getFollowed(userId, lifecycleStates, lastStateStates, ComponentTypeEnum.SERVICE); if (services.isLeft()) { - Map<String, List<? extends Component>> result = new HashMap<String, List<? extends Component>>(); + Map<String, Set<? extends Component>> result = new HashMap<String, Set<? extends Component>>(); result.put("services", services.left().value()); result.put("resources", resources.left().value()); return Either.left(result); @@ -266,10 +284,10 @@ public class ElementBusinessLogic extends BaseBusinessLogic { } } - private Either<Map<String, List<? extends Component>>, ResponseFormat> getFollowedProducts(String userId, Set<LifecycleStateEnum> lifecycleStates, Set<LifecycleStateEnum> lastStateStates) { - Either<List<Product>, StorageOperationStatus> products = toscaOperationFacade.getFollowed(userId, lifecycleStates, lastStateStates, ComponentTypeEnum.PRODUCT); + private Either<Map<String, Set<? extends Component>>, ResponseFormat> getFollowedProducts(String userId, Set<LifecycleStateEnum> lifecycleStates, Set<LifecycleStateEnum> lastStateStates) { + Either<Set<Product>, StorageOperationStatus> products = toscaOperationFacade.getFollowed(userId, lifecycleStates, lastStateStates, ComponentTypeEnum.PRODUCT); if (products.isLeft()) { - Map<String, List<? extends Component>> result = new HashMap<String, List<? extends Component>>(); + Map<String, Set<? extends Component>> result = new HashMap<>(); result.put("products", products.left().value()); return Either.left(result); } else { @@ -1031,10 +1049,9 @@ public class ElementBusinessLogic extends BaseBusinessLogic { } Either<List<Component>, StorageOperationStatus> result = getFilteredComponents(filters, assetTypeEnum, false); - - if (result.isRight()) {// category hierarchy mismatch or - // category/subCategory/distributionStatus not - // found + + // category hierarchy mismatch or category/subCategory/distributionStatus not found + if (result.isRight()) { List<String> params = getErrorResponseParams(filters, assetTypeEnum); return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(result.right().value()), params.get(0), params.get(1), params.get(2))); } @@ -1046,7 +1063,7 @@ public class ElementBusinessLogic extends BaseBusinessLogic { } private Either<List<Component>, StorageOperationStatus> getFilteredComponents(Map<FilterKeyEnum, String> filters, ComponentTypeEnum assetType, boolean inTransaction) { - Either<List<Component>, StorageOperationStatus> assetResult = null; + Either<List<Component>, StorageOperationStatus> assetResult = Either.left(new LinkedList<>()); if(assetType == ComponentTypeEnum.RESOURCE){ assetResult = getFilteredResouces(filters, inTransaction); diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogic.java index c3471e46e1..f545548b95 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogic.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/InputsBusinessLogic.java @@ -20,16 +20,14 @@ package org.openecomp.sdc.be.components.impl; -import java.util.ArrayList; -import java.util.Collections; -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import java.util.Optional; +import java.util.*; import java.util.Map.Entry; import java.util.function.BiConsumer; import java.util.stream.Collectors; +import jline.internal.Log; +import org.apache.commons.collections.CollectionUtils; +import org.apache.commons.collections.MapUtils; import org.json.simple.JSONObject; import org.openecomp.sdc.be.components.validation.ComponentValidations; import org.openecomp.sdc.be.config.BeEcompErrorManager; @@ -77,13 +75,15 @@ public class InputsBusinessLogic extends BaseBusinessLogic { private static final String GET_INPUT = "get_input"; + private static final short LOOP_PROTECTION_LEVEL = 10 ; + private static String ASSOCIATING_INPUT_TO_PROP = "AssociatingInputToComponentInstanceProperty"; - private Gson gson = new Gson(); - + private Gson gson = new Gson(); + /** * associate inputs to a given component with paging - * + * * @param componentId * @param userId * @param fromId @@ -97,10 +97,10 @@ public class InputsBusinessLogic extends BaseBusinessLogic { if (resp.isRight()) { return Either.right(resp.right().value()); } - - + + ComponentParametersView filters = new ComponentParametersView(); - filters.disableAll(); + filters.disableAll(); filters.setIgnoreInputs(false); Either<org.openecomp.sdc.be.model.Component, StorageOperationStatus> getComponentEither = toscaOperationFacade.getToscaElement(componentId, filters); @@ -108,15 +108,15 @@ public class InputsBusinessLogic extends BaseBusinessLogic { ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(getComponentEither.right().value()); log.debug("Failed to found component {}, error: {}", componentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); - + } org.openecomp.sdc.be.model.Component component = getComponentEither.left().value(); List<InputDefinition> inputs = component.getInputs(); - + return Either.left(inputs); } - + public Either<List<ComponentInstanceInput>, ResponseFormat> getComponentInstanceInputs(String userId, String componentId, String componentInstanceId) { Either<User, ResponseFormat> resp = validateUserExists(userId, "get Inputs", false); @@ -124,10 +124,10 @@ public class InputsBusinessLogic extends BaseBusinessLogic { if (resp.isRight()) { return Either.right(resp.right().value()); } - - + + ComponentParametersView filters = new ComponentParametersView(); - filters.disableAll(); + filters.disableAll(); filters.setIgnoreInputs(false); filters.setIgnoreComponentInstances(false); filters.setIgnoreComponentInstancesInputs(false); @@ -137,7 +137,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(getComponentEither.right().value()); log.debug("Failed to found component {}, error: {}", componentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); - + } org.openecomp.sdc.be.model.Component component = getComponentEither.left().value(); @@ -152,7 +152,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { /** * associate properties to a given component instance input - * + * * @param instanceId * @param userId * @param inputId @@ -169,58 +169,58 @@ public class InputsBusinessLogic extends BaseBusinessLogic { ComponentParametersView filters = new ComponentParametersView(); filters.disableAll(); filters.setIgnoreComponentInstances(false); - + if(!instanceId.equals(inputId)){ - - + + Either<org.openecomp.sdc.be.model.Component, StorageOperationStatus> getComponentEither = toscaOperationFacade.getToscaElement(parentId, filters); - + if(getComponentEither.isRight()){ ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(getComponentEither.right().value()); log.debug("Failed to found component {}, error: {}", parentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); - + } component = getComponentEither.left().value(); Optional<ComponentInstance> ciOp = component.getComponentInstances().stream().filter(ci ->ci.getUniqueId().equals(instanceId)).findAny(); if(ciOp.isPresent()){ parentId = ciOp.get().getComponentUid(); } - - } - - filters.setIgnoreInputs(false); - + + } + + filters.setIgnoreInputs(false); + filters.setIgnoreComponentInstancesProperties(false); filters.setIgnoreComponentInstancesInputs(false); filters.setIgnoreProperties(false); - + Either<org.openecomp.sdc.be.model.Component, StorageOperationStatus> getComponentEither = toscaOperationFacade.getToscaElement(parentId, filters); - + if(getComponentEither.isRight()){ ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(getComponentEither.right().value()); log.debug("Failed to found component {}, error: {}", parentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); - + } component = getComponentEither.left().value(); - + Optional<InputDefinition> op = component.getInputs().stream().filter(in -> in.getUniqueId().equals(inputId)).findFirst(); if(!op.isPresent()){ ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(getComponentEither.right().value()); log.debug("Failed to found input {} under component {}, error: {}", inputId, parentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); } - + return Either.left(getComponentInstancePropertiesByInputId(component, inputId)); } - + public Either<InputDefinition, ResponseFormat> updateInputValue(ComponentTypeEnum componentType, String componentId, InputDefinition input, String userId, boolean shouldLockComp, boolean inTransaction) { - + Either<InputDefinition, ResponseFormat> result = null; org.openecomp.sdc.be.model.Component component = null; - + try { Either<User, ResponseFormat> resp = validateUserExists(userId, "get input", false); @@ -232,7 +232,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { ComponentParametersView componentParametersView = new ComponentParametersView(); componentParametersView.disableAll(); - componentParametersView.setIgnoreInputs(false); + componentParametersView.setIgnoreInputs(false); componentParametersView.setIgnoreUsers(false); Either<? extends org.openecomp.sdc.be.model.Component, ResponseFormat> validateComponent = validateComponentExists(componentId, componentType, componentParametersView); @@ -264,7 +264,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } Map<String, DataTypeDefinition> dataTypes = allDataTypes.left().value(); - + Optional<InputDefinition> op = component.getInputs().stream().filter(in -> in.getUniqueId().equals(input.getUniqueId())).findFirst(); if(!op.isPresent()){ ActionStatus actionStatus = ActionStatus.COMPONENT_NOT_FOUND; @@ -273,7 +273,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { return result; } InputDefinition currentInput = op.get(); - + String innerType = null; String propertyType = currentInput.getType(); ToscaPropertyType type = ToscaPropertyType.isValidType(propertyType); @@ -293,7 +293,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { innerType = propDef.getType(); } // Specific Update Logic - + Either<Object, Boolean> isValid = propertyOperation.validateAndUpdatePropertyValue(propertyType, input.getDefaultValue(), true, innerType, allDataTypes.left().value()); String newValue = currentInput.getDefaultValue(); @@ -308,23 +308,23 @@ public class InputsBusinessLogic extends BaseBusinessLogic { newValue = object.toString(); } } - + currentInput.setDefaultValue(newValue); - + Either<InputDefinition, StorageOperationStatus> status = toscaOperationFacade.updateInputOfComponent(component, currentInput); - + if(status.isRight()){ ActionStatus actionStatus = componentsUtils.convertFromStorageResponseForResourceInstanceProperty(status.right().value()); result = Either.right(componentsUtils.getResponseFormat(actionStatus, "")); return result; } - - + + result = Either.left(status.left().value()); - + return result; - - + + }finally { if (false == inTransaction) { @@ -357,28 +357,28 @@ public class InputsBusinessLogic extends BaseBusinessLogic { org.openecomp.sdc.be.model.Component component = null; ComponentParametersView filters = new ComponentParametersView(); filters.disableAll(); - filters.setIgnoreComponentInstances(false); - filters.setIgnoreInputs(false); + filters.setIgnoreComponentInstances(false); + filters.setIgnoreInputs(false); filters.setIgnoreComponentInstancesInputs(false); filters.setIgnoreProperties(false); - + Either<org.openecomp.sdc.be.model.Component, StorageOperationStatus> getComponentEither = toscaOperationFacade.getToscaElement(parentId, filters); - + if(getComponentEither.isRight()){ ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(getComponentEither.right().value()); log.debug("Failed to found component {}, error: {}", parentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); - + } component = getComponentEither.left().value(); - + Optional<InputDefinition> op = component.getInputs().stream().filter(in -> in.getUniqueId().equals(inputId)).findFirst(); if(!op.isPresent()){ ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(getComponentEither.right().value()); log.debug("Failed to found input {} under component {}, error: {}", inputId, parentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); } - + return Either.left(getComponentInstanceInputsByInputId(component, inputId)); } @@ -387,11 +387,11 @@ public class InputsBusinessLogic extends BaseBusinessLogic { Either<List<InputDefinition>, ResponseFormat> result = null; org.openecomp.sdc.be.model.Component component = null; - + Map<String, List<ComponentInstanceInput>> inputsValueToCreateMap = new HashMap<>(); - Map<String, List<ComponentInstanceProperty>> propertiesToCreateMap = new HashMap<>(); + Map<String, List<ComponentInstanceProperty>> propertiesToCreateMap = new HashMap<>(); Map<String, InputDefinition> inputsToCreate = new HashMap<>(); - + try { Either<User, ResponseFormat> resp = validateUserExists(userId, "get Properties by input", false); @@ -441,7 +441,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { ////////////////////////////////////////////////////////////////////////////////////////////////////// - + List<InputDefinition> resList = new ArrayList<InputDefinition>(); Map<String, List<InputDefinition>> newInputsMap = componentInstInputsMapUi.getComponentInstanceInputsMap(); List<ComponentInstance> ciList = component.getComponentInstances(); @@ -450,7 +450,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { for (Entry<String, List<InputDefinition>> entry : newInputsMap.entrySet()) { List<ComponentInstanceInput> inputsValueToCreate = new ArrayList<>(); String compInstId = entry.getKey(); - + Optional<ComponentInstance> op = ciList.stream().filter(ci -> ci.getUniqueId().equals(compInstId)).findAny(); if(!op.isPresent()){ ActionStatus actionStatus = ActionStatus.INVALID_CONTENT; @@ -468,12 +468,12 @@ public class InputsBusinessLogic extends BaseBusinessLogic { return result; } org.openecomp.sdc.be.model.Component origComponent = origComponentEither.left().value(); - + List<InputDefinition> inputs = entry.getValue(); if (inputs != null && !inputs.isEmpty()) { - - for (InputDefinition input : inputs) { + + for (InputDefinition input : inputs) { StorageOperationStatus status = addInputsToComponent(componentId, inputsToCreate, allDataTypes.left().value(), resList, index, inputsValueToCreate, compInstId, compInstname, origComponent, input); if(status != StorageOperationStatus.OK ){ @@ -489,51 +489,51 @@ public class InputsBusinessLogic extends BaseBusinessLogic { inputsValueToCreateMap.put(compInstId, inputsValueToCreate); } } - + } - + Map<String, List<ComponentInstancePropInput>> newInputsPropsMap = componentInstInputsMapUi.getComponentInstanceProperties(); if (newInputsPropsMap != null && !newInputsPropsMap.isEmpty()) { - + result = createInputsFromProperty(component, origComponentMap, inputsToCreate, propertiesToCreateMap, dataTypes, resList, newInputsPropsMap); - + if (result.isRight()) { log.debug("Failed to create inputs of resource for id {} error {}", component.getUniqueId(), result.right().value()); return result; } resList = result.left().value(); - + } - - + + Either<List<InputDefinition>, StorageOperationStatus> assotiateInputsEither = toscaOperationFacade.addInputsToComponent(inputsToCreate, component.getUniqueId()); if(assotiateInputsEither.isRight()){ log.debug("Failed to create inputs under component {}. Status is {}", component.getUniqueId(), assotiateInputsEither.right().value()); result = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(assotiateInputsEither.right().value()))); return result; } - + Either<Map<String, List<ComponentInstanceProperty>>, StorageOperationStatus> assotiatePropsEither = toscaOperationFacade.addComponentInstancePropertiesToComponent(component, propertiesToCreateMap, component.getUniqueId()); if(assotiatePropsEither.isRight()){ log.debug("Failed to add inputs values under component {}. Status is {}", component.getUniqueId(), assotiateInputsEither.right().value()); result = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(assotiateInputsEither.right().value()))); return result; } - + Either<Map<String, List<ComponentInstanceInput>>, StorageOperationStatus> addciInputsEither = toscaOperationFacade.addComponentInstanceInputsToComponent(component, inputsValueToCreateMap); if(addciInputsEither.isRight()){ log.debug("Failed to add inputs values under component {}. Status is {}", component.getUniqueId(), assotiateInputsEither.right().value()); result = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(assotiateInputsEither.right().value()))); return result; } - - - - + + + + result = Either.left(resList); return result; - /////////////////////////////////////////////////////////////////////////////////////////// - + /////////////////////////////////////////////////////////////////////////////////////////// + } finally { if (false == inTransaction) { @@ -558,29 +558,29 @@ public class InputsBusinessLogic extends BaseBusinessLogic { private StorageOperationStatus addInputsToComponent(String componentId, Map<String, InputDefinition> inputsToCreate, Map<String, DataTypeDefinition> allDataTypes, List<InputDefinition> resList, int index, List<ComponentInstanceInput> inputsValueToCreate, String compInstId, String compInstname, org.openecomp.sdc.be.model.Component origComponent, InputDefinition input) { - + Either<List<InputDefinition>, ResponseFormat> result; String innerType = null; InputDefinition oldInput = origComponent.getInputs().stream().filter(ciIn -> ciIn.getUniqueId().equals(input.getUniqueId())).findAny().get(); String serviceInputName = compInstname + "_" + input.getName(); input.setName(serviceInputName); - + JSONObject jobject = new JSONObject(); jobject.put(GET_INPUT, input.getName()); - + ComponentInstanceInput inputValue = new ComponentInstanceInput(oldInput, jobject.toJSONString(), null); - + Either<String, StorageOperationStatus> validatevalueEiter = validateInputValueBeforeCreate(inputValue, jobject.toJSONString(), false, innerType, allDataTypes); - if (validatevalueEiter.isRight()) { - + if (validatevalueEiter.isRight()) { + return validatevalueEiter.right().value(); - } - - String uniqueId = UniqueIdBuilder.buildResourceInstanceInputValueUid(compInstId, index++); + } + + String uniqueId = UniqueIdBuilder.buildResourceInstanceInputValueUid(compInstId, index++); inputValue.setUniqueId(uniqueId); inputValue.setValue(validatevalueEiter.left().value()); - - + + input.setUniqueId(UniqueIdBuilder.buildPropertyUniqueId(componentId, input.getName())); input.setSchema(oldInput.getSchema()); input.setDefaultValue(oldInput.getDefaultValue()); @@ -592,20 +592,21 @@ public class InputsBusinessLogic extends BaseBusinessLogic { input.setRequired(oldInput.isRequired()); input.setOwnerId(null); input.setParentUniqueId(null); + input.setInstanceUniqueId(compInstId); inputsToCreate.put(input.getName(), input); - - - + + + List<GetInputValueDataDefinition> getInputValues = new ArrayList<>(); GetInputValueDataDefinition getInputValueDataDefinition = new GetInputValueDataDefinition(); getInputValueDataDefinition.setInputId(input.getUniqueId()); getInputValueDataDefinition.setInputName(input.getName()); getInputValues.add(getInputValueDataDefinition); - inputValue.setGetInputValues(getInputValues); - + inputValue.setGetInputValues(getInputValues); + inputsValueToCreate.add(inputValue); input.setInputs(inputsValueToCreate); - + resList.add(input); return StorageOperationStatus.OK; } @@ -685,11 +686,11 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } public Either<List<InputDefinition>, ResponseFormat> createInputsInGraph(Map<String, InputDefinition> inputs, org.openecomp.sdc.be.model.Component component, User user, boolean inTransaction) { - - List<InputDefinition> resList = inputs.values().stream().collect(Collectors.toList()); + + List<InputDefinition> resList = inputs.values().stream().collect(Collectors.toList()); Either<List<InputDefinition>, ResponseFormat> result = Either.left(resList); List<InputDefinition> resourceProperties = component.getInputs(); - + if(inputs != null && !inputs.isEmpty()){ Either<Map<String, DataTypeDefinition>, ResponseFormat> allDataTypes = getAllDataTypes(applicationDataTypeCache); if (allDataTypes.isRight()) { @@ -697,16 +698,16 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } Map<String, DataTypeDefinition> dataTypes = allDataTypes.left().value(); - + for (Map.Entry<String, InputDefinition> inputDefinition : inputs.entrySet()) { String inputName = inputDefinition.getKey(); - inputDefinition.getValue().setName(inputName); - + inputDefinition.getValue().setName(inputName); + Either<InputDefinition, ResponseFormat> preparedInputEither = prepareAndValidateInputBeforeCreate(inputDefinition.getValue(), dataTypes); if(preparedInputEither.isRight()){ return Either.right(preparedInputEither.right().value()); } - + } if (resourceProperties != null) { Map<String, InputDefinition> generatedInputs = resourceProperties.stream().collect(Collectors.toMap(i -> i.getName(), i -> i)); @@ -716,28 +717,104 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } inputs = mergeEither.left().value(); } - + Either<List<InputDefinition>, StorageOperationStatus> assotiateInputsEither = toscaOperationFacade.createAndAssociateInputs(inputs, component.getUniqueId()); if(assotiateInputsEither.isRight()){ log.debug("Failed to create inputs under component {}. Status is {}", component.getUniqueId(), assotiateInputsEither.right().value()); return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(assotiateInputsEither.right().value()))); } result = Either.left(assotiateInputsEither.left().value()); - + } - - + + return result; } + + /* Mutates the object + * Tail recurse -> traverse the tosca elements and remove nested empty map properties + * this only handles nested maps, other objects are left untouched (even a Set containing a map) since behaviour is unexpected + * + * @param toscaElement - expected map of tosca values + * @return mutated @param toscaElement , where empty maps are deleted , return null for empty map. + **/ + private Object cleanEmptyNestedValuesInMap(Object toscaElement , short loopProtectionLevel ){ + //region - Stop if map is empty + if (loopProtectionLevel<=0 || toscaElement==null || !(toscaElement instanceof Map)) + return toscaElement; + //endregion + //region - Remove empty map entries & return null iff empty map + if ( MapUtils.isNotEmpty( (Map)toscaElement ) ) { + Object ret; + Set<Object> keysToRemove = new HashSet<>(); // use different set to avoid ConcurrentModificationException + for( Object key : ((Map)toscaElement).keySet() ) { + Object value = ((Map) toscaElement).get(key); + ret = cleanEmptyNestedValuesInMap(value , --loopProtectionLevel ); + if ( ret == null ) + keysToRemove.add(key); + } + Collection set = ((Map) toscaElement).keySet(); + if (CollectionUtils.isNotEmpty(set)) + set.removeAll(keysToRemove); + + if ( isEmptyNestedMap(toscaElement) ) // similar to < if ( MapUtils.isEmpty( (Map)toscaElement ) ) > ,but adds nested map check + return null; + } + //endregion + else + return null; + return toscaElement; + } + + //@returns true iff map nested maps are all empty + //ignores other collection objects + private boolean isEmptyNestedMap(Object element){ + boolean isEmpty = true; + if (element != null){ + if ( element instanceof Map ){ + if (MapUtils.isEmpty((Map)element)) + isEmpty = true; + else + { + for( Object key : ((Map)(element)).keySet() ){ + Object value = ((Map)(element)).get(key); + isEmpty &= isEmptyNestedMap( value ); + } + } + } else { + isEmpty = false; + } + } + return isEmpty; + } + + public Either cleanNestedMap( Map mappedToscaTemplate , boolean deepClone ){ + if (MapUtils.isNotEmpty( mappedToscaTemplate ) ){ + if (deepClone){ + if (!(mappedToscaTemplate instanceof HashMap)) + return Either.right("expecting mappedToscaTemplate as HashMap ,recieved "+ mappedToscaTemplate.getClass().getSimpleName() ); + else + mappedToscaTemplate = (HashMap)((HashMap) mappedToscaTemplate).clone(); + } + return Either.left( (Map) cleanEmptyNestedValuesInMap( mappedToscaTemplate , InputsBusinessLogic.LOOP_PROTECTION_LEVEL ) ); + } + else { + log.debug("mappedToscaTemplate is empty "); + return Either.right("mappedToscaTemplate is empty "); + } + } + + + /** * Delete input from service - * + * * @param componentType * @param inputId * @param component * @param user - * + * * @return */ public Either<InputDefinition, ResponseFormat> deleteInput(String componentType, String componentId, String userId, String inputId) { @@ -762,7 +839,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { componentParametersView.setIgnoreComponentInstancesInputs(false); componentParametersView.setIgnoreComponentInstancesProperties(false); componentParametersView.setIgnoreUsers(false); - + Either<org.openecomp.sdc.be.model.Component, StorageOperationStatus> componentEither = toscaOperationFacade.getToscaElement(componentId, componentParametersView); if (componentEither.isRight()) { deleteEither = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(componentEither.right().value()))); @@ -779,7 +856,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { if (!optionalInput.isPresent()) { return Either.right(componentsUtils.getResponseFormat(ActionStatus.INPUT_IS_NOT_CHILD_OF_COMPONENT, inputId, componentId)); } - + InputDefinition inputForDelete = optionalInput.get(); // Lock component @@ -798,11 +875,11 @@ public class InputsBusinessLogic extends BaseBusinessLogic { deleteEither = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(status), component.getName())); return deleteEither; } - + List<ComponentInstanceInput> inputsValue= getComponentInstanceInputsByInputId(component, inputId); Map<String, List<ComponentInstanceInput>> insInputsMatToDelete = new HashMap<>(); - - if(inputsValue != null && !inputsValue.isEmpty()){ + + if(inputsValue != null && !inputsValue.isEmpty()){ for(ComponentInstanceInput inputValue: inputsValue){ List<ComponentInstanceInput> inputList = null; String ciId = inputValue.getComponentInstanceId(); @@ -821,22 +898,29 @@ public class InputsBusinessLogic extends BaseBusinessLogic { return deleteEither; } } - + // US848813 delete service input that relates to VL / CP property - + List<ComponentInstanceProperty> propertiesValue = getComponentInstancePropertiesByInputId(component, inputId); if(propertiesValue != null && !propertiesValue.isEmpty()){ - //propertyList = propertyValueStatus.left().value(); + //propertyList = propertyValueStatus.left().value(); for(ComponentInstanceProperty propertyValue: propertiesValue){ - + String value = propertyValue.getValue(); Map<String, Object> mappedToscaTemplate = (Map<String, Object>) new Yaml().load(value); - + resetInputName(mappedToscaTemplate, inputForDelete.getName()); - + value = ""; - if(!mappedToscaTemplate.isEmpty()) - value = gson.toJson(mappedToscaTemplate); + if(!mappedToscaTemplate.isEmpty()){ + Either result = cleanNestedMap(mappedToscaTemplate , true); + Map modifiedMappedToscaTemplate = mappedToscaTemplate; + if (result.isLeft()) + modifiedMappedToscaTemplate = (Map)result.left().value(); + else + Log.warn("Map cleanup failed -> " +result.right().value().toString()); //continue, don't break operation + value = gson.toJson(modifiedMappedToscaTemplate); + } propertyValue.setValue(value); String compInstId = propertyValue.getComponentInstanceId(); propertyValue.setRules(null); @@ -857,7 +941,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { if (findDefaultValue.isRight()) { deleteEither = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(DaoStatusConverter.convertTitanStatusToStorageStatus(findDefaultValue.right().value())))); return deleteEither; - + } String defaultValue = findDefaultValue.left().value(); propertyValue.setDefaultValue(defaultValue); @@ -868,10 +952,10 @@ public class InputsBusinessLogic extends BaseBusinessLogic { deleteEither = Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(status), component.getName())); return deleteEither; } - + } } - + deleteEither = Either.left(inputForDelete); return deleteEither; @@ -888,7 +972,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } private Either<InputDefinition, ResponseFormat> prepareAndValidateInputBeforeCreate(InputDefinition newInputDefinition, Map<String, DataTypeDefinition> dataTypes) { - + // validate input default values Either<Boolean, ResponseFormat> defaultValuesValidation = validatePropertyDefaultValue(newInputDefinition, dataTypes); @@ -918,7 +1002,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } return Either.left(newInputDefinition); } - + public boolean isInputExist(List<InputDefinition> inputs, String resourceUid, String inputName) { if (inputs == null) { @@ -937,18 +1021,18 @@ public class InputsBusinessLogic extends BaseBusinessLogic { return false; } - - + + public Either<InputDefinition, ResponseFormat> getInputsAndPropertiesForComponentInput(String userId, String componentId, String inputId, boolean inTransaction) { Either<InputDefinition, ResponseFormat> result = null; try { - + Either<User, ResponseFormat> resp = validateUserExists(userId, "get Properties by input", false); if (resp.isRight()) { return Either.right(resp.right().value()); } Either<List<ComponentInstanceProperty>, StorageOperationStatus> propertiesEitherRes = null; - + ComponentParametersView filters = new ComponentParametersView(); filters.disableAll(); filters.setIgnoreComponentInstances(false); @@ -961,7 +1045,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(getComponentEither.right().value()); log.debug("Failed to found component {}, error: {}", componentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); - + } org.openecomp.sdc.be.model.Component component = getComponentEither.left().value(); Optional<InputDefinition> op = component.getInputs().stream().filter(in -> in.getUniqueId().equals(inputId)).findFirst(); @@ -970,18 +1054,18 @@ public class InputsBusinessLogic extends BaseBusinessLogic { log.debug("Failed to found input {} under component {}, error: {}", inputId, componentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); } - + InputDefinition resObj = op.get(); - + List<ComponentInstanceInput> inputCIInput = getComponentInstanceInputsByInputId(component, inputId) ; - + resObj.setInputs(inputCIInput); - - + + List<ComponentInstanceProperty> inputProps = getComponentInstancePropertiesByInputId(component, inputId) ; - - resObj.setProperties(inputProps); - + + resObj.setProperties(inputProps); + result = Either.left(resObj); @@ -1004,7 +1088,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } } - + private List<ComponentInstanceProperty> getComponentInstancePropertiesByInputId(org.openecomp.sdc.be.model.Component component, String inputId){ List<ComponentInstanceProperty> resList = new ArrayList<>(); Map<String, List<ComponentInstanceProperty>> ciPropertiesMap = component.getComponentInstancesProperties(); @@ -1029,7 +1113,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } } } - + } } } @@ -1038,7 +1122,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { return resList; } - + private List<ComponentInstanceInput> getComponentInstanceInputsByInputId(org.openecomp.sdc.be.model.Component component, String inputId){ List<ComponentInstanceInput> resList = new ArrayList<>(); Map<String, List<ComponentInstanceInput>> ciInputsMap = component.getComponentInstancesInputs(); @@ -1063,7 +1147,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } } } - + } } } @@ -1072,11 +1156,11 @@ public class InputsBusinessLogic extends BaseBusinessLogic { return resList; } - + private Either<org.openecomp.sdc.be.model.Component, StorageOperationStatus> getOriginComponent(ComponentInstance ci, Map<String, org.openecomp.sdc.be.model.Component> origComponentMap){ Either<org.openecomp.sdc.be.model.Component, StorageOperationStatus> result = null; String compInstname = ci.getNormalizedName(); - + ComponentParametersView componentParametersView = new ComponentParametersView(); componentParametersView.disableAll(); componentParametersView.setIgnoreInputs(false); @@ -1096,9 +1180,9 @@ public class InputsBusinessLogic extends BaseBusinessLogic { result = Either.left(origComponent); return result; } - - - + + + private Either<List<InputDefinition>, ResponseFormat> createInputsFromProperty(org.openecomp.sdc.be.model.Component component, Map<String, org.openecomp.sdc.be.model.Component> origComponentMap, Map<String, InputDefinition> inputsToCreate, Map<String, List<ComponentInstanceProperty>> propertiesToCreateMap, Map<String, DataTypeDefinition> dataTypes, List<InputDefinition> resList, Map<String, List<ComponentInstancePropInput>> newInputsPropsMap) { List<ComponentInstance> ciList = component.getComponentInstances(); String componentId = component.getUniqueId(); @@ -1106,13 +1190,13 @@ public class InputsBusinessLogic extends BaseBusinessLogic { List<ComponentInstanceProperty> propertiesToCreate = new ArrayList<>(); String compInstId = entry.getKey(); List<ComponentInstancePropInput> properties = entry.getValue(); - + Optional<ComponentInstance> op = ciList.stream().filter(ci -> ci.getUniqueId().equals(compInstId)).findAny(); if(!op.isPresent()){ ActionStatus actionStatus = ActionStatus.INVALID_CONTENT; log.debug("Failed to find component instance {} under component {}", compInstId, componentId); return Either.right(componentsUtils.getResponseFormat(actionStatus)); - + } ComponentInstance ci = op.get(); String compInstname = ci.getNormalizedName(); @@ -1121,33 +1205,34 @@ public class InputsBusinessLogic extends BaseBusinessLogic { ActionStatus actionStatus = componentsUtils.convertFromStorageResponse(origComponentEither.right().value()); log.debug("Failed to create inputs value under component {}, error: {}", componentId, actionStatus.name()); return Either.right(componentsUtils.getResponseFormat(actionStatus)); - + } org.openecomp.sdc.be.model.Component origComponent = origComponentEither.left().value(); - + //String originType = (String) titanGenericDao.getProperty(originVertex, GraphPropertiesDictionary.LABEL.getProperty()); - + String inputName = compInstname; - + if (properties != null && !properties.isEmpty()) { for (ComponentInstancePropInput propInput : properties) { propInput.setOwnerId(null); propInput.setParentUniqueId(null); + Either<InputDefinition, StorageOperationStatus> createInputRes = createInputForComponentInstance(component, origComponent,ci, inputsToCreate, propertiesToCreate, dataTypes, inputName, propInput); - + if (createInputRes.isRight()) { log.debug("Failed to create input of resource instance for id {} error {}", compInstId, createInputRes.right().value()); return Either.right(componentsUtils.getResponseFormat(componentsUtils.convertFromStorageResponse(createInputRes.right().value()))); - + } - + resList.add(createInputRes.left().value()); - + } propertiesToCreateMap.put(compInstId, propertiesToCreate); } - + } return Either.left(resList); } @@ -1156,7 +1241,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { String propertiesName = propInput.getPropertiesName() ; PropertyDefinition selectedProp = propInput.getInput(); String[] parsedPropNames = propInput.getParsedPropNames(); - + if(parsedPropNames != null){ for(String str: parsedPropNames){ inputName += "_" + str; @@ -1164,89 +1249,103 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } else { inputName += "_" + propInput.getName(); } - + InputDefinition input = null; - ComponentInstanceProperty prop = propInput; - + ComponentInstanceProperty prop = propInput; + + if(CollectionUtils.isNotEmpty(propertiesToCreate)){ + Optional<ComponentInstanceProperty> propOpt = propertiesToCreate.stream().filter(p -> p.getName().equals(propInput.getName())).findFirst(); + if(propOpt.isPresent()){ + prop = propOpt.get(); + } + } + boolean complexProperty = false; if(propertiesName != null && !propertiesName.isEmpty() && selectedProp != null){ + complexProperty = true; input = new InputDefinition(selectedProp); }else{ input = new InputDefinition(prop); input.setName(inputName + "_" + prop.getName()); - + } - input.setName(inputName); + input.setName(inputName); input.setUniqueId(UniqueIdBuilder.buildPropertyUniqueId(component.getUniqueId(), input.getName())); input.setInputPath(propertiesName); - + input.setInstanceUniqueId(ci.getUniqueId()); + input.setPropertyId(propInput.getUniqueId()); + JSONObject jobject = new JSONObject(); - - + + if(prop.getValue() == null || prop.getValue().isEmpty()){ - if(propertiesName != null && !propertiesName.isEmpty() && selectedProp != null){ - - jobject = createJSONValueForProperty(parsedPropNames.length -1, parsedPropNames, jobject, inputName); - prop.setValue(jobject.toJSONString()); - + if(complexProperty){ + + jobject = createJSONValueForProperty(parsedPropNames.length -1, parsedPropNames, jobject, inputName); + prop.setValue(jobject.toJSONString()); + }else{ - + jobject.put(GET_INPUT, input.getName()); - prop.setValue(jobject.toJSONString()); - + prop.setValue(jobject.toJSONString()); + } - + }else{ - - String value = prop.getValue(); + + String value = prop.getValue(); Object objValue = new Yaml().load(value); if( objValue instanceof Map || objValue instanceof List ){ - if(propertiesName == null ||propertiesName.isEmpty()){ + if(!complexProperty){ jobject.put(GET_INPUT, input.getName()); prop.setValue(jobject.toJSONString()); prop.setRules(null); - + }else{ Map<String, Object> mappedToscaTemplate = (Map<String, Object>) objValue; createInputValue(mappedToscaTemplate, 1, parsedPropNames, inputName); - - String json = gson.toJson(mappedToscaTemplate); + + String json = gson.toJson(mappedToscaTemplate); prop.setValue(json); prop.setRules(null); } - + }else{ jobject.put(GET_INPUT, input.getName()); prop.setValue(jobject.toJSONString()); prop.setRules(null); } - + } prop.setComponentInstanceId(ci.getUniqueId()); prop.setComponentInstanceName(ci.getName()); - - List<GetInputValueDataDefinition> getInputValues = new ArrayList<>(); + + if(CollectionUtils.isEmpty(prop.getGetInputValues())){ + prop.setGetInputValues(new ArrayList<>()); + } + List<GetInputValueDataDefinition> getInputValues = prop.getGetInputValues(); + GetInputValueDataDefinition getInputValueDataDefinition = new GetInputValueDataDefinition(); getInputValueDataDefinition.setInputId(input.getUniqueId()); getInputValueDataDefinition.setInputName(input.getName()); getInputValues.add(getInputValueDataDefinition); - prop.setGetInputValues(getInputValues); - - propertiesToCreate.add(prop); - + + if(!propertiesToCreate.contains(prop)){ + propertiesToCreate.add(prop); + } + inputsToCreate.put(input.getName(), input); - List<ComponentInstanceProperty> propertiesList = new ArrayList<>(); // adding the property with the new value for UI propertiesList.add(prop); input.setProperties(propertiesList); - + return Either.left(input); - + } - + private JSONObject createJSONValueForProperty (int i, String [] parsedPropNames, JSONObject ooj, String inputName){ - + while(i >= 1){ - if( i == parsedPropNames.length -1){ + if( i == parsedPropNames.length -1){ JSONObject jobProp = new JSONObject(); jobProp.put(GET_INPUT, inputName); ooj.put(parsedPropNames[i], jobProp); @@ -1260,17 +1359,17 @@ public class InputsBusinessLogic extends BaseBusinessLogic { return res; } } - + return ooj; } - + public void resetInputName(Map<String, Object> lhm1, String inputName){ for (Map.Entry<String, Object> entry : lhm1.entrySet()) { String key = entry.getKey(); Object value = entry.getValue(); if (value instanceof String && ((String) value).equalsIgnoreCase(inputName) && key.equals(GET_INPUT)) { value = ""; - lhm1.remove(key); + lhm1.remove(key); } else if (value instanceof Map) { Map<String, Object> subMap = (Map<String, Object>)value; resetInputName(subMap, inputName); @@ -1280,7 +1379,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { } } - + private Map<String, Object> createInputValue(Map<String, Object> lhm1, int index, String[] inputNames, String inputName){ while(index < inputNames.length){ if(lhm1.containsKey(inputNames[index])){ @@ -1289,7 +1388,7 @@ public class InputsBusinessLogic extends BaseBusinessLogic { if(index == inputNames.length -1){ ((Map) value).put(GET_INPUT, inputName); return ((Map) value); - + }else{ index++; return createInputValue((Map)value, index, inputNames, inputName); @@ -1299,14 +1398,14 @@ public class InputsBusinessLogic extends BaseBusinessLogic { if(index == inputNames.length -1){ jobProp.put(GET_INPUT, inputName); lhm1.put(inputNames[index], jobProp); - return lhm1; - }else{ + return lhm1; + }else{ lhm1.put(inputNames[index], jobProp); index++; return createInputValue(jobProp, index, inputNames, inputName); } } - }else{ + }else{ Map<String, Object> jobProp = new HashMap<>(); lhm1.put(inputNames[index], jobProp); if(index == inputNames.length -1){ diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogic.java b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogic.java index d3492f8f40..cc4a6d9c71 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogic.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/components/impl/ResourceBusinessLogic.java @@ -44,6 +44,7 @@ import java.util.stream.Collectors; import javax.servlet.ServletContext; import org.apache.commons.codec.binary.Base64; +import org.apache.commons.collections.CollectionUtils; import org.apache.commons.collections.MapUtils; import org.apache.commons.lang3.tuple.ImmutablePair; import org.openecomp.sdc.be.components.impl.ArtifactsBusinessLogic.ArtifactOperationEnum; @@ -2364,6 +2365,21 @@ public class ResourceBusinessLogic extends ComponentBusinessLogic { for (ArtifactDefinition artToDelete : listToDelete) { findArtifactToDelete(parsedGroup, artifactsToDelete, groupListEntry.getKey().getUniqueId(), artToDelete, createdDeplymentArtifacts); } + if(artifactsToDelete != null && !artifactsToDelete.isEmpty()){ + GroupDefinition group = groupListEntry.getKey(); + for(ArtifactDefinition artifactDefinition: artifactsToDelete){ + if (CollectionUtils.isNotEmpty(group.getArtifacts()) && group.getArtifacts().contains(artifactDefinition.getUniqueId())) { + group.getArtifacts().remove(artifactDefinition.getUniqueId()); + + } + if (CollectionUtils.isNotEmpty(group.getArtifactsUuid()) && group.getArtifactsUuid().contains(artifactDefinition.getArtifactUUID())) { + group.getArtifactsUuid().remove(artifactDefinition.getArtifactUUID()); + + } + } + + } + for (ArtifactTemplateInfo jsonMasterArtifact : jsonMasterArtifacts) { if (maserArtifact.getArtifactName().equalsIgnoreCase(jsonMasterArtifact.getFileName())) { MergedArtifactInfo mergedGroup = new MergedArtifactInfo(); diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/distribution/servlet/DistributionCatalogServlet.java b/catalog-be/src/main/java/org/openecomp/sdc/be/distribution/servlet/DistributionCatalogServlet.java index 948968e367..8c0041af9a 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/distribution/servlet/DistributionCatalogServlet.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/distribution/servlet/DistributionCatalogServlet.java @@ -31,6 +31,7 @@ import javax.servlet.ServletContext; import javax.servlet.http.HttpServletRequest; import javax.ws.rs.Consumes; import javax.ws.rs.GET; +import javax.ws.rs.HeaderParam; import javax.ws.rs.Path; import javax.ws.rs.PathParam; import javax.ws.rs.Produces; @@ -51,13 +52,14 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.jcabi.aspects.Loggable; + +import fj.data.Either; import io.swagger.annotations.Api; import io.swagger.annotations.ApiOperation; +import io.swagger.annotations.ApiParam; import io.swagger.annotations.ApiResponse; import io.swagger.annotations.ApiResponses; -import fj.data.Either; - /** * This Servlet serves external users to download artifacts. * @@ -76,18 +78,43 @@ public class DistributionCatalogServlet extends BeGenericServlet { // ******************************************************* // Download (GET) artifacts // **********************************************************/ - + /** + * + * @param request + * @param requestId + * @param instanceIdHeader + * @param accept + * @param authorization + * @param serviceName + * @param serviceVersion + * @param artifactName + * @return + */ @GET @Path("/services/{serviceName}/{serviceVersion}/artifacts/{artifactName}") @Consumes(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_OCTET_STREAM) - @ApiOperation(value = "Download service artifact", httpMethod = "GET", notes = "Returns downloaded artifact", response = Response.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact downloaded"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), - @ApiResponse(code = 404, message = "Artifact not found") }) - public Response downloadServiceArtifact(@PathParam("serviceName") final String serviceName, @PathParam("serviceVersion") final String serviceVersion, @PathParam("artifactName") final String artifactName, - @Context final HttpServletRequest request) { + @ApiOperation(value = "Download service artifact", httpMethod = "GET", notes = "Returns downloaded artifact", response = String.class) + @ApiResponses(value = { + @ApiResponse(code = 200, message = "The artifact is found and streamed.", response = String.class), + @ApiResponse(code = 400, message = "Missing “X-ECOMP-InstanceID” HTTP header - POL5001"), + @ApiResponse(code = 401, message = "ECOMP component should authenticate itself and to re-send again HTTP request with its Basic Authentication credentials - POL5002"), + @ApiResponse(code = 403, message = "ECOMP component is not authorized - POL5003"), + @ApiResponse(code = 404, message = "Specified Service is not found - SVC4503"), + @ApiResponse(code = 404, message = "Specified Service Version is not found - SVC4504"), + @ApiResponse(code = 404, message = "Specified artifact is not found - SVC4505"), + @ApiResponse(code = 405, message = "Method Not Allowed: Invalid HTTP method type used (PUT,DELETE,POST will be rejected) - POL4050"), + @ApiResponse(code = 500, message = "The GET request failed either due to internal SDC problem or Cambria Service failure. ECOMP Component should continue the attempts to get the needed information - POL5000")}) + public Response downloadServiceArtifact(@Context final HttpServletRequest request, + @ApiParam(value = "X-ECOMP-RequestID header", required = false)@HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, + @ApiParam(value = "X-ECOMP-InstanceID header", required = true)@HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader, + @ApiParam(value = "Determines the format of the body of the response", required = false)@HeaderParam(value = Constants.ACCEPT_HEADER) String accept, + @ApiParam(value = "The username and password", required = true)@HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, + @PathParam("serviceName") final String serviceName, + @PathParam("serviceVersion") final String serviceVersion, + @PathParam("artifactName") final String artifactName) { + Response response = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); AuditingActionEnum auditingActionEnum = AuditingActionEnum.DISTRIBUTION_ARTIFACT_DOWNLOAD; EnumMap<AuditingFieldsKeysEnum, Object> additionalParam = new EnumMap<AuditingFieldsKeysEnum, Object>(AuditingFieldsKeysEnum.class); @@ -128,18 +155,49 @@ public class DistributionCatalogServlet extends BeGenericServlet { return buildErrorResponse(getComponentsUtils().getResponseFormat(ActionStatus.GENERAL_ERROR)); } } - + + /** + * + * @param request + * @param requestId + * @param instanceIdHeader + * @param accept + * @param authorization + * @param serviceName + * @param serviceVersion + * @param resourceName + * @param resourceVersion + * @param artifactName + * @return + */ @GET @Path("/services/{serviceName}/{serviceVersion}/resources/{resourceName}/{resourceVersion}/artifacts/{artifactName}") @Consumes(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_OCTET_STREAM) - @ApiOperation(value = "Download resource artifact", httpMethod = "GET", notes = "Returns downloaded artifact", response = Response.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact downloaded"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), - @ApiResponse(code = 404, message = "Artifact not found") }) - public Response downloadResourceArtifact(@PathParam("serviceName") final String serviceName, @PathParam("serviceVersion") final String serviceVersion, @PathParam("resourceName") final String resourceName, - @PathParam("resourceVersion") final String resourceVersion, @PathParam("artifactName") final String artifactName, @Context final HttpServletRequest request) { + @ApiOperation(value = "Download resource artifact", httpMethod = "GET", notes = "Returns downloaded artifact", response = String.class) + @ApiResponses(value = { + @ApiResponse(code = 200, message = "The artifact is found and streamed.", response = String.class), + @ApiResponse(code = 400, message = "Missing “X-ECOMP-InstanceID” HTTP header - POL5001"), + @ApiResponse(code = 401, message = "ECOMP component should authenticate itself and to re-send again HTTP request with its Basic Authentication credentials - POL5002"), + @ApiResponse(code = 403, message = "ECOMP component is not authorized - POL5003"), + @ApiResponse(code = 404, message = "Specified Service is not found - SVC4503"), + @ApiResponse(code = 404, message = "Specified Resource Instance is not found - SVC4526"), + @ApiResponse(code = 404, message = "Specified Service Version is not found - SVC4504"), + @ApiResponse(code = 404, message = "Specified artifact is not found - SVC4505"), + @ApiResponse(code = 405, message = "Method Not Allowed: Invalid HTTP method type used (PUT,DELETE,POST will be rejected) - POL4050"), + @ApiResponse(code = 500, message = "The GET request failed either due to internal SDC problem or Cambria Service failure. ECOMP Component should continue the attempts to get the needed information - POL5000")}) + public Response downloadResourceArtifact(@Context final HttpServletRequest request, + @ApiParam(value = "X-ECOMP-RequestID header", required = false)@HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, + @ApiParam(value = "X-ECOMP-InstanceID header", required = true)@HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader, + @ApiParam(value = "Determines the format of the body of the response", required = false)@HeaderParam(value = Constants.ACCEPT_HEADER) String accept, + @ApiParam(value = "The username and password", required = true)@HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, + @PathParam("serviceName") final String serviceName, + @PathParam("serviceVersion") final String serviceVersion, + @PathParam("resourceName") final String resourceName, + @PathParam("resourceVersion") final String resourceVersion, + @PathParam("artifactName") final String artifactName) { + Response response = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); AuditingActionEnum auditingActionEnum = AuditingActionEnum.DISTRIBUTION_ARTIFACT_DOWNLOAD; EnumMap<AuditingFieldsKeysEnum, Object> additionalParam = new EnumMap<AuditingFieldsKeysEnum, Object>(AuditingFieldsKeysEnum.class); @@ -181,22 +239,49 @@ public class DistributionCatalogServlet extends BeGenericServlet { } } - // -------------------------------- - + /** + * + * @param request + * @param requestId + * @param instanceIdHeader + * @param accept + * @param authorization + * @param serviceName + * @param serviceVersion + * @param resourceInstanceName + * @param artifactName + * @return + */ @GET @Path("/services/{serviceName}/{serviceVersion}/resourceInstances/{resourceInstanceName}/artifacts/{artifactName}") @Consumes(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_OCTET_STREAM) - @ApiOperation(value = "Download resource artifact", httpMethod = "GET", notes = "Returns downloaded artifact", response = Response.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact downloaded"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), - @ApiResponse(code = 404, message = "Artifact not found") }) - public Response downloadResourceInstanceArtifact(@PathParam("serviceName") final String serviceName, @PathParam("serviceVersion") final String serviceVersion, @PathParam("resourceInstanceName") final String resourceInstanceName, - @PathParam("artifactName") final String artifactName, @Context final HttpServletRequest request) { + @ApiOperation(value = "Download resource instance artifact", httpMethod = "GET", notes = "Returns downloaded artifact", response = String.class) + @ApiResponses(value = { + @ApiResponse(code = 200, message = "The artifact is found and streamed.", response = String.class), + @ApiResponse(code = 400, message = "Missing “X-ECOMP-InstanceID” HTTP header - POL5001"), + @ApiResponse(code = 401, message = "ECOMP component should authenticate itself and to re-send again HTTP request with its Basic Authentication credentials - POL5002"), + @ApiResponse(code = 403, message = "ECOMP component is not authorized - POL5003"), + @ApiResponse(code = 404, message = "Specified Service is not found - SVC4503"), + @ApiResponse(code = 404, message = "Specified Resource Instance is not found - SVC4526"), + @ApiResponse(code = 404, message = "Specified Service Version is not found - SVC4504"), + @ApiResponse(code = 404, message = "Specified artifact is not found - SVC4505"), + @ApiResponse(code = 405, message = "Method Not Allowed: Invalid HTTP method type used (PUT,DELETE,POST will be rejected) - POL4050"), + @ApiResponse(code = 500, message = "The GET request failed either due to internal SDC problem or Cambria Service failure. ECOMP Component should continue the attempts to get the needed information - POL5000")}) + public Response downloadResourceInstanceArtifact(@Context final HttpServletRequest request, + @ApiParam(value = "X-ECOMP-RequestID header", required = false)@HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, + @ApiParam(value = "X-ECOMP-InstanceID header", required = true)@HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader, + @ApiParam(value = "Determines the format of the body of the response", required = false)@HeaderParam(value = Constants.ACCEPT_HEADER) String accept, + @ApiParam(value = "The username and password", required = true)@HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, + @PathParam("serviceName") final String serviceName, + @PathParam("serviceVersion") final String serviceVersion, + @PathParam("resourceInstanceName") final String resourceInstanceName, + @PathParam("artifactName") final String artifactName) { + Response response = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); AuditingActionEnum auditingActionEnum = AuditingActionEnum.DISTRIBUTION_ARTIFACT_DOWNLOAD; - EnumMap<AuditingFieldsKeysEnum, Object> additionalParam = new EnumMap<AuditingFieldsKeysEnum, Object>(AuditingFieldsKeysEnum.class); + EnumMap<AuditingFieldsKeysEnum, Object> additionalParam = new EnumMap<>(AuditingFieldsKeysEnum.class); additionalParam.put(AuditingFieldsKeysEnum.AUDIT_DISTRIBUTION_CONSUMER_ID, instanceIdHeader); additionalParam.put(AuditingFieldsKeysEnum.AUDIT_DISTRIBUTION_RESOURCE_URL, requestURI); @@ -234,6 +319,4 @@ public class DistributionCatalogServlet extends BeGenericServlet { return buildErrorResponse(getComponentsUtils().getResponseFormat(ActionStatus.GENERAL_ERROR)); } } - - // -------------------------------- } diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/distribution/servlet/DistributionServlet.java b/catalog-be/src/main/java/org/openecomp/sdc/be/distribution/servlet/DistributionServlet.java index 8a7aa73e6a..532cc1767b 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/distribution/servlet/DistributionServlet.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/distribution/servlet/DistributionServlet.java @@ -40,6 +40,8 @@ import org.openecomp.sdc.be.distribution.AuditHandler; import org.openecomp.sdc.be.distribution.DistributionBusinessLogic; import org.openecomp.sdc.be.distribution.api.client.RegistrationRequest; import org.openecomp.sdc.be.distribution.api.client.ServerListResponse; +import org.openecomp.sdc.be.distribution.api.client.TopicRegistrationResponse; +import org.openecomp.sdc.be.distribution.api.client.TopicUnregistrationResponse; import org.openecomp.sdc.be.impl.WebAppContextWrapper; import org.openecomp.sdc.be.model.operations.api.StorageOperationStatus; import org.openecomp.sdc.be.resources.data.auditing.AuditingActionEnum; @@ -55,12 +57,16 @@ import org.slf4j.LoggerFactory; import org.springframework.web.context.WebApplicationContext; import com.jcabi.aspects.Loggable; + +import fj.data.Either; import io.swagger.annotations.Api; +import io.swagger.annotations.ApiImplicitParam; +import io.swagger.annotations.ApiImplicitParams; import io.swagger.annotations.ApiOperation; +import io.swagger.annotations.ApiParam; import io.swagger.annotations.ApiResponse; import io.swagger.annotations.ApiResponses; - -import fj.data.Either; +import io.swagger.annotations.ResponseHeader; /** * This Servlet serves external users for distribution purposes. @@ -78,26 +84,51 @@ public class DistributionServlet extends BeGenericServlet { private static Logger log = LoggerFactory.getLogger(DistributionServlet.class.getName()); @Resource private DistributionBusinessLogic distributionLogic; - + + /** + * + * @param request + * @param requestId + * @param instanceId + * @param accept + * @param authorization + * @return + */ @GET @Path("/distributionUebCluster") @Consumes(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_JSON) - @ApiOperation(value = "UEB Server List", httpMethod = "GET", notes = "return the available UEB Server List", response = String.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "UEB server list fetched successfully"), @ApiResponse(code = 500, message = "One or more BE components (Titan, ES, BE) are down") }) - public Response getUebServerList(@Context final HttpServletRequest request, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) String instanceId, @HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, - @HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, @HeaderParam(value = Constants.ACCEPT_HEADER) String accept) { + @ApiOperation(value = "UEB Server List", httpMethod = "GET", notes = "return the available UEB Server List", + //TODO Tal G fix response headers + responseHeaders = { + @ResponseHeader(name = Constants.CONTENT_TYPE_HEADER, description = "Determines the format of the response body", response = String.class), + @ResponseHeader(name = "Content-Length", description = "Length of the response body", response = String.class)}) + @ApiResponses(value = { + @ApiResponse(code = 200, message = "ECOMP component is authenticated and list of Cambria API server’s FQDNs is returned", response = ServerListResponse.class), + @ApiResponse(code = 400, message = "Missing “X-ECOMP-InstanceID” HTTP header - POL5001"), + @ApiResponse(code = 401, message = "ECOMP component should authenticate itself and to re-send again HTTP request with its credentials for Basic Authentication - POL5002"), + @ApiResponse(code = 403, message = "ECOMP component is not authorized - POL5003"), + @ApiResponse(code = 405, message = "Method Not Allowed: Invalid HTTP method type used ( PUT,DELETE,POST will be rejected) - POL4050"), + @ApiResponse(code = 500, message = "The GET request failed either due to internal SDC problem or Cambria Service failure. ECOMP Component should continue the attempts to get the needed information - POL5000")}) + public Response getUebServerList(@Context final HttpServletRequest request, + @ApiParam(value = "X-ECOMP-RequestID header", required = false)@HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, + @ApiParam(value = "X-ECOMP-InstanceID header", required = true)@HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) String instanceId, + @ApiParam(value = "Determines the format of the body of the response", required = false)@HeaderParam(value = Constants.ACCEPT_HEADER) String accept, + @ApiParam(value = "The username and password", required = true)@HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization) { + init(request); String url = request.getMethod() + " " + request.getRequestURI(); log.debug("Start handle request of {}", url); Response response = null; ResponseFormat responseFormat = null; + if (instanceId == null) { responseFormat = getComponentsUtils().getResponseFormat(ActionStatus.MISSING_X_ECOMP_INSTANCE_ID); response = buildErrorResponse(responseFormat); getComponentsUtils().auditMissingInstanceId(AuditingActionEnum.GET_UEB_CLUSTER, responseFormat.getStatus().toString(), responseFormat.getFormattedMessage()); return response; } + try { Either<ServerListResponse, ResponseFormat> actionResponse = distributionLogic.getUebServerList(); @@ -123,49 +154,45 @@ public class DistributionServlet extends BeGenericServlet { } } - + /** - * Returns list of valid artifact types for validation done in the distribution client.<br> - * The list is the representation of the values of the enum ArtifactTypeEnum. * * @param request - * @param instanceId * @param requestId - * @param authorization + * @param instanceId * @param accept + * @param contenType + * @param contenLength + * @param authorization + * @param requestJson * @return */ - @GET - @Path("/artifactTypes") - @Consumes(MediaType.APPLICATION_JSON) - @Produces(MediaType.APPLICATION_JSON) - @ApiOperation(value = "Artifact types list", httpMethod = "GET", notes = "Fetches available artifact types list", response = String.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact types list fetched successfully"), @ApiResponse(code = 500, message = "One or more BE components (Titan, ES, BE) are down") }) - public Response getValidArtifactTypes(@Context final HttpServletRequest request, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) String instanceId, @HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, - @HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, @HeaderParam(value = Constants.ACCEPT_HEADER) String accept) { - init(request); - String url = request.getMethod() + " " + request.getRequestURI(); - log.debug("Start handle request of {}", url); - Response response = null; - - Wrapper<Response> responseWrapper = new Wrapper<>(); - - validateHeaders(responseWrapper, request, AuditingActionEnum.GET_VALID_ARTIFACT_TYPES); - if (responseWrapper.isEmpty()) { - response = buildOkResponse(getComponentsUtils().getResponseFormat(ActionStatus.OK), ArtifactTypeEnum.values()); - } else { - response = responseWrapper.getInnerElement(); - } - return response; - } - @POST @Path("/registerForDistribution") @Consumes(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_JSON) - @ApiOperation(value = "Subscription status", httpMethod = "POST", notes = "Subscribes for distribution notifications", response = String.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "Subscribed for distribution notifications successfull"), @ApiResponse(code = 500, message = "One or more BE components (Titan, ES, BE) are down") }) - public Response registerForDistribution(@Context final HttpServletRequest request, String requestJson) { + @ApiOperation(value = "Subscription status", httpMethod = "POST", notes = "Subscribes for distribution notifications") + @ApiResponses(value = { + @ApiResponse(code = 200, message = "ECOMP component is successfully registered for distribution", response = TopicRegistrationResponse.class), + @ApiResponse(code = 400, message = "Missing “X-ECOMP-InstanceID” HTTP header - POL5001"), + @ApiResponse(code = 400, message = "Missing Body - POL4500"), + @ApiResponse(code = 400, message = "Invalid Body : missing mandatory parameter “apiPublicKey” - POL4501"), + @ApiResponse(code = 400, message = "Invalid Body : missing mandatory parameter “distrEnvName” - POL4502"), + @ApiResponse(code = 400, message = "Invalid Body : Specified “distrEnvName” doesn’t exist - POL4137"), + @ApiResponse(code = 401, message = "ECOMP component should authenticate itself and to re-send again HTTP request with its Basic Authentication credentials - POL5002"), + @ApiResponse(code = 403, message = "ECOMP component is not authorized - POL5003"), + @ApiResponse(code = 405, message = "Method Not Allowed : Invalid HTTP method type used to register for distribution ( PUT,DELETE,GET will be rejected) - POL4050"), + @ApiResponse(code = 500, message = "The registration failed due to internal SDC problem or Cambria Service failure ECOMP Component should continue the attempts to register for distribution - POL5000")}) + //TODO Tal G fix response headers and to check missing header validations with Michael L + @ApiImplicitParams({@ApiImplicitParam(required = true, dataType = "org.openecomp.sdc.be.distribution.api.client.RegistrationRequest", paramType = "body", value = "json describe the artifact")}) + public Response registerForDistribution(@Context final HttpServletRequest request, + @ApiParam(value = "X-ECOMP-RequestID header", required = false)@HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, + @ApiParam(value = "X-ECOMP-InstanceID header", required = true)@HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) String instanceId, + @ApiParam(value = "Determines the format of the body of the response", required = false)@HeaderParam(value = Constants.ACCEPT_HEADER) String accept, + @ApiParam(value = "Determines the format of the body of the request", required = true)@HeaderParam(value = Constants.CONTENT_TYPE_HEADER) String contenType, + @ApiParam(value = "Length of the request body", required = true)@HeaderParam(value = Constants.CONTENT_LENGTH_HEADER) String contenLength, + @ApiParam(value = "The username and password", required = true)@HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, + String requestJson) { String url = request.getMethod() + " " + request.getRequestURI(); log.debug("Start handle request of {}", url); init(request); @@ -191,14 +218,86 @@ public class DistributionServlet extends BeGenericServlet { return responseWrapper.getInnerElement(); } + + /** + * Returns list of valid artifact types for validation done in the distribution client.<br> + * The list is the representation of the values of the enum ArtifactTypeEnum. + * + * @param request + * @param requestId + * @param instanceId + * @param authorization + * @param accept + * @return + */ + //TODO Get the missing AID for this API + @GET + @Path("/artifactTypes") + @Consumes(MediaType.APPLICATION_JSON) + @Produces(MediaType.APPLICATION_JSON) + @ApiOperation(value = "Artifact types list", httpMethod = "GET", notes = "Fetches available artifact types list", response = String.class) + @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact types list fetched successfully"), @ApiResponse(code = 500, message = "One or more BE components (Titan, ES, BE) are down") }) + public Response getValidArtifactTypes(@Context final HttpServletRequest request, + @HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, + @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) String instanceId, + @HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, + @HeaderParam(value = Constants.ACCEPT_HEADER) String accept) { + init(request); + String url = request.getMethod() + " " + request.getRequestURI(); + log.debug("Start handle request of {}", url); + Response response = null; + + Wrapper<Response> responseWrapper = new Wrapper<>(); + validateHeaders(responseWrapper, request, AuditingActionEnum.GET_VALID_ARTIFACT_TYPES); + if (responseWrapper.isEmpty()) { + response = buildOkResponse(getComponentsUtils().getResponseFormat(ActionStatus.OK), ArtifactTypeEnum.values()); + } else { + response = responseWrapper.getInnerElement(); + } + return response; + } + + /** + * Removes from subscription for distribution notifications + * + * @param request + * @param requestId + * @param instanceId + * @param accept + * @param contenType + * @param contenLength + * @param authorization + * @param requestJson + * @return + */ @POST @Path("/unRegisterForDistribution") @Consumes(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_JSON) - @ApiOperation(value = "Subscription status", httpMethod = "POST", notes = "Removes from subscription for distribution notifications", response = String.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "Successfully removed from subscription for distribution notifications"), @ApiResponse(code = 500, message = "One or more BE components (Titan, ES, BE) are down") }) - public Response unRegisterForDistribution(@Context final HttpServletRequest request, String requestJson) { + @ApiOperation(value = "Subscription status", httpMethod = "POST", notes = "Removes from subscription for distribution notifications") + //TODO Edit the responses + @ApiResponses(value = { + @ApiResponse(code = 204, message = "ECOMP component is successfully unregistered", response = TopicUnregistrationResponse.class), + @ApiResponse(code = 400, message = "Missing “X-ECOMP-InstanceID” HTTP header - POL5001"), + @ApiResponse(code = 400, message = "Missing Body - POL4500"), + @ApiResponse(code = 400, message = "Invalid Body : missing mandatory parameter “apiPublicKey” - POL4501"), + @ApiResponse(code = 400, message = "Invalid Body : missing mandatory parameter “distrEnvName” - SVC4506"), + @ApiResponse(code = 400, message = "Invalid Body : Specified “distrEnvName” doesn’t exist - POL4137"), + @ApiResponse(code = 401, message = "ECOMP component should authenticate itself and to re-send again HTTP request with its Basic Authentication credentials - POL5002"), + @ApiResponse(code = 403, message = "ECOMP component is not authorized - POL5003"), + @ApiResponse(code = 405, message = "Method Not Allowed : Invalid HTTP method type used to register for distribution ( PUT,DELETE,GET will be rejected) - POL4050"), + @ApiResponse(code = 500, message = "The registration failed due to internal SDC problem or Cambria Service failure ECOMP Component should continue the attempts to register for distribution - POL5000")}) + @ApiImplicitParams({@ApiImplicitParam(required = true, dataType = "org.openecomp.sdc.be.distribution.api.client.RegistrationRequest", paramType = "body", value = "json describe the artifact")}) + public Response unRegisterForDistribution(@Context final HttpServletRequest request, + @ApiParam(value = "X-ECOMP-RequestID header", required = false)@HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, + @ApiParam(value = "X-ECOMP-InstanceID header", required = true)@HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) String instanceId, + @ApiParam(value = "Determines the format of the body of the response", required = false)@HeaderParam(value = Constants.ACCEPT_HEADER) String accept, + @ApiParam(value = "Determines the format of the body of the request", required = true)@HeaderParam(value = Constants.CONTENT_TYPE_HEADER) String contenType, + @ApiParam(value = "Length of the request body", required = true)@HeaderParam(value = Constants.CONTENT_LENGTH_HEADER) String contenLength, + @ApiParam(value = "The username and password", required = true)@HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, + String requestJson) { + String url = request.getMethod() + " " + request.getRequestURI(); log.debug("Start handle request of {}", url); init(request); diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/externalapi/servlet/ArtifactExternalServlet.java b/catalog-be/src/main/java/org/openecomp/sdc/be/externalapi/servlet/ArtifactExternalServlet.java index bcd2fe8138..fea300a8bb 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/externalapi/servlet/ArtifactExternalServlet.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/externalapi/servlet/ArtifactExternalServlet.java @@ -31,6 +31,7 @@ import javax.servlet.ServletContext; import javax.servlet.http.HttpServletRequest; import javax.ws.rs.DELETE; import javax.ws.rs.GET; +import javax.ws.rs.HeaderParam; import javax.ws.rs.POST; import javax.ws.rs.Path; import javax.ws.rs.PathParam; @@ -96,13 +97,12 @@ public class ArtifactExternalServlet extends AbstractValidationsServlet { @ApiOperation(value = "uploads of artifact to a resource or service", httpMethod = "POST", notes = "uploads of artifact to a resource or service", response = Response.class) @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact uploaded"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 404, message = "Asset not found") }) - public Response uploadArtifact(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @ApiParam(value = "json describe the artifact", required = true) String data) { + public Response uploadArtifact(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @ApiParam(value = "json describe the artifact", required = true) String data, + @HeaderParam(value = Constants.USER_ID_HEADER) final String userId, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { init(log); Wrapper<ResponseFormat> responseWrapper = new Wrapper<>(); - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); - String userId = request.getHeader(Constants.USER_ID_HEADER); String url = request.getMethod() + " " + requestURI; log.debug("{} {}", startLog, url); ComponentTypeEnum componentType = ComponentTypeEnum.findByParamName(assetType); @@ -166,13 +166,12 @@ public class ArtifactExternalServlet extends AbstractValidationsServlet { @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact uploaded"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 404, message = "Asset not found") }) public Response uploadArtifactToInstance(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @PathParam("resourceInstanceName") final String resourceInstanceName, - @ApiParam(value = "json describe the artifact", required = true) String data) { + @ApiParam(value = "json describe the artifact", required = true) String data, + @HeaderParam(value = Constants.USER_ID_HEADER) final String userId, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { Wrapper<Response> responseWrapper = new Wrapper<>(); ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); - String userId = request.getHeader(Constants.USER_ID_HEADER); String url = request.getMethod() + " " + requestURI; log.debug("{} {}", startLog, url); ComponentTypeEnum componentType = ComponentTypeEnum.findByParamName(assetType); @@ -238,13 +237,12 @@ public class ArtifactExternalServlet extends AbstractValidationsServlet { @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact Updated"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 404, message = "Asset not found") }) public Response updateArtifact(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @PathParam("artifactUUID") final String artifactUUID, - @ApiParam(value = "json describe the artifact", required = true) String data) { + @ApiParam(value = "json describe the artifact", required = true) String data, + @HeaderParam(value = Constants.USER_ID_HEADER) final String userId, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { Wrapper<Response> responseWrapper = new Wrapper<>(); ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); - String userId = request.getHeader(Constants.USER_ID_HEADER); String url = request.getMethod() + " " + requestURI; log.debug("{} {}", startLog, url); ComponentTypeEnum componentType = ComponentTypeEnum.findByParamName(assetType); @@ -311,13 +309,12 @@ public class ArtifactExternalServlet extends AbstractValidationsServlet { @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact Updated"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 404, message = "Asset not found") }) public Response updateArtifactOnResourceInstance(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @PathParam("resourceInstanceName") final String resourceInstanceName, - @PathParam("artifactUUID") final String artifactUUID, @ApiParam(value = "json describe the artifact", required = true) String data) { + @PathParam("artifactUUID") final String artifactUUID, @ApiParam(value = "json describe the artifact", required = true) String data, + @HeaderParam(value = Constants.USER_ID_HEADER) final String userId, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { Wrapper<Response> responseWrapper = new Wrapper<>(); ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); - String userId = request.getHeader(Constants.USER_ID_HEADER); String url = request.getMethod() + " " + requestURI; log.debug("{} {}", startLog, url); ComponentTypeEnum componentType = ComponentTypeEnum.findByParamName(assetType); @@ -383,12 +380,11 @@ public class ArtifactExternalServlet extends AbstractValidationsServlet { @ApiOperation(value = "deletes an artifact of a resource or service", httpMethod = "DELETE", notes = "deletes an artifact of a resource or service", response = Response.class) @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact Deleted"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 404, message = "Asset not found") }) - public Response deleteArtifact(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @PathParam("artifactUUID") final String artifactUUID) { + public Response deleteArtifact(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @PathParam("artifactUUID") final String artifactUUID, + @HeaderParam(value = Constants.USER_ID_HEADER) final String userId, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { Wrapper<Response> responseWrapper = new Wrapper<>(); ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); - String userId = request.getHeader(Constants.USER_ID_HEADER); String requestURI = request.getRequestURI(); String url = request.getMethod() + " " + requestURI; log.debug("{} {}", startLog, url); @@ -455,12 +451,11 @@ public class ArtifactExternalServlet extends AbstractValidationsServlet { @ApiResponses(value = { @ApiResponse(code = 200, message = "Artifact Deleted"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 404, message = "Asset not found") }) public Response deleteArtifactOnResourceInstance(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @PathParam("resourceInstanceName") final String resourceInstanceName, - @PathParam("artifactUUID") final String artifactUUID) { + @PathParam("artifactUUID") final String artifactUUID, + @HeaderParam(value = Constants.USER_ID_HEADER) final String userId, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { Wrapper<Response> responseWrapper = new Wrapper<>(); ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); - String userId = request.getHeader(Constants.USER_ID_HEADER); String requestURI = request.getRequestURI(); String url = request.getMethod() + " " + requestURI; log.debug("{} {}", startLog, url); @@ -529,11 +524,11 @@ public class ArtifactExternalServlet extends AbstractValidationsServlet { @ApiResponse(code = 404, message = "Artifact not found") }) public Response downloadComponentArtifact( @ApiParam(value = "valid values: resources / services", allowableValues = ComponentTypeEnum.RESOURCE_PARAM_NAME + "," + ComponentTypeEnum.SERVICE_PARAM_NAME) @PathParam("assetType") final String assetType, - @PathParam("uuid") final String uuid, @PathParam("artifactUUID") final String artifactUUID) { + @PathParam("uuid") final String uuid, @PathParam("artifactUUID") final String artifactUUID, + @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { Wrapper<Response> responseWrapper = new Wrapper<>(); ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); String url = request.getMethod() + " " + requestURI; log.debug("{} {}", startLog, url); @@ -596,11 +591,11 @@ public class ArtifactExternalServlet extends AbstractValidationsServlet { @ApiResponse(code = 404, message = "Artifact not found") }) public Response downloadResourceInstanceArtifact( @ApiParam(value = "valid values: resources / services", allowableValues = ComponentTypeEnum.RESOURCE_PARAM_NAME + "," + ComponentTypeEnum.SERVICE_PARAM_NAME) @PathParam("assetType") final String assetType, - @PathParam("uuid") final String uuid, @PathParam("resourceInstanceName") final String resourceInstanceName, @PathParam("artifactUUID") final String artifactUUID) { + @PathParam("uuid") final String uuid, @PathParam("resourceInstanceName") final String resourceInstanceName, @PathParam("artifactUUID") final String artifactUUID, + @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { Wrapper<Response> responseWrapper = new Wrapper<>(); ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String requestURI = request.getRequestURI(); String url = request.getMethod() + " " + requestURI; log.debug("{} {}", startLog, url); diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/externalapi/servlet/AssetsDataServlet.java b/catalog-be/src/main/java/org/openecomp/sdc/be/externalapi/servlet/AssetsDataServlet.java index 27c3b409e2..2c1ef925c8 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/externalapi/servlet/AssetsDataServlet.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/externalapi/servlet/AssetsDataServlet.java @@ -68,6 +68,7 @@ import org.openecomp.sdc.be.datatypes.enums.AssetTypeEnum; import org.openecomp.sdc.be.datatypes.enums.ComponentTypeEnum; import org.openecomp.sdc.be.datatypes.enums.FilterKeyEnum; import org.openecomp.sdc.be.datatypes.enums.ResourceTypeEnum; +import org.openecomp.sdc.be.distribution.api.client.TopicRegistrationResponse; import org.openecomp.sdc.be.ecomp.converters.AssetMetadataConverter; import org.openecomp.sdc.be.externalapi.servlet.representation.AssetMetadata; import org.openecomp.sdc.be.model.Component; @@ -117,19 +118,41 @@ public class AssetsDataServlet extends AbstractValidationsServlet { private HttpServletRequest request; private static Logger log = LoggerFactory.getLogger(AssetsDataServlet.class.getName()); - + + /** + * + * @param assetType + * @param category + * @param subCategory + * @param distributionStatus + * @param resourceType + * @param instanceIdHeader + * @return + */ @GET @Path("/{assetType}") @Produces(MediaType.APPLICATION_JSON) - @ApiOperation(value = "Fetch list of assets", httpMethod = "GET", notes = "Returns list of assets", response = Response.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "Assets Fetched"), @ApiResponse(code = 400, message = "Invalid content / Missing content"), @ApiResponse(code = 401, message = "Authorization required"), - @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 404, message = "Asset not found") }) - public Response getAssetList(@PathParam("assetType") final String assetType, @QueryParam("category") String category, @QueryParam("subCategory") String subCategory, @QueryParam("distributionStatus") String distributionStatus, - @QueryParam("resourceType") String resourceType) { + @ApiOperation(value = "Fetch list of assets", httpMethod = "GET", notes = "Returns list of assets", response = AssetMetadata.class, responseContainer="List") + @ApiResponses(value = { + @ApiResponse(code = 200, message = "ECOMP component is authenticated and list of Catalog Assets Metadata is returned", response = AssetMetadata.class, responseContainer="List"), + @ApiResponse(code = 400, message = "Missing “X-ECOMP-InstanceID” HTTP header - POL5001"), + @ApiResponse(code = 401, message = "ECOMP component should authenticate itself and to re-send again HTTP request with its Basic Authentication credentials - POL5002"), + @ApiResponse(code = 403, message = "ECOMP component is not authorized - POL5003"), + @ApiResponse(code = 405, message = "Method Not Allowed : Invalid HTTP method type used to register for distribution (PUT,DELETE,POST will be rejected) - POL4050"), + @ApiResponse(code = 500, message = "The GET request failed either due to internal SDC problem. ECOMP Component should continue the attempts to get the needed information - POL5000")}) + public Response getAssetList( + @ApiParam(value = "X-ECOMP-RequestID header", required = false)@HeaderParam(value = Constants.X_ECOMP_REQUEST_ID_HEADER) String requestId, + @ApiParam(value = "X-ECOMP-InstanceID header", required = true)@HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader, + @ApiParam(value = "Determines the format of the body of the response", required = false)@HeaderParam(value = Constants.ACCEPT_HEADER) String accept, + @ApiParam(value = "The username and password", required = true)@HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, + @ApiParam(value = "The requested asset type", required = true, allowableValues = "resources, services")@PathParam("assetType") final String assetType, + @ApiParam(value = "The filter key (resourceType only for resources)", required = false)@QueryParam("category") String category, + @ApiParam(value = "The filter key (resourceType only for resources)", required = false)@QueryParam("subCategory") String subCategory, + @ApiParam(value = "The filter key (resourceType only for resources)", required = false)@QueryParam("distributionStatus") String distributionStatus, + @ApiParam(value = "The filter key (resourceType only for resources)", required = false)@QueryParam("resourceType") String resourceType) { Response response = null; ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); String query = request.getQueryString(); String requestURI = request.getRequestURI(); String url = request.getMethod() + " " + requestURI; @@ -205,18 +228,26 @@ public class AssetsDataServlet extends AbstractValidationsServlet { return buildErrorResponse(getComponentsUtils().getResponseFormat(ActionStatus.GENERAL_ERROR)); } } - + + /** + * + * @param assetType + * @param uuid + * @param request + * @param instanceIdHeader + * @return + */ @GET @Path("/{assetType}/{uuid}/metadata") @Produces(MediaType.APPLICATION_JSON) @ApiOperation(value = "Fetch metadata of asset by uuid", httpMethod = "GET", notes = "Returns metadata of asset", response = Response.class) @ApiResponses(value = { @ApiResponse(code = 200, message = "Assets Fetched"), @ApiResponse(code = 401, message = "Authorization required"), @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 404, message = "Asset not found") }) - public Response getAssetListByUuid(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @Context final HttpServletRequest request) { + public Response getAssetListByUuid(@PathParam("assetType") final String assetType, @PathParam("uuid") final String uuid, @Context final HttpServletRequest request, + @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { Response response = null; ResponseFormat responseFormat = null; - String instanceIdHeader = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); AuditingActionEnum auditingActionEnum = AuditingActionEnum.GET_ASSET_METADATA; String requestURI = request.getRequestURI(); String url = request.getMethod() + " " + requestURI; @@ -273,7 +304,15 @@ public class AssetsDataServlet extends AbstractValidationsServlet { return buildErrorResponse(getComponentsUtils().getResponseFormat(ActionStatus.GENERAL_ERROR)); } } - + + /** + * + * @param uuid + * @param assetType + * @param authorization + * @param instanceIdHeader + * @return + */ @GET @Path("/{assetType}/{uuid}/toscaModel") @Produces(MediaType.APPLICATION_OCTET_STREAM) @@ -282,7 +321,7 @@ public class AssetsDataServlet extends AbstractValidationsServlet { @ApiResponse(code = 404, message = "Asset not found") }) public Response getToscaModel(@PathParam("uuid") final String uuid, @ApiParam(value = "valid values: resources / services", allowableValues = ComponentTypeEnum.RESOURCE_PARAM_NAME + "," + ComponentTypeEnum.SERVICE_PARAM_NAME) @PathParam("assetType") final String assetType, - @HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization) { + @HeaderParam(value = Constants.AUTHORIZATION_HEADER) String authorization, @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { String url = request.getRequestURI(); log.debug("Start handle request of {} {}", request.getMethod(), url); @@ -291,14 +330,13 @@ public class AssetsDataServlet extends AbstractValidationsServlet { ServletContext context = request.getSession().getServletContext(); ComponentTypeEnum componentType = ComponentTypeEnum.findByParamName(assetType); AuditingActionEnum auditingActionEnum = AuditingActionEnum.GET_TOSCA_MODEL; - String userId = request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER); EnumMap<AuditingFieldsKeysEnum, Object> additionalParam = new EnumMap<AuditingFieldsKeysEnum, Object>(AuditingFieldsKeysEnum.class); - additionalParam.put(AuditingFieldsKeysEnum.AUDIT_DISTRIBUTION_CONSUMER_ID, userId); + additionalParam.put(AuditingFieldsKeysEnum.AUDIT_DISTRIBUTION_CONSUMER_ID, instanceIdHeader); additionalParam.put(AuditingFieldsKeysEnum.AUDIT_DISTRIBUTION_RESOURCE_URL, url); additionalParam.put(AuditingFieldsKeysEnum.AUDIT_RESOURCE_TYPE, componentType.getValue()); additionalParam.put(AuditingFieldsKeysEnum.AUDIT_SERVICE_INSTANCE_ID, uuid); - if (userId == null || userId.isEmpty()) { + if (instanceIdHeader == null || instanceIdHeader.isEmpty()) { log.debug("getToscaModel: Missing X-ECOMP-InstanceID header"); responseFormat = getComponentsUtils().getResponseFormat(ActionStatus.MISSING_X_ECOMP_INSTANCE_ID); getComponentsUtils().auditExternalGetAsset(responseFormat, auditingActionEnum, additionalParam); @@ -341,6 +379,8 @@ public class AssetsDataServlet extends AbstractValidationsServlet { * * @param assetType * @param data + * @param userId + * @param instanceIdHeader * @return */ @POST @@ -353,12 +393,15 @@ public class AssetsDataServlet extends AbstractValidationsServlet { @ApiResponse(code = 403, message = "Restricted operation"), @ApiResponse(code = 201, message = "Resource created"), @ApiResponse(code = 400, message = "Invalid content / Missing content"), @ApiResponse(code = 409, message = "Resource already exist") }) - public Response createResource(@PathParam("assetType") final String assetType, @ApiParam(value = "json describe the artifact", required = true) String data) { + public Response createResource(@PathParam("assetType") final String assetType, + @ApiParam(value = "json describe the artifact", required = true) String data, + @HeaderParam(value = Constants.USER_ID_HEADER) final String userId, + @HeaderParam(value = Constants.X_ECOMP_INSTANCE_ID_HEADER) final String instanceIdHeader) { + init(log); Wrapper<ResponseFormat> responseWrapper = new Wrapper<>(); String requestURI = request.getRequestURI(); - String userId = request.getHeader(Constants.USER_ID_HEADER); String url = request.getMethod() + " " + requestURI; log.debug("Start handle request of {}", url); Resource resource = null; @@ -369,8 +412,7 @@ public class AssetsDataServlet extends AbstractValidationsServlet { try { // Validate X-ECOMP-InstanceID Header if (responseWrapper.isEmpty()) { - validateXECOMPInstanceIDHeader(request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER), - responseWrapper); + validateXECOMPInstanceIDHeader(instanceIdHeader, responseWrapper); } // Validate USER_ID Header if (responseWrapper.isEmpty()) { @@ -457,7 +499,123 @@ public class AssetsDataServlet extends AbstractValidationsServlet { additionalParams); } } - + + /** + * Changing the lifecycle of an asset + * @param jsonChangeInfo The description - request body + * @param assetType The requested asset type.Valid values are: resources / services (for VFCMT – use "resources") + * @param uuid The uuid of the desired resource to be changed + * @param lifecycleTransition The lifecycle operation to be performed on the asset.Valid values are:Checkin / Checkout / CERTIFICATION_REQUEST + * @param userId + * @return + */ + @POST + @Path("/{assetType}/{uuid}/lifecycleState/{lifecycleOperation}") + @Consumes(MediaType.APPLICATION_JSON) + @Produces(MediaType.APPLICATION_JSON) + @ApiOperation(value = "Change Resource lifecycle State", httpMethod = "POST", response = Response.class) + @ApiResponses(value = { @ApiResponse(code = 200, message = "Resource state changed"), @ApiResponse(code = 403, message = "Asset is already checked-out by another user")}) + public Response changeResourceState(@ApiParam(value = "LifecycleChangeInfo - relevant for checkin", required = false) String jsonChangeInfo, + @ApiParam(value = "validValues: resources / services ", allowableValues = ComponentTypeEnum.RESOURCE_PARAM_NAME + "," + ComponentTypeEnum.SERVICE_PARAM_NAME) @PathParam(value = "assetType") final String assetType, + @ApiParam(value = "id of component to be changed") @PathParam(value = "uuid") final String uuid, + @ApiParam(allowableValues = "checkout, checkin", required = true) @PathParam(value = "lifecycleOperation") final String lifecycleTransition, + @HeaderParam(value = Constants.USER_ID_HEADER) final String userId) { + + Response response = null; + EnumMap<AuditingFieldsKeysEnum, Object> additionalParams = new EnumMap<>(AuditingFieldsKeysEnum.class); + + init(log); + + String requestURI = request.getRequestURI(); + String url = request.getMethod() + " " + requestURI; + log.debug("Start handle request of {}", url); + + //get the business logic + ServletContext context = request.getSession().getServletContext(); + LifecycleBusinessLogic businessLogic = getLifecycleBL(context); + + Wrapper<ResponseFormat> responseWrapper = runValidations(assetType); + ComponentTypeEnum componentType = ComponentTypeEnum.findByParamName(assetType); + Component component = null; + Component responseObject = null; + User modifier = null; + + try{ + if (responseWrapper.isEmpty()) { + //get user + Either<User, ResponseFormat> eitherGetUser = getUser(request, userId); + if (eitherGetUser.isRight()) { + ResponseFormat responseFormat = eitherGetUser.right().value(); + responseWrapper.setInnerElement(responseFormat); + return buildErrorResponse(responseFormat); + } + modifier = eitherGetUser.left().value(); + + //get the component id from the uuid + Either<Component, ResponseFormat> latestVersion = businessLogic.getLatestComponentByUuid(componentType, uuid); + if (latestVersion.isRight()) { + ResponseFormat responseFormat = latestVersion.right().value(); + responseWrapper.setInnerElement(responseFormat); + return buildErrorResponse(responseFormat); + } + component = latestVersion.left().value(); + String componentId = component.getUniqueId(); + + //validate the transition is valid + Either<LifeCycleTransitionEnum, ResponseFormat> validateEnum = validateTransitionEnum(lifecycleTransition, modifier); + if (validateEnum.isRight()) { + ResponseFormat responseFormat = validateEnum.right().value(); + responseWrapper.setInnerElement(responseFormat); + return buildErrorResponse(responseFormat); + } + LifeCycleTransitionEnum transitionEnum = validateEnum.left().value(); + + //create changeInfo + LifecycleChangeInfoWithAction changeInfo = new LifecycleChangeInfoWithAction(); + try { + if (jsonChangeInfo != null && !jsonChangeInfo.isEmpty()) { + ObjectMapper mapper = new ObjectMapper(); + changeInfo = new LifecycleChangeInfoWithAction(mapper.readValue(jsonChangeInfo, LifecycleChangeInfoBase.class).getUserRemarks()); + } + } + catch (Exception e) { + BeEcompErrorManager.getInstance().processEcompError(EcompErrorName.BeInvalidJsonInput, "convertJsonToObject"); + BeEcompErrorManager.getInstance().logBeInvalidJsonInput("convertJsonToObject"); + log.debug("failed to convert from json {}", jsonChangeInfo, e); + ResponseFormat responseFormat = getComponentsUtils().getInvalidContentErrorAndAudit(modifier, AuditingActionEnum.CHECKOUT_RESOURCE); + responseWrapper.setInnerElement(responseFormat); + return buildErrorResponse(responseFormat); + } + + //execute business logic + Either<? extends Component, ResponseFormat> actionResponse = businessLogic.changeComponentState(componentType, componentId, modifier, transitionEnum, changeInfo, false, true); + if (actionResponse.isRight()) { + log.info("failed to change resource state"); + ResponseFormat responseFormat = actionResponse.right().value(); + responseWrapper.setInnerElement(responseFormat); + return buildErrorResponse(responseFormat); + } + + log.debug("change state successful !!!"); + responseObject = actionResponse.left().value(); + response = buildCreatedResourceResponse(responseObject, context, responseWrapper); + } else { + response = buildErrorResponse(responseWrapper.getInnerElement()); + } + + return response; + } catch (Exception e) { + BeEcompErrorManager.getInstance().processEcompError(EcompErrorName.BeRestApiGeneralError, "Change Lifecycle State"); + BeEcompErrorManager.getInstance().logBeRestApiGeneralError("Change Lifecycle State"); + log.debug("change lifecycle state failed with exception", e); + ResponseFormat responseFormat = getComponentsUtils().getResponseFormat(ActionStatus.GENERAL_ERROR); + responseWrapper.setInnerElement(responseFormat); + return buildErrorResponse(responseFormat); + } finally{ + auditChnageLifecycleAction(additionalParams, responseWrapper, componentType, component, responseObject, modifier, userId); + } + } + private void prepareAdditionalAudit(Resource resource, EnumMap<AuditingFieldsKeysEnum, Object> additionalParams) { additionalParams.put(AuditingFieldsKeysEnum.AUDIT_RESOURCE_PREV_VERSION, StringUtils.EMPTY); additionalParams.put(AuditingFieldsKeysEnum.AUDIT_RESOURCE_PREV_STATE, StringUtils.EMPTY); @@ -489,14 +647,12 @@ public class AssetsDataServlet extends AbstractValidationsServlet { responseFormat = resMetadata.right().value(); responseWrapper.setInnerElement(responseFormat); response = buildErrorResponse(responseFormat); - } - else{ + }else{ final AssetMetadata assetData = resMetadata.left().value(); assetData.setToscaModelURL(null); responseWrapper.setInnerElement(getComponentsUtils().getResponseFormat(ActionStatus.CREATED)); Object representation = RepresentationUtils.toRepresentation(assetData); - responseFormat = getComponentsUtils().getResponseFormat(ActionStatus.OK); response = buildOkResponse(getComponentsUtils().getResponseFormat(ActionStatus.CREATED), representation); } return response; @@ -575,119 +731,7 @@ public class AssetsDataServlet extends AbstractValidationsServlet { } - /** - * Changing the lifecycle of an asset - * @param jsonChangeInfo The description - request body - * @param assetType The requested asset type.Valid values are: resources / services (for VFCMT – use "resources") - * @param uuid The uuid of the desired resource to be changed - * @param lifecycleTransition The lifecycle operation to be performed on the asset.Valid values are:Checkin / Checkout / CERTIFICATION_REQUEST - * @return - */ - @POST - @Path("/{assetType}/{uuid}/lifecycleState/{lifecycleOperation}") - @Consumes(MediaType.APPLICATION_JSON) - @Produces(MediaType.APPLICATION_JSON) - @ApiOperation(value = "Change Resource lifecycle State", httpMethod = "POST", response = Response.class) - @ApiResponses(value = { @ApiResponse(code = 200, message = "Resource state changed"), @ApiResponse(code = 403, message = "Asset is already checked-out by another user")}) - public Response changeResourceState(@ApiParam(value = "LifecycleChangeInfo - relevant for checkin", required = false) String jsonChangeInfo, - @ApiParam(value = "validValues: resources / services ", allowableValues = ComponentTypeEnum.RESOURCE_PARAM_NAME + "," + ComponentTypeEnum.SERVICE_PARAM_NAME) @PathParam(value = "assetType") final String assetType, - @ApiParam(value = "id of component to be changed") @PathParam(value = "uuid") final String uuid, - @ApiParam(allowableValues = "checkout, checkin", required = true) @PathParam(value = "lifecycleOperation") final String lifecycleTransition) { - Response response = null; - EnumMap<AuditingFieldsKeysEnum, Object> additionalParams = new EnumMap<>(AuditingFieldsKeysEnum.class); - - init(log); - - String requestURI = request.getRequestURI(); - String url = request.getMethod() + " " + requestURI; - log.debug("Start handle request of {}", url); - - //get the business logic - ServletContext context = request.getSession().getServletContext(); - LifecycleBusinessLogic businessLogic = getLifecycleBL(context); - - Wrapper<ResponseFormat> responseWrapper = runValidations(assetType); - ComponentTypeEnum componentType = ComponentTypeEnum.findByParamName(assetType); - Component component = null; - Component responseObject = null; - User modifier = null; - String userId = request.getHeader(Constants.USER_ID_HEADER); - - try{ - if (responseWrapper.isEmpty()) { - //get user - Either<User, ResponseFormat> eitherGetUser = getUser(request, userId); - if (eitherGetUser.isRight()) { - ResponseFormat responseFormat = eitherGetUser.right().value(); - responseWrapper.setInnerElement(responseFormat); - return buildErrorResponse(responseFormat); - } - modifier = eitherGetUser.left().value(); - - //get the component id from the uuid - Either<Component, ResponseFormat> latestVersion = businessLogic.getLatestComponentByUuid(componentType, uuid); - if (latestVersion.isRight()) { - ResponseFormat responseFormat = latestVersion.right().value(); - responseWrapper.setInnerElement(responseFormat); - return buildErrorResponse(responseFormat); - } - component = latestVersion.left().value(); - String componentId = component.getUniqueId(); - - //validate the transition is valid - Either<LifeCycleTransitionEnum, ResponseFormat> validateEnum = validateTransitionEnum(lifecycleTransition, modifier); - if (validateEnum.isRight()) { - ResponseFormat responseFormat = validateEnum.right().value(); - responseWrapper.setInnerElement(responseFormat); - return buildErrorResponse(responseFormat); - } - LifeCycleTransitionEnum transitionEnum = validateEnum.left().value(); - - //create changeInfo - LifecycleChangeInfoWithAction changeInfo = new LifecycleChangeInfoWithAction(); - try { - if (jsonChangeInfo != null && !jsonChangeInfo.isEmpty()) { - ObjectMapper mapper = new ObjectMapper(); - changeInfo = new LifecycleChangeInfoWithAction(mapper.readValue(jsonChangeInfo, LifecycleChangeInfoBase.class).getUserRemarks()); - } - } - catch (Exception e) { - BeEcompErrorManager.getInstance().processEcompError(EcompErrorName.BeInvalidJsonInput, "convertJsonToObject"); - BeEcompErrorManager.getInstance().logBeInvalidJsonInput("convertJsonToObject"); - log.debug("failed to convert from json {}", jsonChangeInfo, e); - ResponseFormat responseFormat = getComponentsUtils().getInvalidContentErrorAndAudit(modifier, AuditingActionEnum.CHECKOUT_RESOURCE); - responseWrapper.setInnerElement(responseFormat); - return buildErrorResponse(responseFormat); - } - - //execute business logic - Either<? extends Component, ResponseFormat> actionResponse = businessLogic.changeComponentState(componentType, componentId, modifier, transitionEnum, changeInfo, false, true); - if (actionResponse.isRight()) { - log.info("failed to change resource state"); - ResponseFormat responseFormat = actionResponse.right().value(); - responseWrapper.setInnerElement(responseFormat); - return buildErrorResponse(responseFormat); - } - - log.debug("change state successful !!!"); - responseObject = actionResponse.left().value(); - response = buildCreatedResourceResponse(responseObject, context, responseWrapper); - } else { - response = buildErrorResponse(responseWrapper.getInnerElement()); - } - - return response; - } catch (Exception e) { - BeEcompErrorManager.getInstance().processEcompError(EcompErrorName.BeRestApiGeneralError, "Change Lifecycle State"); - BeEcompErrorManager.getInstance().logBeRestApiGeneralError("Change Lifecycle State"); - log.debug("change lifecycle state failed with exception", e); - ResponseFormat responseFormat = getComponentsUtils().getResponseFormat(ActionStatus.GENERAL_ERROR); - responseWrapper.setInnerElement(responseFormat); - return buildErrorResponse(responseFormat); - } finally{ - auditChnageLifecycleAction(additionalParams, responseWrapper, componentType, component, responseObject, modifier, userId); - } - } + private void auditChnageLifecycleAction(EnumMap<AuditingFieldsKeysEnum, Object> additionalParams, Wrapper<ResponseFormat> responseWrapper, ComponentTypeEnum componentType, Component component, @@ -756,7 +800,6 @@ public class AssetsDataServlet extends AbstractValidationsServlet { return responseWrapper; } - private Either<LifeCycleTransitionEnum, ResponseFormat> validateTransitionEnum(final String lifecycleTransition, User user) { LifeCycleTransitionEnum transitionEnum = LifeCycleTransitionEnum.CHECKOUT; try { diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/servlets/AdditionalInformationServlet.java b/catalog-be/src/main/java/org/openecomp/sdc/be/servlets/AdditionalInformationServlet.java index c1d74b5d85..15b3eb20c6 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/servlets/AdditionalInformationServlet.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/servlets/AdditionalInformationServlet.java @@ -66,7 +66,15 @@ import fj.data.Either; public class AdditionalInformationServlet extends BeGenericServlet { private static Logger log = LoggerFactory.getLogger(AdditionalInformationServlet.class.getName()); - + + /** + * + * @param resourceId + * @param data + * @param request + * @param userUserId + * @return + */ @POST @Path("/resources/{resourceId}/additionalinfo") @Consumes(MediaType.APPLICATION_JSON) @@ -80,7 +88,15 @@ public class AdditionalInformationServlet extends BeGenericServlet { return createAdditionalInformationLabelForComponent(NodeTypeEnum.Resource, resourceId, request, userUserId, data); } - + + /** + * + * @param serviceId + * @param data + * @param request + * @param userUserId + * @return + */ @POST @Path("/services/{serviceId}/additionalinfo") @Consumes(MediaType.APPLICATION_JSON) @@ -94,7 +110,16 @@ public class AdditionalInformationServlet extends BeGenericServlet { return createAdditionalInformationLabelForComponent(NodeTypeEnum.Service, serviceId, request, userUserId, data); } - + + /** + * + * @param resourceId + * @param labelId + * @param data + * @param request + * @param userId + * @return + */ @PUT @Path("/resources/{resourceId}/additionalinfo/{labelId}") @Consumes(MediaType.APPLICATION_JSON) @@ -109,7 +134,16 @@ public class AdditionalInformationServlet extends BeGenericServlet { return updateAdditionalInformationLabelForComponent(NodeTypeEnum.Resource, resourceId, labelId, request, userId, data); } - + + /** + * + * @param serviceId + * @param labelId + * @param data + * @param request + * @param userId + * @return + */ @PUT @Path("/services/{serviceId}/additionalinfo/{labelId}") @Consumes(MediaType.APPLICATION_JSON) @@ -124,7 +158,15 @@ public class AdditionalInformationServlet extends BeGenericServlet { return updateAdditionalInformationLabelForComponent(NodeTypeEnum.Service, serviceId, labelId, request, userId, data); } - + + /** + * + * @param resourceId + * @param labelId + * @param request + * @param userId + * @return + */ @DELETE @Path("/resources/{resourceId}/additionalinfo/{labelId}") @Consumes(MediaType.APPLICATION_JSON) @@ -138,7 +180,15 @@ public class AdditionalInformationServlet extends BeGenericServlet { return deleteAdditionalInformationLabelForComponent(NodeTypeEnum.Resource, resourceId, labelId, request, userId); } - + + /** + * + * @param serviceId + * @param labelId + * @param request + * @param userId + * @return + */ @DELETE @Path("/services/{serviceId}/additionalinfo/{labelId}") @Consumes(MediaType.APPLICATION_JSON) @@ -152,7 +202,15 @@ public class AdditionalInformationServlet extends BeGenericServlet { return deleteAdditionalInformationLabelForComponent(NodeTypeEnum.Service, serviceId, labelId, request, userId); } - + + /** + * + * @param resourceId + * @param labelId + * @param request + * @param userId + * @return + */ @GET @Path("/resources/{resourceId}/additionalinfo/{labelId}") @Consumes(MediaType.APPLICATION_JSON) @@ -166,7 +224,15 @@ public class AdditionalInformationServlet extends BeGenericServlet { return getAdditionalInformationLabelForComponent(NodeTypeEnum.Resource, resourceId, labelId, request, userId); } - + + /** + * + * @param serviceId + * @param labelId + * @param request + * @param userId + * @return + */ @GET @Path("/services/{serviceId}/additionalinfo/{labelId}") @Consumes(MediaType.APPLICATION_JSON) @@ -180,7 +246,14 @@ public class AdditionalInformationServlet extends BeGenericServlet { return getAdditionalInformationLabelForComponent(NodeTypeEnum.Service, serviceId, labelId, request, userId); } - + + /** + * + * @param resourceId + * @param request + * @param userId + * @return + */ @GET @Path("/resources/{resourceId}/additionalinfo") @Consumes(MediaType.APPLICATION_JSON) @@ -194,7 +267,14 @@ public class AdditionalInformationServlet extends BeGenericServlet { return getAllAdditionalInformationLabelForComponent(NodeTypeEnum.Resource, resourceId, request, userId); } - + + /** + * + * @param serviceId + * @param request + * @param userId + * @return + */ @GET @Path("/services/{serviceId}/additionalinfo") @Consumes(MediaType.APPLICATION_JSON) diff --git a/catalog-be/src/main/java/org/openecomp/sdc/be/servlets/ComponentInstanceServlet.java b/catalog-be/src/main/java/org/openecomp/sdc/be/servlets/ComponentInstanceServlet.java index 48a45ac04c..9bf4b681bd 100644 --- a/catalog-be/src/main/java/org/openecomp/sdc/be/servlets/ComponentInstanceServlet.java +++ b/catalog-be/src/main/java/org/openecomp/sdc/be/servlets/ComponentInstanceServlet.java @@ -110,6 +110,7 @@ public class ComponentInstanceServlet extends AbstractValidationsServlet { try { ComponentInstance componentInstance = RepresentationUtils.fromRepresentation(data, ComponentInstance.class); + componentInstance.setInvariantName(null); ComponentTypeEnum componentTypeEnum = ComponentTypeEnum.findByParamName(containerComponentType); ComponentInstanceBusinessLogic componentInstanceLogic = getComponentInstanceBL(context, componentTypeEnum); if (componentInstanceLogic == null) { diff --git a/catalog-be/src/main/webapp/WEB-INF/web.xml b/catalog-be/src/main/webapp/WEB-INF/web.xml index fe228a3f97..b559d1b80f 100644 --- a/catalog-be/src/main/webapp/WEB-INF/web.xml +++ b/catalog-be/src/main/webapp/WEB-INF/web.xml @@ -130,7 +130,7 @@ <init-param> <param-name>swagger.api.basepath</param-name> <!-- Check if second param can be added --> - <param-value>http://localhost:8080/sdc/</param-value> + <param-value>http://localhost:8080/sdc</param-value> </init-param> <init-param> @@ -139,24 +139,6 @@ </init-param> <load-on-startup>2</load-on-startup> </servlet> - -<!-- Remove after swagger 2 integration --> -<!-- <servlet> - <servlet-name>Jersey2Config</servlet-name> - <servlet-class>io.swagger.jersey.config.JerseyJaxrsConfig</servlet-class> - <init-param> - <param-name>api.version</param-name> - <param-value>1.0.0</param-value> - </init-param> - - <init-param> - <param-name>swagger.api.basepath</param-name> - <param-value>http://behost:8080/sdc2/rest</param-value> - </init-param> - - <load-on-startup>2</load-on-startup> - <async-supported>true</async-supported> - </servlet> --> <!-- ECOMP Portal --> <servlet> @@ -165,13 +147,6 @@ <load-on-startup>3</load-on-startup> <async-supported>true</async-supported> </servlet> - -<!-- Remove after swagger 2 integration --> - <!-- Removed, the servlet mapping will be taken from annotation --> -<!-- <servlet-mapping> - <servlet-name>ECOMPServlet</servlet-name> - <url-pattern>/api/*</url-pattern> - </servlet-mapping> --> <servlet> <servlet-name>ViewStatusMessages</servlet-name> @@ -190,7 +165,7 @@ <async-supported>true</async-supported> <init-param> <param-name>methods</param-name> - <param-value>GET,POST</param-value> + <param-value>GET,POST,PUT,DELETE</param-value> </init-param> <init-param> <param-name>mimeTypes</param-name> diff --git a/catalog-be/src/test/java/org/openecomp/sdc/be/externalapi/servlet/AssetsDataServletTest.java b/catalog-be/src/test/java/org/openecomp/sdc/be/externalapi/servlet/AssetsDataServletTest.java index d6808da5d6..4251749f5a 100644 --- a/catalog-be/src/test/java/org/openecomp/sdc/be/externalapi/servlet/AssetsDataServletTest.java +++ b/catalog-be/src/test/java/org/openecomp/sdc/be/externalapi/servlet/AssetsDataServletTest.java @@ -101,7 +101,7 @@ public class AssetsDataServletTest extends JerseyTest { when(request.getHeader(Constants.X_ECOMP_INSTANCE_ID_HEADER)).thenReturn("mockXEcompInstanceId"); when(request.getHeader(Constants.USER_ID_HEADER)).thenReturn("mockAttID"); when(request.getRequestURL()).thenReturn(new StringBuffer("sdc/v1/catalog/resources")); - + when(session.getServletContext()).thenReturn(servletContext); when(servletContext.getAttribute(Constants.WEB_APPLICATION_CONTEXT_WRAPPER_ATTR)).thenReturn(webAppContextWrapper); when(webAppContextWrapper.getWebAppContext(servletContext)).thenReturn(webApplicationContext); @@ -159,7 +159,8 @@ public class AssetsDataServletTest extends JerseyTest { @Test public void createVfcmtHappyScenario() { final JSONObject createRequest = buildCreateJsonRequest(); - Response response = target().path("/v1/catalog/resources").request(MediaType.APPLICATION_JSON).post(Entity.json(createRequest.toJSONString()), Response.class); + Response response = target().path("/v1/catalog/resources").request(MediaType.APPLICATION_JSON).header(Constants.X_ECOMP_INSTANCE_ID_HEADER, "mockXEcompInstanceId").header(Constants.USER_ID_HEADER, "mockAttID") + .post(Entity.json(createRequest.toJSONString()), Response.class); assertTrue(response.getStatus() == HttpStatus.SC_CREATED); } |