X-Git-Url: https://gerrit.o-ran-sc.org/r/gitweb?a=blobdiff_plain;f=otf-service-api%2Fsrc%2Fmain%2Fjava%2Forg%2Foran%2Fotf%2Fapi%2Fservice%2Fimpl%2FTestStrategyServiceImpl.java;fp=otf-service-api%2Fsrc%2Fmain%2Fjava%2Forg%2Foran%2Fotf%2Fapi%2Fservice%2Fimpl%2FTestStrategyServiceImpl.java;h=13d125ab9c0048dfce864a0c82bd61804f9e9915;hb=14f6f95c84a4a1fa8774190db4a03fd0214ec55f;hp=0000000000000000000000000000000000000000;hpb=f49bd1efeaaddd4891c1f329b18d8cfb28b3e75b;p=it%2Fotf.git diff --git a/otf-service-api/src/main/java/org/oran/otf/api/service/impl/TestStrategyServiceImpl.java b/otf-service-api/src/main/java/org/oran/otf/api/service/impl/TestStrategyServiceImpl.java new file mode 100644 index 0000000..13d125a --- /dev/null +++ b/otf-service-api/src/main/java/org/oran/otf/api/service/impl/TestStrategyServiceImpl.java @@ -0,0 +1,228 @@ +/* Copyright (c) 2019 AT&T Intellectual Property. # +# # +# Licensed under the Apache License, Version 2.0 (the "License"); # +# you may not use this file except in compliance with the License. # +# You may obtain a copy of the License at # +# # +# http://www.apache.org/licenses/LICENSE-2.0 # +# # +# Unless required by applicable law or agreed to in writing, software # +# distributed under the License is distributed on an "AS IS" BASIS, # +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # +# See the License for the specific language governing permissions and # +# limitations under the License. # +##############################################################################*/ + + +package org.oran.otf.api.service.impl; + +import org.oran.otf.api.Utilities; +import org.oran.otf.api.handler.CamundaProcessDeploymentHandler; +import org.oran.otf.api.service.TestStrategyService; +import org.oran.otf.common.model.TestDefinition; +import org.oran.otf.common.model.User; +import org.oran.otf.common.model.local.BpmnInstance; +import org.oran.otf.common.model.local.DeployTestStrategyRequest; +import org.oran.otf.common.model.local.OTFApiResponse; +import org.oran.otf.common.repository.GroupRepository; +import org.oran.otf.common.repository.TestDefinitionRepository; +import org.oran.otf.common.repository.UserRepository; +import org.oran.otf.common.utility.http.ResponseUtility; +import com.fasterxml.jackson.databind.ObjectMapper; +import io.swagger.v3.oas.annotations.Hidden; +import java.io.IOException; +import java.io.InputStream; +import java.util.Base64; +import java.util.Optional; +import javax.ws.rs.core.MediaType; +import javax.ws.rs.core.Response; +import org.apache.http.HttpResponse; +import org.apache.http.conn.HttpHostConnectException; +import org.apache.http.util.EntityUtils; +import org.bson.types.ObjectId; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +@Service +@Hidden +public class TestStrategyServiceImpl implements TestStrategyService { + + private static final Logger logger = LoggerFactory.getLogger(TestStrategyServiceImpl.class); + + @Autowired private TestDefinitionRepository testDefinitionRepository; + + @Autowired private UserRepository userRepository; + + @Autowired private CamundaProcessDeploymentHandler camundaProcessDeploymentHandler; + + @Autowired private GroupRepository groupRepository; + + public Response deployTestStrategy( + InputStream bpmn, + InputStream compressedResources, + String testDefinitionId, + String testDefinitionDeployerId, + String definitionId, + String authorization) { + if (bpmn == null) + return Utilities.Http.BuildResponse.badRequestWithMessage( + "BPMN input stream cannot be null."); + + // Decode the authorization header. + byte[] decodedAuthorization = Base64.getDecoder().decode(authorization.replace("Basic ", "")); + String credentials = new String(decodedAuthorization); + String[] credentialsArray = credentials.split(":"); + + /* Check if the request came from the system specified mechanized identifier. The request goes through AAF + * authorization before reaching this code, therefore, assume the headers aren't spoofed. */ + if (!credentialsArray[0].equals(System.getenv("AAF_ID"))) + return Utilities.Http.BuildResponse.badRequestWithMessage( + "Unauthorized to use this service."); + + // Map to a POJO model2. + ObjectId _testDefinitionDeployerId = null; + ObjectId _testDefinitionId = null; + + if (testDefinitionDeployerId != null && ObjectId.isValid(testDefinitionDeployerId)) + _testDefinitionDeployerId = new ObjectId(testDefinitionDeployerId); + if (testDefinitionId != null && ObjectId.isValid(testDefinitionId)) + _testDefinitionId = new ObjectId(testDefinitionId); + + DeployTestStrategyRequest request = + new DeployTestStrategyRequest(_testDefinitionDeployerId, _testDefinitionId, definitionId); + + // String bpmnContents = null; + // try (final Reader reader = new InputStreamReader(bpmn)) { + // bpmnContents = CharStreams.toString(reader); + // } catch (Exception e) { + // e.printStackTrace(); + // } + + // Check if the request actually contains a bpmn string. + // try { + // if (bpmnContents == null || bpmnContents.trim().length() == 0) + // return Utilities.Http.BuildResponse.badRequestWithMessage("BPMN contents are null."); + // } catch (Exception e) { + // logger.error(Utilities.getStackTrace(e)); + // } + + // If a test definition id is supplied, the request intends to update an existing test + // definition. + if (request.getTestDefinitionId() != null) { + // Check if the test definition exists in the database. + Optional testDefinitionOptional = + testDefinitionRepository.findById(request.getTestDefinitionId().toString()); + + if (!testDefinitionOptional.isPresent()) + return Utilities.Http.BuildResponse.badRequestWithMessage( + String.format("Test definition (%s) was not found.", request.getTestDefinitionId())); + + // Check if a user to update the definition was supplied. + if (request.getTestDefinitionDeployerId() == null) + return Utilities.Http.BuildResponse.badRequestWithMessage( + "Must specify testDefinitionDeployerId."); + + // Check if the user requesting to update the definition is the user who originally created + // the definition. + TestDefinition testDefinition = testDefinitionOptional.get(); + + if (!testDefinition + .getCreatedBy() + .toString() + .equals(request.getTestDefinitionDeployerId().toString())) + return Utilities.Http.BuildResponse.badRequestWithMessage( + String.format( + "User (%s) is not authorized to update this test definition.", + request.getTestDefinitionDeployerId())); + + // Check if the version to deploy already exists + for (BpmnInstance bpmnInstance : testDefinition.getBpmnInstances()) { + if (bpmnInstance.getProcessDefinitionId().equalsIgnoreCase(request.getDefinitionId())) + return Utilities.Http.BuildResponse.badRequestWithMessage( + String.format( + "A deployment with the definitionId %s already exists.", + request.getDefinitionId())); + } + } + + // Make the deployment request to Camunda. Relay the response received by Camunda. + return camundaProcessDeploymentHandler.start(bpmn, compressedResources); + } + + public Response deleteByDeploymentId(String deploymentId, String authorization) { + User user = Utilities.findUserByAuthHeader(authorization, userRepository); + if (!isAuthorized(authorization)) { + return Utilities.Http.BuildResponse.unauthorized(); + } + + String url = + String.format( + "%s:%s/%s/%s", + System.getenv("otf.camunda.host"), + System.getenv("otf.camunda.port"), + System.getenv("otf.camunda.deploymentDeletionUri"), + deploymentId); + + try { + HttpResponse res = Utilities.Http.httpDeleteAAF(url); + String resStr = EntityUtils.toString(res.getEntity()); + int status = res.getStatusLine().getStatusCode(); + return Response.status(status) + .type(MediaType.APPLICATION_JSON) + .entity(new OTFApiResponse(status, resStr)) + .build(); + + } catch (Exception e) { + e.printStackTrace(); + return Utilities.Http.BuildResponse.internalServerError(); + } + } + + public Response deleteByTestDefinitionId(String testDefinitionId, String authorization) { + User user = Utilities.findUserByAuthHeader(authorization, userRepository); + if (!isAuthorized(authorization)) { + return Utilities.Http.BuildResponse.unauthorizedWithMessage("Authorization headers not set."); + } + + String url = + String.format( + "%s:%s/%s/%s", + System.getenv("otf.camunda.host"), + System.getenv("otf.camunda.port"), + System.getenv("otf.camunda.testDefinitionDeletionUri"), + testDefinitionId); + + try { + HttpResponse res = Utilities.Http.httpDeleteAAF(url); + String resStr = EntityUtils.toString(res.getEntity()); + int status = res.getStatusLine().getStatusCode(); + return Response.status(status) + .type(MediaType.APPLICATION_JSON) + .entity(new OTFApiResponse(status, resStr)) + .build(); + } catch (HttpHostConnectException e) { + return ResponseUtility.Build.serviceUnavailableWithMessage(e.getMessage()); + } catch (Exception e) { + e.printStackTrace(); + return Utilities.Http.BuildResponse.internalServerError(); + } + } + + private boolean isAuthorized(String authorization) { + User user = Utilities.findUserByAuthHeader(authorization, userRepository); + return (user.getEmail().equalsIgnoreCase("email@localhost") + || user.getEmail().equalsIgnoreCase("email@localhost")); + } + + private DeployTestStrategyRequest mapToDeployTestStrategyRequest(String body) { + ObjectMapper mapper = new ObjectMapper(); + try { + return mapper.readValue(body, DeployTestStrategyRequest.class); // Perform the mapping + } catch (IOException e) { // Indicates an unknown request body + logger.error(e.getMessage()); + return null; + } + } +}