class VfcManagerSol005 {

    public RestfulResponse terminateNs(NsOperationKey nsOperationKey, String nsInstanceId) throws ApplicationException {
        // Step1: save segment operation info for delete process
        LOGGER.info("save segment operation for delete process");
        ResourceOperationStatus status = new ResourceOperationStatus(nsOperationKey.getServiceId(),
                nsOperationKey.getOperationId(), nsOperationKey.getNodeTemplateUUID());
        status.setStatus(RequestsDbConstant.Status.PROCESSING);
        resourceOperationStatusRepository.save(status);

        LOGGER.info("SOL005 terminate ns -> begin");
        // Step2: prepare url and method type
        String url = getUrl(nsInstanceId, CommonConstant.Step.TERMINATE);
        String methodType = CommonConstant.MethodType.POST;

        instanceNfvoMapping = instanceNfvoMappingRepository.findOneByInstanceId(nsInstanceId);

        if (instanceNfvoMapping != null) {

            url = instanceNfvoMapping.getEndpoint() + instanceNfvoMapping.getApiRoot() + url;

        } else {
            throw new ApplicationException(HttpCode.INTERNAL_SERVER_ERROR, DriverExceptionID.FAIL_TO_TERMINATE_NS);
        }
        // Step3: prepare restful parameters and options
        Map<String, String> reqBody = new HashMap<>();
        reqBody.put("terminationTime", LocalDateTime.now().toString());

        // Step4: Call the NFVO or SDNO service to terminate service
        LOGGER.info("request body for terminate NS" + JsonUtil.marshal(reqBody));
        RestfulResponse terminateRsp = restfulUtil.send(url, methodType, JsonUtil.marshal(reqBody));
        ValidateUtil.assertObjectNotNull(terminateRsp);
        LOGGER.info("terminate ns response status is : {}", terminateRsp.getStatus());
        LOGGER.info("terminate ns response content is : {}", terminateRsp.getResponseContent());
        // Step 3: update segment operation
        if (!HttpCode.isSucess(terminateRsp.getStatus())) {
            LOGGER.error("fail to terminate ns");
            status.setStatus(RequestsDbConstant.Status.ERROR);
            status.setErrorCode(String.valueOf(terminateRsp.getStatus()));
            status.setStatusDescription(CommonConstant.StatusDesc.TERMINATE_NS_FAILED);
            resourceOperationStatusRepository.save(status);

            throw new ApplicationException(HttpCode.INTERNAL_SERVER_ERROR, DriverExceptionID.FAIL_TO_TERMINATE_NS);
        }
        // @SuppressWarnings("unchecked")
        String jobId = null;
        Map<String, String> rsp = new HashMap<>();
        if (terminateRsp.getStatus() == 202) {
            String jobUri = terminateRsp.getRespHeaderStr(CommonConstant.JOB_URI);
            jobId = jobUri.split("/")[4];
            jobId.split("/");
            if (ValidateUtil.isStrEmpty(jobId)) {
                LOGGER.error("Invalid jobId from instantiate operation");
                status.setStatus(RequestsDbConstant.Status.ERROR);
                status.setErrorCode(String.valueOf(terminateRsp.getStatus()));
                status.setStatusDescription(CommonConstant.StatusDesc.INSTANTIATE_NS_FAILED);
                resourceOperationStatusRepository.save(status);
                throw new ApplicationException(HttpCode.INTERNAL_SERVER_ERROR,
                        DriverExceptionID.INVALID_RESPONSE_FROM_INSTANTIATE_OPERATION);
            }
            rsp.put(CommonConstant.JOB_ID, jobId);
            LOGGER.info("terminate ns -> end");
            LOGGER.info("update segment job id -> begin");
            status.setProgress("60");
            status.setStatusDescription("NS is termination completed");
            status.setJobId(jobId);
            resourceOperationStatusRepository.save(status);
            LOGGER.info("update segment job id -> end");
        } else if (terminateRsp.getStatus() > 400 && terminateRsp.getStatus() < 600) {
            LOGGER.error("ERROR while executing instantiateNs request");
            ProblemDetails problemDetails = JsonUtil.unMarshal(terminateRsp.getResponseContent(), ProblemDetails.class);
            status.setStatus(RequestsDbConstant.Status.ERROR);
            status.setErrorCode(String.valueOf(terminateRsp.getStatus()));
            status.setStatusDescription(CommonConstant.StatusDesc.TERMINATE_NS_FAILED + problemDetails.getDetail());
            resourceOperationStatusRepository.save(status);
            if (terminateRsp.getStatus() == 406) {
                throw new ApplicationException(HttpCode.NOT_ACCEPTABLE, DriverExceptionID.FAIL_TO_TERMINATE_NS);
            } else if (terminateRsp.getStatus() == 400) {
                throw new ApplicationException(HttpCode.BAD_REQUEST, DriverExceptionID.FAIL_TO_TERMINATE_NS);
            } else if (terminateRsp.getStatus() == 404) {
                throw new ApplicationException(HttpCode.NOT_FOUND, DriverExceptionID.FAIL_TO_TERMINATE_NS);
            } else if (terminateRsp.getStatus() == 409) {
                LOGGER.error("The operation cannot be executed currently,\n"
                        + "due to a conflict with the state of the resource");
                throw new ApplicationException(HttpCode.RESPOND_CONFLICT, DriverExceptionID.FAIL_TO_TERMINATE_NS);
            } else if (terminateRsp.getStatus() == 500) {
                throw new ApplicationException(HttpCode.INTERNAL_SERVER_ERROR, DriverExceptionID.FAIL_TO_TERMINATE_NS);
            } else {
                throw new ApplicationException(HttpCode.INTERNAL_SERVER_ERROR, DriverExceptionID.FAIL_TO_TERMINATE_NS);
            }

        }
        instanceNfvoMapping.setJobId(jobId);
        instanceNfvoMappingRepository.save(instanceNfvoMapping);
        terminateRsp.setResponseContent(rsp.toString());
        return terminateRsp;
    }

    public  VfcManagerSol005();

}