diff options
author | hyu2010 <henry.yu1@huawei.com> | 2020-09-07 18:07:25 -0400 |
---|---|---|
committer | hyu2010 <henry.yu1@huawei.com> | 2020-09-15 21:21:22 -0400 |
commit | c2110d59a01f3343a42cf55045bf67e456c2f182 (patch) | |
tree | 606150d795cd28469204e4fe35c13016ad89fe19 /bpmn/so-bpmn-infrastructure-common/src/main/groovy | |
parent | 78be30206872dbf2907a42d5070b197536d4a9c2 (diff) |
Implementation of TN NSSMF WF on SO
(1) Workflow of Allocate TN NSSI
(2) Workflow of Deallocate TN NSSI
(3) Workflow of Activate and Deactivate TN NSSI
(4) Workflow of Modify TN NSSI
NOTE:
1. The full implementation of TN NSSMF consists of two layers:
(1) The TN Sice definition layer, which is an orchestration
layer that provides the NBI of TN NSSMF to its consumers
(i.e., it concerns the "what" question), and (2) the TN slice
realization layer, which is responsible for the actual network
configurations of TN slicing (i.e., the "how" question). The first
layer is done on the SO (i.e., this changeset), while the 2nd
layer is implemented on the SDNC. That's why this changeset is
relatively simple, since the "real work" is done by the SDNC.
2. This changeset depends on the common NSSMF WF
(https://gerrit.onap.org/r/c/so/+/111477)
Issue-ID: SO-2959
Signed-off-by: hyu2010 <henry.yu1@huawei.com>
Change-Id: I9d4e77b7706d28fb4133ddca0ff1d6e307be613d
Signed-off-by: hyu2010 <henry.yu1@huawei.com>
Diffstat (limited to 'bpmn/so-bpmn-infrastructure-common/src/main/groovy')
6 files changed, 1546 insertions, 0 deletions
diff --git a/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoActivateTnNssi.groovy b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoActivateTnNssi.groovy new file mode 100644 index 0000000000..04fe161295 --- /dev/null +++ b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoActivateTnNssi.groovy @@ -0,0 +1,162 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP - SO + * ================================================================================ + * Copyright (C) 2020 Huawei Technologies Co., Ltd. All rights reserved. + * ================================================================================ + * 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. + * ============LICENSE_END========================================================= + */ + +package org.onap.so.bpmn.infrastructure.scripts + +import com.fasterxml.jackson.databind.ObjectMapper +import groovy.json.JsonSlurper +import org.camunda.bpm.engine.delegate.BpmnError +import org.camunda.bpm.engine.delegate.DelegateExecution +import org.onap.aai.domain.yang.ServiceInstance +import org.onap.aaiclient.client.aai.AAIObjectType +import org.onap.aaiclient.client.aai.AAIResourcesClient +import org.onap.aaiclient.client.aai.entities.uri.AAIResourceUri +import org.onap.aaiclient.client.aai.entities.uri.AAIUriFactory +import org.onap.so.bpmn.common.scripts.AbstractServiceTaskProcessor +import org.onap.so.bpmn.common.scripts.ExceptionUtil +import org.onap.so.bpmn.common.scripts.RequestDBUtil +import org.onap.so.bpmn.core.json.JsonUtils +import org.onap.so.db.request.beans.ResourceOperationStatus +import org.slf4j.Logger +import org.slf4j.LoggerFactory + +public class DoActivateTnNssi extends AbstractServiceTaskProcessor { + String Prefix = "TNACT_" + + ExceptionUtil exceptionUtil = new ExceptionUtil() + JsonUtils jsonUtil = new JsonUtils() + RequestDBUtil requestDBUtil = new RequestDBUtil() + TnNssmfUtils tnNssmfUtils = new TnNssmfUtils() + JsonSlurper jsonSlurper = new JsonSlurper() + ObjectMapper objectMapper = new ObjectMapper() + private static final Logger logger = LoggerFactory.getLogger(DoActivateTnNssi.class) + + + public void preProcessRequest(DelegateExecution execution) { + logger.debug("Start preProcessRequest") + + execution.setVariable("startTime", System.currentTimeMillis()) + String msg = tnNssmfUtils.getExecutionInputParams(execution) + logger.debug("Activate TN NSSI input parameters: " + msg) + + execution.setVariable("prefix", Prefix) + + tnNssmfUtils.setSdncCallbackUrl(execution, true) + logger.debug("SDNC Callback URL: " + execution.getVariable("sdncCallbackUrl")) + + String modelInvariantUuid = execution.getVariable("modelInvariantUuid") + String modelUuid = execution.getVariable("modelUuid") + //here modelVersion is not set, we use modelUuid to decompose the service. + def isDebugLogEnabled = true + execution.setVariable("isDebugLogEnabled", isDebugLogEnabled) + String serviceModelInfo = """{ + "modelInvariantUuid":"${modelInvariantUuid}", + "modelUuid":"${modelUuid}", + "modelVersion":"" + }""" + execution.setVariable("serviceModelInfo", serviceModelInfo) + + String sliceServiceInstanceId = execution.getVariable("serviceInstanceID") + execution.setVariable("sliceServiceInstanceId", sliceServiceInstanceId) + + String sliceServiceInstanceName = execution.getVariable("servicename") + execution.setVariable("sliceServiceInstanceName", sliceServiceInstanceName) + + String operationType = execution.getVariable("operationType") + String actionType = operationType.equals("activateInstance") ? "activate" : "deactivate" + execution.setVariable("actionType", actionType) + + + logger.debug("Finish preProcessRequest") + } + + void preprocessSdncActOrDeactTnNssiRequest(DelegateExecution execution) { + def method = getClass().getSimpleName() + '.preprocessSdncActivateTnNssiRequest(' + + 'execution=' + execution.getId() + ')' + def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled') + logger.trace('Entered ' + method) + + try { + String serviceInstanceId = execution.getVariable("sliceServiceInstanceId") + String actionType = execution.getVariable("actionType") + + String sdncRequest = tnNssmfUtils.buildSDNCRequest(execution, serviceInstanceId, actionType) + + execution.setVariable("TNNSSMF_SDNCRequest", sdncRequest) + logger.debug("Outgoing SDNCRequest is: \n" + sdncRequest) + + } catch (Exception e) { + logger.debug("Exception Occured Processing preprocessSdncDeallocateTnNssiRequest. Exception is:\n" + e) + exceptionUtil.buildAndThrowWorkflowException(execution, 1002, "Error Occured during preProcessSDNCActivateRequest Method:\n" + e.getMessage()) + } + logger.trace("COMPLETED preprocessSdncActivateTnNssiRequest Process") + } + + + void validateSDNCResponse(DelegateExecution execution, String response) { + tnNssmfUtils.validateSDNCResponse(execution, response, method) + } + + + void updateAAIOrchStatus(DelegateExecution execution) { + logger.debug("Start updateAAIOrchStatus") + String tnNssiId = execution.getVariable("tnNssiId") + String orchStatus = execution.getVariable("orchestrationStatus") + + try { + ServiceInstance si = new ServiceInstance() + si.setOrchestrationStatus(orchStatus) + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, tnNssiId) + client.update(uri, si) + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in CreateSliceService.updateAAIOrchStatus " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + + logger.debug("Finish updateAAIOrchStatus") + } + + void prepareUpdateJobStatus(DelegateExecution execution, + String status, + String progress, + String statusDescription) { + String serviceId = execution.getVariable("serviceInstanceID") + String jobId = execution.getVariable("jobId") + String nsiId = execution.getVariable("nsiId") + String operType = execution.getVariable("actionType") + + + ResourceOperationStatus roStatus = new ResourceOperationStatus() + roStatus.setServiceId(serviceId) + roStatus.setOperationId(jobId) + roStatus.setResourceTemplateUUID(nsiId) + roStatus.setOperType(operType) + roStatus.setProgress(progress) + roStatus.setStatus(status) + roStatus.setStatusDescription(statusDescription) + requestDBUtil.prepareUpdateResourceOperationStatus(execution, status) + } + +} + diff --git a/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoCreateTnNssiInstance.groovy b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoCreateTnNssiInstance.groovy new file mode 100644 index 0000000000..534467f6ab --- /dev/null +++ b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoCreateTnNssiInstance.groovy @@ -0,0 +1,231 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP - SO + * ================================================================================ + * Copyright (C) 2020 Huawei Technologies Co., Ltd. All rights reserved. + * ================================================================================ + * 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. + * ============LICENSE_END========================================================= + */ + +package org.onap.so.bpmn.infrastructure.scripts + +import org.camunda.bpm.engine.delegate.BpmnError +import org.camunda.bpm.engine.delegate.DelegateExecution +import org.onap.aai.domain.yang.SliceProfile +import org.onap.aaiclient.client.aai.AAIObjectType +import org.onap.aaiclient.client.aai.AAIResourcesClient +import org.onap.aaiclient.client.aai.entities.uri.AAIResourceUri +import org.onap.aaiclient.client.aai.entities.uri.AAIUriFactory +import org.onap.so.bpmn.common.scripts.AbstractServiceTaskProcessor +import org.onap.so.bpmn.common.scripts.ExceptionUtil +import org.onap.so.bpmn.core.json.JsonUtils +import org.slf4j.Logger +import org.slf4j.LoggerFactory + +class DoCreateTnNssiInstance extends AbstractServiceTaskProcessor { + + private static final Logger logger = LoggerFactory.getLogger(DoCreateTnNssiInstance.class); + JsonUtils jsonUtil = new JsonUtils() + TnNssmfUtils tnNssmfUtils = new TnNssmfUtils() + ExceptionUtil exceptionUtil = new ExceptionUtil() + String Prefix = "DCTN_" + + void preProcessRequest(DelegateExecution execution) { + String msg = "" + logger.trace("Enter preProcessRequest()") + + execution.setVariable("prefix", Prefix) + + String modelInvariantUuid = execution.getVariable("modelInvariantUuid") + String modelUuid = execution.getVariable("modelUuid") + //here modelVersion is not set, we use modelUuid to decompose the service. + def isDebugLogEnabled = true + execution.setVariable("isDebugLogEnabled", isDebugLogEnabled) + String serviceModelInfo = """{ + "modelInvariantUuid":"${modelInvariantUuid}", + "modelUuid":"${modelUuid}", + "modelVersion":"" + }""" + execution.setVariable("serviceModelInfo", serviceModelInfo) + + logger.trace("Exit preProcessRequest") + } + + + void createSliceProfile(DelegateExecution execution) { + + String sliceserviceInstanceId = execution.getVariable("sliceServiceInstanceId") + String sliceProfileStr = execution.getVariable("sliceProfile") + String sliceProfileId = UUID.randomUUID().toString() + SliceProfile sliceProfile = new SliceProfile(); + sliceProfile.setProfileId(sliceProfileId) + sliceProfile.setLatency(Integer.parseInt(jsonUtil.getJsonValue(sliceProfileStr, "latency"))) + sliceProfile.setResourceSharingLevel(jsonUtil.getJsonValue(sliceProfileStr, "resourceSharingLevel")) + sliceProfile.setSNssai(tnNssmfUtils.getFirstSnssaiFromSliceProfile(sliceProfileStr)) //TODO: should be list + + sliceProfile.setE2ELatency(Integer.parseInt(jsonUtil.getJsonValue(sliceProfileStr, "latency"))) + sliceProfile.setMaxBandwidth(Integer.parseInt(jsonUtil.getJsonValue(sliceProfileStr, "maxBandwidth"))) + + //TODO: new API + sliceProfile.setReliability(new Object()) + try { + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SLICE_PROFILE, execution.getVariable + ("globalSubscriberId"), + execution.getVariable("subscriptionServiceType"), sliceserviceInstanceId, sliceProfileId) + client.create(uri, sliceProfile) + + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in DoCreateSliceServiceInstance.instantiateSliceService. " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + } + + + void createServiceInstance(DelegateExecution execution) { + + String serviceRole = "TN" + String serviceType = execution.getVariable("subscriptionServiceType") + String ssInstanceId = execution.getVariable("sliceServiceInstanceId") + String sliceProfileStr = execution.getVariable("sliceProfile") + try { + org.onap.aai.domain.yang.ServiceInstance ss = new org.onap.aai.domain.yang.ServiceInstance() + ss.setServiceInstanceId(ssInstanceId) + String sliceInstanceName = execution.getVariable("sliceServiceInstanceName") + ss.setServiceInstanceName(sliceInstanceName) + ss.setServiceType(serviceType) + String serviceStatus = "allocated" + ss.setOrchestrationStatus(serviceStatus) + String modelInvariantUuid = execution.getVariable("modelInvariantUuid") + String modelUuid = execution.getVariable("modelUuid") + ss.setModelInvariantId(modelInvariantUuid) + ss.setModelVersionId(modelUuid) + String serviceInstanceLocationid = tnNssmfUtils.getFirstPlmnIdFromSliceProfile(sliceProfileStr) + ss.setServiceInstanceLocationId(serviceInstanceLocationid) + String snssai = tnNssmfUtils.getFirstSnssaiFromSliceProfile(sliceProfileStr) + ss.setEnvironmentContext(snssai) + ss.setServiceRole(serviceRole) + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, execution.getVariable("globalSubscriberId"), execution.getVariable("subscriptionServiceType"), ssInstanceId) + client.create(uri, ss) + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in DoCreateTnNssiInstance.createServiceInstance. " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + } + + + void createAllottedResource(DelegateExecution execution) { + String serviceInstanceId = execution.getVariable('sliceServiceInstanceId') + + AAIResourcesClient resourceClient = getAAIClient() + AAIResourceUri ssServiceuri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, serviceInstanceId) + + try { + List<String> networkStrList = jsonUtil.StringArrayToList(execution.getVariable("transportSliceNetworks")) + + for (String networkStr : networkStrList) { + String allottedResourceId = UUID.randomUUID().toString() + AAIResourceUri allottedResourceUri = AAIUriFactory.createResourceUri(AAIObjectType.ALLOTTED_RESOURCE, + execution.getVariable("globalSubscriberId"), execution.getVariable("subscriptionServiceType"), + execution.getVariable("sliceserviceInstanceId"), allottedResourceId) + execution.setVariable("allottedResourceUri", allottedResourceUri) + String modelInvariantId = execution.getVariable("modelInvariantUuid") + String modelVersionId = execution.getVariable("modelUuid") + + org.onap.aai.domain.yang.AllottedResource resource = new org.onap.aai.domain.yang.AllottedResource() + resource.setId(allottedResourceId) + resource.setType("TsciNetwork") + resource.setAllottedResourceName("network_" + execution.getVariable("sliceServiceInstanceName")) + resource.setModelInvariantId(modelInvariantId) + resource.setModelVersionId(modelVersionId) + getAAIClient().create(allottedResourceUri, resource) + //AAIResourceUri serviceInstanceUri = AAIUriFactory.createResourceFromExistingURI(AAIObjectType.SERVICE_INSTANCE, UriBuilder.fromPath(ssServiceuri).build()) + //getAAIClient().connect(allottedResourceUri,ssServiceuri) + //execution.setVariable("aaiARPath", allottedResourceUri.build().toString()); + + String linkArrayStr = jsonUtil.getJsonValue(networkStr, "connectionLinks") + createLogicalLinksForAllocatedResource(execution, linkArrayStr, serviceInstanceId, allottedResourceId) + } + + } catch (Exception ex) { + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, "Exception in createAaiAR " + ex.getMessage()) + } + } + + void createLogicalLinksForAllocatedResource(DelegateExecution execution, + String linkArrayStr, String serviceInstanceId, + String allottedResourceId) { + + try { + List<String> linkStrList = jsonUtil.StringArrayToList(linkArrayStr) + + for (String linkStr : linkStrList) { + String logicalLinkId = UUID.randomUUID().toString() + String epA = jsonUtil.getJsonValue(linkStr, "transportEndpointA") + String epB = jsonUtil.getJsonValue(linkStr, "transportEndpointB") + String modelInvariantId = execution.getVariable("modelInvariantUuid") + String modelVersionId = execution.getVariable("modelUuid") + + org.onap.aai.domain.yang.LogicalLink resource = new org.onap.aai.domain.yang.LogicalLink() + resource.setLinkId(logicalLinkId) + resource.setLinkName(epA) + resource.setLinkName2(epB) + resource.setModelInvariantId(modelInvariantId) + resource.setModelVersionId(modelVersionId) + + AAIResourceUri logicalLinkUri = AAIUriFactory.createResourceUri(AAIObjectType.LOGICAL_LINK, logicalLinkId) + getAAIClient().create(logicalLinkUri, resource) + } + } catch (Exception ex) { + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, + "Exception in createLogicalLinksForAllocatedResource" + ex.getMessage()) + } + } + + void preprocessSdncAllocateTnNssiRequest(DelegateExecution execution) { + def method = getClass().getSimpleName() + '.preProcessSDNCActivateRequest(' + + 'execution=' + execution.getId() + + ')' + def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled') + logger.trace('Entered ' + method) + + logger.trace("STARTED preProcessSDNCActivateRequest Process") + try { + String serviceInstanceId = execution.getVariable("sliceServiceInstanceId") + + String createSDNCRequest = tnNssmfUtils.buildSDNCRequest(execution, serviceInstanceId, "create") + + execution.setVariable("TNNSSMF_SDNCRequest", createSDNCRequest) + logger.debug("Outgoing SDNCRequest is: \n" + createSDNCRequest) + + } catch (Exception e) { + logger.debug("Exception Occured Processing preProcessSDNCActivateRequest. Exception is:\n" + e) + exceptionUtil.buildAndThrowWorkflowException(execution, 1002, + "Error Occured during preProcessSDNCActivateRequest Method:\n" + e.getMessage()) + } + logger.trace("COMPLETED preProcessSDNCActivateRequest Process") + } + + + void validateSDNCResponse(DelegateExecution execution, String response, String method) { + tnNssmfUtils.validateSDNCResponse(execution, response, method) + } +} diff --git a/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoDeallocateTnNssi.groovy b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoDeallocateTnNssi.groovy new file mode 100644 index 0000000000..7681bf9346 --- /dev/null +++ b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoDeallocateTnNssi.groovy @@ -0,0 +1,169 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP - SO + * ================================================================================ + * Copyright (C) 2020 Huawei Technologies Co., Ltd. All rights reserved. + * ================================================================================ + * 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. + * ============LICENSE_END========================================================= + */ + +package org.onap.so.bpmn.infrastructure.scripts + +import com.fasterxml.jackson.databind.ObjectMapper +import groovy.json.JsonSlurper +import org.camunda.bpm.engine.delegate.BpmnError +import org.camunda.bpm.engine.delegate.DelegateExecution +import org.onap.aai.domain.yang.ServiceInstance +import org.onap.aaiclient.client.aai.AAIObjectType +import org.onap.aaiclient.client.aai.AAIResourcesClient +import org.onap.aaiclient.client.aai.entities.uri.AAIResourceUri +import org.onap.aaiclient.client.aai.entities.uri.AAIUriFactory +import org.onap.so.bpmn.common.scripts.AbstractServiceTaskProcessor +import org.onap.so.bpmn.common.scripts.ExceptionUtil +import org.onap.so.bpmn.common.scripts.RequestDBUtil +import org.onap.so.bpmn.core.json.JsonUtils +import org.onap.so.db.request.beans.ResourceOperationStatus +import org.slf4j.Logger +import org.slf4j.LoggerFactory + +class DoDeallocateTnNssi extends AbstractServiceTaskProcessor { + String Prefix = "TNDEALLOC_" + + ExceptionUtil exceptionUtil = new ExceptionUtil() + JsonUtils jsonUtil = new JsonUtils() + RequestDBUtil requestDBUtil = new RequestDBUtil() + TnNssmfUtils tnNssmfUtils = new TnNssmfUtils() + JsonSlurper jsonSlurper = new JsonSlurper() + ObjectMapper objectMapper = new ObjectMapper() + private static final Logger logger = LoggerFactory.getLogger(DoDeallocateTnNssi.class) + + + void preProcessRequest(DelegateExecution execution) { + logger.debug("Start preProcessRequest") + + execution.setVariable("startTime", System.currentTimeMillis()) + String msg = tnNssmfUtils.getExecutionInputParams(execution) + logger.debug("Deallocate TN NSSI input parameters: " + msg) + + execution.setVariable("prefix", Prefix) + + tnNssmfUtils.setSdncCallbackUrl(execution, true) + logger.debug("SDNC Callback URL: " + execution.getVariable("sdncCallbackUrl")) + + String sliceServiceInstanceId = execution.getVariable("serviceInstanceID") + execution.setVariable("sliceServiceInstanceId", sliceServiceInstanceId) + + String sliceServiceInstanceName = execution.getVariable("servicename") + execution.setVariable("sliceServiceInstanceName", sliceServiceInstanceName) + + + String modelInvariantUuid = execution.getVariable("modelInvariantUuid") + String modelUuid = execution.getVariable("modelUuid") + //here modelVersion is not set, we use modelUuid to decompose the service. + def isDebugLogEnabled = true + execution.setVariable("isDebugLogEnabled", isDebugLogEnabled) + String serviceModelInfo = """{ + "modelInvariantUuid":"${modelInvariantUuid}", + "modelUuid":"${modelUuid}", + "modelVersion":"" + }""" + execution.setVariable("serviceModelInfo", serviceModelInfo) + logger.debug("Finish preProcessRequest") + } + + void preprocessSdncDeallocateTnNssiRequest(DelegateExecution execution) { + def method = getClass().getSimpleName() + '.preprocessSdncDeallocateTnNssiRequest(' + + 'execution=' + execution.getId() + ')' + def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled') + logger.trace('Entered ' + method) + + try { + String serviceInstanceId = execution.getVariable("serviceInstanceID") + + String sdncRequest = tnNssmfUtils.buildSDNCRequest(execution, serviceInstanceId, "deallocate") + + execution.setVariable("TNNSSMF_SDNCRequest", sdncRequest) + logger.debug("Outgoing SDNCRequest is: \n" + sdncRequest) + + } catch (Exception e) { + logger.debug("Exception Occured Processing preprocessSdncDeallocateTnNssiRequest. Exception is:\n" + e) + exceptionUtil.buildAndThrowWorkflowException(execution, 1002, "Error Occured during preProcessSDNCActivateRequest Method:\n" + e.getMessage()) + } + logger.trace("COMPLETED preprocessSdncDeallocateTnNssiRequest Process") + } + + + void validateSDNCResponse(DelegateExecution execution, String response, String method) { + tnNssmfUtils.validateSDNCResponse(execution, response, method) + } + + void deleteServiceInstance(DelegateExecution execution) { + try { + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, + execution.getVariable("globalSubscriberId"), + execution.getVariable("subscriptionServiceType"), + execution.getVariable("serviceInstanceID")) + client.delete(uri) + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in DoDeallocateTnNssi.deleteServiceInstance. " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + } + + public void updateAAIOrchStatus(DelegateExecution execution) { + logger.debug("Start updateAAIOrchStatus") + String tnNssiId = execution.getVariable("serviceInstanceID") + String orchStatus = execution.getVariable("orchestrationStatus") + + try { + ServiceInstance si = new ServiceInstance() + si.setOrchestrationStatus(orchStatus) + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, tnNssiId) + client.update(uri, si) + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in CreateSliceService.updateAAIOrchStatus " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + + logger.debug("Finish updateAAIOrchStatus") + } + + void prepareUpdateJobStatus(DelegateExecution execution, + String status, + String progress, + String statusDescription) { + String serviceId = execution.getVariable("serviceInstanceID") + String jobId = execution.getVariable("jobId") + String nsiId = execution.getVariable("nsiId") + + ResourceOperationStatus roStatus = new ResourceOperationStatus() + roStatus.setServiceId(serviceId) + roStatus.setOperationId(jobId) + roStatus.setResourceTemplateUUID(nsiId) + roStatus.setOperType("Deallocate") + roStatus.setProgress(progress) + roStatus.setStatus(status) + roStatus.setStatusDescription(statusDescription) + requestDBUtil.prepareUpdateResourceOperationStatus(execution, status) + } +} + diff --git a/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoModifyTnNssi.groovy b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoModifyTnNssi.groovy new file mode 100644 index 0000000000..0b7a5ff59b --- /dev/null +++ b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/DoModifyTnNssi.groovy @@ -0,0 +1,401 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP - SO + * ================================================================================ + * Copyright (C) 2020 Huawei Technologies Co., Ltd. All rights reserved. + * ================================================================================ + * 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. + * ============LICENSE_END========================================================= + */ + +package org.onap.so.bpmn.infrastructure.scripts + +import com.fasterxml.jackson.databind.ObjectMapper +import groovy.json.JsonSlurper +import org.camunda.bpm.engine.delegate.BpmnError +import org.camunda.bpm.engine.delegate.DelegateExecution +import org.onap.aai.domain.yang.ServiceInstance +import org.onap.aai.domain.yang.SliceProfile +import org.onap.aaiclient.client.aai.AAIObjectType +import org.onap.aaiclient.client.aai.AAIResourcesClient +import org.onap.aaiclient.client.aai.entities.uri.AAIResourceUri +import org.onap.aaiclient.client.aai.entities.uri.AAIUriFactory +import org.onap.so.bpmn.common.scripts.AbstractServiceTaskProcessor +import org.onap.so.bpmn.common.scripts.ExceptionUtil +import org.onap.so.bpmn.common.scripts.RequestDBUtil +import org.onap.so.bpmn.core.json.JsonUtils +import org.onap.so.db.request.beans.ResourceOperationStatus +import org.slf4j.Logger +import org.slf4j.LoggerFactory + +import static org.apache.commons.lang3.StringUtils.isBlank + +public class DoModifyTnNssi extends AbstractServiceTaskProcessor { + String Prefix = "TNMOD_" + + ExceptionUtil exceptionUtil = new ExceptionUtil() + JsonUtils jsonUtil = new JsonUtils() + RequestDBUtil requestDBUtil = new RequestDBUtil() + TnNssmfUtils tnNssmfUtils = new TnNssmfUtils() + JsonSlurper jsonSlurper = new JsonSlurper() + ObjectMapper objectMapper = new ObjectMapper() + private static final Logger logger = LoggerFactory.getLogger(DoModifyTnNssi.class) + + + void preProcessRequest(DelegateExecution execution) { + logger.debug("Start preProcessRequest") + execution.setVariable("prefix", Prefix) + String msg = "" + + try { + execution.setVariable("startTime", System.currentTimeMillis()) + msg = tnNssmfUtils.getExecutionInputParams(execution) + logger.debug("Modify TN NSSI input parameters: " + msg) + + execution.setVariable("prefix", Prefix) + + tnNssmfUtils.setSdncCallbackUrl(execution, true) + logger.debug("SDNC Callback URL: " + execution.getVariable("sdncCallbackUrl")) + + String additionalPropJsonStr = execution.getVariable("sliceParams") + + String sliceServiceInstanceId = execution.getVariable("serviceInstanceID") + execution.setVariable("sliceServiceInstanceId", sliceServiceInstanceId) + + String sliceServiceInstanceName = execution.getVariable("servicename") + execution.setVariable("sliceServiceInstanceName", sliceServiceInstanceName) + + String operationId = UUID.randomUUID().toString() + execution.setVariable("operationId", operationId) + + String modelInvariantUuid = execution.getVariable("modelInvariantUuid") + String modelUuid = execution.getVariable("modelUuid") + //here modelVersion is not set, we use modelUuid to decompose the service. + def isDebugLogEnabled = true + execution.setVariable("isDebugLogEnabled", isDebugLogEnabled) + String serviceModelInfo = """{ + "modelInvariantUuid":"${modelInvariantUuid}", + "modelUuid":"${modelUuid}", + "modelVersion":"" + }""" + execution.setVariable("serviceModelInfo", serviceModelInfo) + + //additional properties + String sliceProfile = jsonUtil.getJsonValue(additionalPropJsonStr, "sliceProfile") + if (isBlank(sliceProfile)) { + msg = "Input sliceProfile is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } else { + execution.setVariable("sliceProfile", sliceProfile) + } + + String transportSliceNetworks = jsonUtil.getJsonValue(additionalPropJsonStr, "transportSliceNetworks") + if (isBlank(transportSliceNetworks)) { + msg = "Input transportSliceNetworks is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } else { + execution.setVariable("transportSliceNetworks", transportSliceNetworks) + } + logger.debug("transportSliceNetworks: " + transportSliceNetworks) + + String nsiInfo = jsonUtil.getJsonValue(additionalPropJsonStr, "nsiInfo") + if (isBlank(nsiInfo)) { + msg = "Input nsiInfo is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } else { + execution.setVariable("nsiInfo", nsiInfo) + } + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + msg = "Exception in preProcessRequest " + ex.getMessage() + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + logger.debug("Finish preProcessRequest") + } + + + void deleteServiceInstance(DelegateExecution execution) { + try { + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, + execution.getVariable("globalSubscriberId"), + execution.getVariable("subscriptionServiceType"), + execution.getVariable("serviceInstanceID")) + client.delete(uri) + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in DoDeallocateTnNssi.deleteServiceInstance. " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + } + + + void getExistingServiceInstance(DelegateExecution execution) { + String serviceInstanceId = execution.getVariable("serviceInstanceID") + + AAIResourcesClient resourceClient = getAAIClient() + AAIResourceUri ssServiceuri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, serviceInstanceId) + + try { + if (resourceClient.exists(ssServiceuri)) { + execution.setVariable("ssi_resourceLink", ssServiceuri.build().toString()) + org.onap.aai.domain.yang.ServiceInstance ss = + resourceClient.get(org.onap.aai.domain.yang.ServiceInstance.class, ssServiceuri) + org.onap.aai.domain.yang.SliceProfile sliceProfile = ss.getSliceProfiles().getSliceProfile().get(0) + execution.setVariable("sliceProfileId", sliceProfile.getProfileId()) + + org.onap.aai.domain.yang.AllottedResources ars = ss.getAllottedResources() + List<org.onap.aai.domain.yang.AllottedResource> arList = ars.getAllottedResource() + List<String> arIdList = new ArrayList<>() + for (org.onap.aai.domain.yang.AllottedResource ar : arList) { + String arId = ar.getId() + arIdList.add(arId) + } + execution.setVariable("arIdList", arIdList) + } else { + exceptionUtil.buildAndThrowWorkflowException(execution, 2500, "Service instance was not found in aai to " + + "associate allotted resource for service :" + serviceInstanceId) + } + } catch (BpmnError e) { + throw e; + } catch (Exception ex) { + String msg = "Exception in getServiceInstance. " + ex.getMessage() + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + + } + + public void updateTnNssiInAAI(DelegateExecution execution) { + getExistingServiceInstance(execution) + + updateServiceInstance(execution) + updateSliceProfile(execution) + updateAllottedResource(execution) + } + + void updateServiceInstance(DelegateExecution execution) { + String serviceRole = "TN" + String serviceType = execution.getVariable("subscriptionServiceType") + String sliceProfileStr = execution.getVariable("sliceProfile") + String ssInstanceId = execution.getVariable("sliceServiceInstanceId") + try { + org.onap.aai.domain.yang.ServiceInstance ss = new org.onap.aai.domain.yang.ServiceInstance() + ss.setServiceInstanceId(ssInstanceId) + String sliceInstanceName = execution.getVariable("sliceServiceInstanceName") + ss.setServiceInstanceName(sliceInstanceName) + ss.setServiceType(serviceType) + String serviceStatus = "modified" + ss.setOrchestrationStatus(serviceStatus) + String modelInvariantUuid = execution.getVariable("modelInvariantUuid") + String modelUuid = execution.getVariable("modelUuid") + ss.setModelInvariantId(modelInvariantUuid) + ss.setModelVersionId(modelUuid) + String serviceInstanceLocationid = tnNssmfUtils.getFirstPlmnIdFromSliceProfile(sliceProfileStr) + ss.setServiceInstanceLocationId(serviceInstanceLocationid) + String snssai = tnNssmfUtils.getFirstSnssaiFromSliceProfile(sliceProfileStr) + ss.setEnvironmentContext(snssai) + ss.setServiceRole(serviceRole) + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, execution.getVariable("globalSubscriberId"), execution.getVariable("subscriptionServiceType"), ssInstanceId) + client.update(uri, ss) + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in DoCreateTnNssiInstance.createServiceInstance. " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + } + + void updateSliceProfile(DelegateExecution execution) { + + String sliceserviceInstanceId = execution.getVariable("sliceServiceInstanceId") + String sliceProfileStr = execution.getVariable("sliceProfile") + String sliceProfileId = execution.getVariable("sliceProfileId") + SliceProfile sliceProfile = new SliceProfile(); + sliceProfile.setProfileId(sliceProfileId) + sliceProfile.setLatency(Integer.parseInt(jsonUtil.getJsonValue(sliceProfileStr, "latency"))) + sliceProfile.setResourceSharingLevel(jsonUtil.getJsonValue(sliceProfileStr, "resourceSharingLevel")) + sliceProfile.setSNssai(tnNssmfUtils.getFirstSnssaiFromSliceProfile(sliceProfileStr)) //TODO: should be list + + sliceProfile.setE2ELatency(Integer.parseInt(jsonUtil.getJsonValue(sliceProfileStr, "latency"))) + sliceProfile.setMaxBandwidth(Integer.parseInt(jsonUtil.getJsonValue(sliceProfileStr, "maxBandwidth"))) + + //TODO: new API + sliceProfile.setReliability(new Object()) + try { + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SLICE_PROFILE, execution.getVariable + ("globalSubscriberId"), + execution.getVariable("subscriptionServiceType"), sliceserviceInstanceId, sliceProfileId) + client.update(uri, sliceProfile) + + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in updateSliceProfile. " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + } + + void updateAllottedResource(DelegateExecution execution) { + String serviceInstanceId = execution.getVariable('serviceInstanceID') + + List<String> arIdList = execution.getVariable("arIdList") + try { + for (String arId : arIdList) { + AAIResourceUri arUri = AAIUriFactory.createResourceUri(AAIObjectType.ALLOTTED_RESOURCE, + execution.getVariable("globalSubscriberId"), execution.getVariable("subscriptionServiceType"), + serviceInstanceId, arId) + + getAAIClient().delete(arUri) + } + + List<String> networkStrList = jsonUtil.StringArrayToList(execution.getVariable("transportSliceNetworks")) + + for (String networkStr : networkStrList) { + String allottedResourceId = UUID.randomUUID().toString() + AAIResourceUri allottedResourceUri = AAIUriFactory.createResourceUri(AAIObjectType.ALLOTTED_RESOURCE, + execution.getVariable("globalSubscriberId"), execution.getVariable("subscriptionServiceType"), + execution.getVariable("sliceserviceInstanceId"), allottedResourceId) + execution.setVariable("allottedResourceUri", allottedResourceUri) + String modelInvariantId = execution.getVariable("modelInvariantUuid") + String modelVersionId = execution.getVariable("modelUuid") + + org.onap.aai.domain.yang.AllottedResource resource = new org.onap.aai.domain.yang.AllottedResource() + resource.setId(allottedResourceId) + resource.setType("TsciNetwork") + resource.setAllottedResourceName("network_" + execution.getVariable("sliceServiceInstanceName")) + resource.setModelInvariantId(modelInvariantId) + resource.setModelVersionId(modelVersionId) + getAAIClient().create(allottedResourceUri, resource) + + String linkArrayStr = jsonUtil.getJsonValue(networkStr, "connectionLinks") + createLogicalLinksForAllocatedResource(execution, linkArrayStr, serviceInstanceId, allottedResourceId) + } + + } catch (Exception ex) { + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, "Exception in createAaiAR " + ex.getMessage()) + } + } + + void createLogicalLinksForAllocatedResource(DelegateExecution execution, + String linkArrayStr, String serviceInstanceId, + String allottedResourceId) { + + try { + List<String> linkStrList = jsonUtil.StringArrayToList(linkArrayStr) + + for (String linkStr : linkStrList) { + String logicalLinkId = UUID.randomUUID().toString() + String epA = jsonUtil.getJsonValue(linkStr, "transportEndpointA") + String epB = jsonUtil.getJsonValue(linkStr, "transportEndpointB") + String modelInvariantId = execution.getVariable("modelInvariantUuid") + String modelVersionId = execution.getVariable("modelUuid") + + org.onap.aai.domain.yang.LogicalLink resource = new org.onap.aai.domain.yang.LogicalLink() + resource.setLinkId(logicalLinkId) + resource.setLinkName(epA) + resource.setLinkName2(epB) + resource.setModelInvariantId(modelInvariantId) + resource.setModelVersionId(modelVersionId) + + AAIResourceUri logicalLinkUri = AAIUriFactory.createResourceUri(AAIObjectType.LOGICAL_LINK, logicalLinkId) + getAAIClient().create(logicalLinkUri, resource) + } + } catch (Exception ex) { + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, + "Exception in createLogicalLinksForAllocatedResource" + ex.getMessage()) + } + } + + + void preprocessSdncModifyTnNssiRequest(DelegateExecution execution) { + def method = getClass().getSimpleName() + '.preprocessSdncModifyTnNssiRequest(' + + 'execution=' + execution.getId() + ')' + def isDebugLogEnabled = execution.getVariable('isDebugLogEnabled') + logger.trace('Entered ' + method) + + try { + String serviceInstanceId = execution.getVariable("serviceInstanceID") + + String sdncRequest = tnNssmfUtils.buildSDNCRequest(execution, serviceInstanceId, "modify") + + execution.setVariable("TNNSSMF_SDNCRequest", sdncRequest) + logger.debug("Outgoing SDNCRequest is: \n" + sdncRequest) + + } catch (Exception e) { + logger.debug("Exception Occured Processing preprocessSdncModifyTnNssiRequest. Exception is:\n" + e) + exceptionUtil.buildAndThrowWorkflowException(execution, 1002, "Error Occured during preProcessSDNCActivateRequest Method:\n" + e.getMessage()) + } + logger.trace("COMPLETED preprocessSdncModifyTnNssiRequest Process") + } + + + void validateSDNCResponse(DelegateExecution execution, String response, String method) { + tnNssmfUtils.validateSDNCResponse(execution, response, method) + } + + + void updateAAIOrchStatus(DelegateExecution execution) { + logger.debug("Start updateAAIOrchStatus") + String sliceServiceInstanceId = execution.getVariable("sliceServiceInstanceId") + String orchStatus = execution.getVariable("orchestrationStatus") + + try { + ServiceInstance si = new ServiceInstance() + si.setOrchestrationStatus(orchStatus) + AAIResourcesClient client = getAAIClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, sliceServiceInstanceId) + client.update(uri, si) + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in CreateSliceService.updateAAIOrchStatus " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + + logger.debug("Finish updateAAIOrchStatus") + } + + void prepareUpdateJobStatus(DelegateExecution execution, + String status, + String progress, + String statusDescription) { + String serviceId = execution.getVariable("serviceInstanceID") + String jobId = execution.getVariable("jobId") + String nsiId = execution.getVariable("nsiId") + + ResourceOperationStatus roStatus = new ResourceOperationStatus() + roStatus.setServiceId(serviceId) + roStatus.setOperationId(jobId) + roStatus.setResourceTemplateUUID(nsiId) + roStatus.setOperType("Modify") + roStatus.setProgress(progress) + roStatus.setStatus(status) + roStatus.setStatusDescription(statusDescription) + requestDBUtil.prepareUpdateResourceOperationStatus(execution, status) + } + +} + diff --git a/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/TnAllocateNssi.groovy b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/TnAllocateNssi.groovy new file mode 100644 index 0000000000..3367920064 --- /dev/null +++ b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/TnAllocateNssi.groovy @@ -0,0 +1,339 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP - SO + * ================================================================================ + * Copyright (C) 2020 Huawei Technologies Co., Ltd. All rights reserved. + * ================================================================================ + * 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. + * ============LICENSE_END========================================================= + */ + +package org.onap.so.bpmn.infrastructure.scripts + +import com.fasterxml.jackson.databind.ObjectMapper +import com.google.gson.JsonArray +import com.google.gson.JsonObject +import groovy.json.JsonSlurper +import org.camunda.bpm.engine.delegate.BpmnError +import org.camunda.bpm.engine.delegate.DelegateExecution +import org.onap.aai.domain.yang.ServiceInstance +import org.onap.aaiclient.client.aai.AAIObjectType +import org.onap.aaiclient.client.aai.AAIResourcesClient +import org.onap.aaiclient.client.aai.entities.uri.AAIResourceUri +import org.onap.aaiclient.client.aai.entities.uri.AAIUriFactory +import org.onap.so.bpmn.common.scripts.AbstractServiceTaskProcessor +import org.onap.so.bpmn.common.scripts.ExceptionUtil +import org.onap.so.bpmn.common.scripts.RequestDBUtil +import org.onap.so.bpmn.core.UrnPropertiesReader +import org.onap.so.bpmn.core.domain.ServiceDecomposition +import org.onap.so.bpmn.core.domain.ServiceProxy +import org.onap.so.bpmn.core.json.JsonUtils +import org.onap.so.db.request.beans.ResourceOperationStatus +import org.slf4j.Logger +import org.slf4j.LoggerFactory +import org.springframework.web.util.UriUtils + +import static org.apache.commons.lang3.StringUtils.isBlank + +class TnAllocateNssi extends AbstractServiceTaskProcessor { + String Prefix = "TNALLOC_" + + ExceptionUtil exceptionUtil = new ExceptionUtil() + JsonUtils jsonUtil = new JsonUtils() + RequestDBUtil requestDBUtil = new RequestDBUtil() + JsonSlurper jsonSlurper = new JsonSlurper() + ObjectMapper objectMapper = new ObjectMapper() + TnNssmfUtils tnNssmfUtils = new TnNssmfUtils() + private static final Logger logger = LoggerFactory.getLogger(TnAllocateNssi.class) + + void preProcessRequest(DelegateExecution execution) { + logger.debug("Start preProcessRequest") + execution.setVariable("prefix", Prefix) + String msg = "" + + try { + execution.setVariable("startTime", System.currentTimeMillis()) + + msg = tnNssmfUtils.getExecutionInputParams(execution) + logger.debug("Allocate TN NSSI input parameters: " + msg) + + tnNssmfUtils.setSdncCallbackUrl(execution, true) + logger.debug("SDNC Callback URL: " + execution.getVariable("sdncCallbackUrl")) + + String additionalPropJsonStr = execution.getVariable("sliceParams") + + String tnNssiId = execution.getVariable("serviceInstanceID") + if (isBlank(tnNssiId)) { + tnNssiId = UUID.randomUUID().toString() + } + + String operationId = UUID.randomUUID().toString() + execution.setVariable("operationId", operationId) + + logger.debug("Generate new TN NSSI ID:" + tnNssiId) + tnNssiId = UriUtils.encode(tnNssiId, "UTF-8") + execution.setVariable("sliceServiceInstanceId", tnNssiId) + + String sliceServiceInstanceName = execution.getVariable("servicename") + execution.setVariable("sliceServiceInstanceName", sliceServiceInstanceName) + + //additional properties + String sliceProfile = jsonUtil.getJsonValue(additionalPropJsonStr, "sliceProfile") + if (isBlank(sliceProfile)) { + msg = "Input sliceProfile is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } else { + execution.setVariable("sliceProfile", sliceProfile) + } + + String transportSliceNetworks = jsonUtil.getJsonValue(additionalPropJsonStr, "transportSliceNetworks") + if (isBlank(transportSliceNetworks)) { + msg = "Input transportSliceNetworks is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } else { + execution.setVariable("transportSliceNetworks", transportSliceNetworks) + } + logger.debug("transportSliceNetworks: " + transportSliceNetworks) + + String nsiInfoStr = jsonUtil.getJsonValue(additionalPropJsonStr, "nsiInfo") + if (isBlank(nsiInfoStr)) { + msg = "Input nsiInfo is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } else { + execution.setVariable("nsiInfo", nsiInfoStr) + } + + //nsiId is passed in from caller bpmn + //String nsiIdStr = jsonUtil.getJsonValue(nsiInfo, "nsiId") + //execution.setVariable("nsiId", nsiIdStr) + + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + msg = "Exception in preProcessRequest " + ex.getMessage() + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + logger.debug("Finish preProcessRequest") + } + + + void prepareDecomposeService(DelegateExecution execution) { + logger.debug("Start prepareDecomposeService") + String msg = "" + String modelUuid = execution.getVariable("modelUuid") + if (isBlank(modelUuid)) { + msg = "Input modelUuid is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } + + String modelInvariantUuid = execution.getVariable("modelInvariantUuid") + if (isBlank(modelInvariantUuid)) { + msg = "Input modelInvariantUuid is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } + + String serviceModelInfo = """{ + "modelInvariantUuid":"${modelInvariantUuid}", + "modelUuid":"${modelUuid}", + "modelVersion":"" + }""" + execution.setVariable("ssServiceModelInfo", serviceModelInfo) + + logger.debug("Finish prepareDecomposeService") + } + + void processDecomposition(DelegateExecution execution) { + logger.debug("Start processDecomposition") + + ServiceDecomposition tnNsstServiceDecomposition = execution.getVariable("tnNsstServiceDecomposition") + logger.debug("tnNsstServiceDecomposition : " + tnNsstServiceDecomposition.toString()) + //TN NSST decomposition + String tnModelVersion = tnNsstServiceDecomposition.getModelInfo().getModelVersion() + String tnModelName = tnNsstServiceDecomposition.getModelInfo().getModelName() + List<ServiceProxy> serviceProxyList = tnNsstServiceDecomposition.getServiceProxy() + List<String> nsstInfoList = new ArrayList<>() + for (ServiceProxy serviceProxy : serviceProxyList) { + String nsstModelUuid = serviceProxy.getModelInfo().getModelUuid() + String nsstModelInvariantUuid = serviceProxy.getModelInfo().getModelInvariantUuid() + String name = serviceProxy.getModelInfo().getModelName() + String nsstServiceModelInfo = """{ + "UUID":"${nsstModelUuid}", + "invariantUUID":"${nsstModelInvariantUuid}", + "name":"${name}" + }""" + nsstInfoList.add(nsstServiceModelInfo) + } + int currentIndex = 0 + int maxIndex = nsstInfoList.size() + if (maxIndex < 1) { + String msg = "Exception in TN NSST processDecomposition. There is no NSST associated with TN NSST " + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + execution.setVariable("tnNsstInfoList", nsstInfoList) + execution.setVariable("tnModelVersion", tnModelVersion) + execution.setVariable("tnModelName", tnModelName) + execution.setVariable("currentIndex", currentIndex) + execution.setVariable("maxIndex", maxIndex) + + logger.debug("End processDecomposition") + } + + void prepareOofSelection(DelegateExecution execution) { + logger.debug("Start prepareOofSelection") + + String urlString = UrnPropertiesReader.getVariable("mso.oof.endpoint", execution) + logger.debug("get NSSI option OOF Url: " + urlString) + //build oof request body + String requestId = execution.getVariable("msoRequestId") + String messageType = "NSISelectionResponse" + Map<String, Object> profileInfo = objectMapper.readValue(execution.getVariable("sliceProfile"), Map.class) + String modelUuid = execution.getVariable("modelUuid") + String modelInvariantUuid = execution.getVariable("modelInvariantUuid") + String modelName = execution.getVariable("tnModelName") + String timeout = UrnPropertiesReader.getVariable("mso.adapters.oof.timeout", execution); + List<String> nsstInfoList = objectMapper.readValue(execution.getVariable("nsstInfoList"), List.class) + JsonArray capabilitiesList = new JsonArray() + + execution.setVariable("nssiSelection_Url", "/api/oof/selection/nsi/v1") + execution.setVariable("nssiSelection_messageType", messageType) + execution.setVariable("nssiSelection_correlator", requestId) + execution.setVariable("nssiSelection_timeout", timeout) + String oofRequest = buildSelectTnNssiRequest(requestId, messageType, modelUuid, modelInvariantUuid, + modelName, profileInfo, nsstInfoList, capabilitiesList, false) + execution.setVariable("nssiSelection_oofRequest", oofRequest) + + logger.debug("Finish prepareOofSelection") + } + + String buildSelectTnNssiRequest(String requestId, String messageType, String UUID, String invariantUUID, + String name, Map<String, Object> profileInfo, + List<String> nsstInfoList, JsonArray capabilitiesList, Boolean preferReuse) { + + def transactionId = requestId + logger.debug("transactionId is: " + transactionId) + String correlator = requestId + String callbackUrl = UrnPropertiesReader.getVariable("mso.adapters.oof.callback.endpoint") + "/" + messageType + "/" + correlator + ObjectMapper objectMapper = new ObjectMapper() + String profileJson = objectMapper.writeValueAsString(profileInfo) + String nsstInfoListString = objectMapper.writeValueAsString(nsstInfoList) + //Prepare requestInfo object + JsonObject requestInfo = new JsonObject() + requestInfo.addProperty("transactionId", transactionId) + requestInfo.addProperty("requestId", requestId) + requestInfo.addProperty("callbackUrl", callbackUrl) + requestInfo.addProperty("sourceId", "SO") + requestInfo.addProperty("timeout", 600) + requestInfo.addProperty("numSolutions", 1) + + //Prepare serviceInfo object + JsonObject ranNsstInfo = new JsonObject() + ranNsstInfo.addProperty("UUID", UUID) + ranNsstInfo.addProperty("invariantUUID", invariantUUID) + ranNsstInfo.addProperty("name", name) + + JsonObject json = new JsonObject() + json.add("requestInfo", requestInfo) + json.add("NSTInfo", ranNsstInfo) + json.addProperty("serviceProfile", profileJson) + json.addProperty("NSSTInfo", nsstInfoListString) + json.add("subnetCapabilities", capabilitiesList) + json.addProperty("preferReuse", preferReuse) + + return json.toString() + } + + void processOofSelection(DelegateExecution execution) { + logger.debug(Prefix + "processOofSelection method start") + String oofResponse = execution.getVariable("nssiSelection_asyncCallbackResponse") + String requestStatus = jsonUtil.getJsonValue(oofResponse, "requestStatus") + if (requestStatus.equals("completed")) { + List<String> solution = jsonUtil.StringArrayToList(jsonUtil.getJsonValue(oofResponse, "solutions")) + boolean existingNSI = jsonUtil.getJsonValue(solution.get(0), "existingNSI") + if (existingNSI) { + def sharedNSISolution = jsonUtil.getJsonValue(solution.get(0), "sharedNSISolution") + execution.setVariable("sharedTnNssiSolution", sharedNSISolution) + logger.debug("sharedTnNssiSolution from OOF " + sharedNSISolution) + String tnServiceInstanceId = jsonUtil.getJsonValue(solution.get(0), "sharedNSISolution.NSIId") + execution.setVariable("tnServiceInstanceId", tnServiceInstanceId) + org.onap.so.bpmn.core.domain.ServiceInstance serviceInstance = new org.onap.so.bpmn.core.domain.ServiceInstance(); + serviceInstance.setInstanceId(tnServiceInstanceId); + ServiceDecomposition serviceDecomposition = execution.getVariable("tnNsstServiceDecomposition") + serviceDecomposition.setServiceInstance(serviceInstance); + execution.setVariable("tnNsstServiceDecomposition", serviceDecomposition) + execution.setVariable("isOofTnNssiSelected", true) + } else { + def sliceProfiles = jsonUtil.getJsonValue(solution.get(0), "newNSISolution.sliceProfiles") + execution.setVariable("tnConstituentSliceProfiles", sliceProfiles) + execution.setVariable("isOofTnNssiSelected", false) + logger.debug("tnConstituentSliceProfiles list from OOF " + sliceProfiles) + } + } else { + String statusMessage = jsonUtil.getJsonValue(oofResponse, "statusMessage") + logger.error("received failed status from oof " + statusMessage) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, "Received a failed Async Response from OOF : " + statusMessage) + } + + logger.debug(Prefix + "processOofSelection method finished") + } + + void updateAAIOrchStatus(DelegateExecution execution) { + logger.debug("Start updateAAIOrchStatus") + String sliceServiceInstanceId = execution.getVariable("sliceServiceInstanceId") + String orchStatus = execution.getVariable("orchestrationStatus") + + try { + ServiceInstance si = new ServiceInstance() + si.setOrchestrationStatus(orchStatus) + AAIResourcesClient client = new AAIResourcesClient() + AAIResourceUri uri = AAIUriFactory.createResourceUri(AAIObjectType.SERVICE_INSTANCE, sliceServiceInstanceId) + client.update(uri, si) + } catch (BpmnError e) { + throw e + } catch (Exception ex) { + String msg = "Exception in CreateSliceService.updateAAIOrchStatus " + ex.getMessage() + logger.info(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 7000, msg) + } + + logger.debug("Finish updateAAIOrchStatus") + } + + + void prepareUpdateJobStatus(DelegateExecution execution, + String status, + String progress, + String statusDescription) { + String serviceId = execution.getVariable("sliceServiceInstanceId") + String jobId = execution.getVariable("jobId") + String nsiId = execution.getVariable("nsiId") + + ResourceOperationStatus roStatus = new ResourceOperationStatus() + roStatus.setServiceId(serviceId) + roStatus.setOperationId(jobId) + roStatus.setResourceTemplateUUID(nsiId) + roStatus.setOperType("Allocate") + roStatus.setProgress(progress) + roStatus.setStatus(status) + roStatus.setStatusDescription(statusDescription) + requestDBUtil.prepareUpdateResourceOperationStatus(execution, status) + } + +} + diff --git a/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/TnNssmfUtils.groovy b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/TnNssmfUtils.groovy new file mode 100644 index 0000000000..a1b883c34e --- /dev/null +++ b/bpmn/so-bpmn-infrastructure-common/src/main/groovy/org/onap/so/bpmn/infrastructure/scripts/TnNssmfUtils.groovy @@ -0,0 +1,244 @@ +/*- + * ============LICENSE_START======================================================= + * ONAP - SO + * ================================================================================ + * Copyright (C) 2020 Huawei Technologies Co., Ltd. All rights reserved. + * ================================================================================ + * 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. + * ============LICENSE_END========================================================= + */ + +package org.onap.so.bpmn.infrastructure.scripts + + +import org.camunda.bpm.engine.delegate.DelegateExecution +import org.onap.so.bpmn.common.scripts.ExceptionUtil +import org.onap.so.bpmn.common.scripts.MsoUtils +import org.onap.so.bpmn.common.scripts.SDNCAdapterUtils +import org.onap.so.bpmn.core.RollbackData +import org.onap.so.bpmn.core.UrnPropertiesReader +import org.onap.so.bpmn.core.WorkflowException +import org.onap.so.bpmn.core.json.JsonUtils +import org.slf4j.Logger +import org.slf4j.LoggerFactory + +import static org.apache.commons.lang3.StringUtils.isBlank + +class TnNssmfUtils { + private static final Logger logger = LoggerFactory.getLogger(TnNssmfUtils.class); + + + ExceptionUtil exceptionUtil = new ExceptionUtil() + JsonUtils jsonUtil = new JsonUtils() + MsoUtils msoUtils = new MsoUtils() + SDNCAdapterUtils sdncAdapterUtils = new SDNCAdapterUtils() + + TnNssmfUtils() { + } + + + void setSdncCallbackUrl(DelegateExecution execution, boolean exceptionOnErr) { + setSdncCallbackUrl(execution, "sdncCallbackUrl", exceptionOnErr) + } + + void setSdncCallbackUrl(DelegateExecution execution, String variableName, boolean exceptionOnErr) { + String sdncCallbackUrl = UrnPropertiesReader.getVariable('mso.workflow.sdncadapter.callback', execution) + + if (isBlank(sdncCallbackUrl) && exceptionOnErr) { + String msg = "mso.workflow.sdncadapter.callback is null" + logger.debug(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } else { + execution.setVariable(variableName, sdncCallbackUrl) + } + } + + String buildSDNCRequest(DelegateExecution execution, String svcInstId, String action) { + + String uuid = execution.getVariable('testReqId') // for junits + if (uuid == null) { + uuid = execution.getVariable("msoRequestId") + "-" + System.currentTimeMillis() + } + + def callbackURL = execution.getVariable("sdncCallbackUrl") + def requestId = execution.getVariable("msoRequestId") + def serviceId = execution.getVariable("sliceServiceInstanceId") + def vnfType = execution.getVariable("serviceType") + def vnfName = execution.getVariable("sliceServiceInstanceName") + def tenantId = execution.getVariable("sliceServiceInstanceId") + def source = execution.getVariable("sliceServiceInstanceId") + def vnfId = execution.getVariable("sliceServiceInstanceId") + def cloudSiteId = execution.getVariable("sliceServiceInstanceId") + def serviceModelInfo = execution.getVariable("serviceModelInfo") + def vnfModelInfo = execution.getVariable("serviceModelInfo") + def globalSubscriberId = execution.getVariable("globalSubscriberId") + + String vnfNameString = """<vnf-name>${MsoUtils.xmlEscape(vnfName)}</vnf-name>""" + String serviceEcompModelInformation = sdncAdapterUtils.modelInfoToEcompModelInformation(serviceModelInfo) + String vnfEcompModelInformation = sdncAdapterUtils.modelInfoToEcompModelInformation(vnfModelInfo) + + String sdncVNFParamsXml = "" + + if (execution.getVariable("vnfParamsExistFlag") == true) { + sdncVNFParamsXml = buildSDNCParamsXml(execution) + } else { + sdncVNFParamsXml = "" + } + + String sdncRequest = + """<sdncadapterworkflow:SDNCAdapterWorkflowRequest xmlns:ns5="http://org.onap/so/request/types/v1" + xmlns:sdncadapterworkflow="http://org.onap/so/workflow/schema/v1" + xmlns:sdncadapter="http://org.onap/workflow/sdnc/adapter/schema/v1"> + <sdncadapter:RequestHeader> + <sdncadapter:RequestId>${MsoUtils.xmlEscape(uuid)}</sdncadapter:RequestId> + <sdncadapter:SvcInstanceId>${MsoUtils.xmlEscape(svcInstId)}</sdncadapter:SvcInstanceId> + <sdncadapter:SvcAction>${MsoUtils.xmlEscape(action)}</sdncadapter:SvcAction> + <sdncadapter:SvcOperation>vnf-topology-operation</sdncadapter:SvcOperation> + <sdncadapter:CallbackUrl>${MsoUtils.xmlEscape(callbackURL)}</sdncadapter:CallbackUrl> + <sdncadapter:MsoAction>generic-resource</sdncadapter:MsoAction> + </sdncadapter:RequestHeader> + <sdncadapterworkflow:SDNCRequestData> + <request-information> + <request-id>${MsoUtils.xmlEscape(requestId)}</request-id> + <request-action>AllocateTnNssi</request-action> + <source>${MsoUtils.xmlEscape(source)}</source> + <notification-url/> + <order-number/> + <order-version/> + </request-information> + <service-information> + <service-id>${MsoUtils.xmlEscape(serviceId)}</service-id> + <subscription-service-type>${MsoUtils.xmlEscape(serviceId)}</subscription-service-type> + ${serviceEcompModelInformation} + <service-instance-id>${MsoUtils.xmlEscape(svcInstId)}</service-instance-id> + <global-customer-id>${MsoUtils.xmlEscape(globalSubscriberId)}</global-customer-id> + </service-information> + <vnf-information> + <vnf-id>${MsoUtils.xmlEscape(vnfId)}</vnf-id> + <vnf-type>${MsoUtils.xmlEscape(vnfType)}</vnf-type> + ${vnfEcompModelInformation} + </vnf-information> + <vnf-request-input> + ${vnfNameString} + <tenant>${MsoUtils.xmlEscape(tenantId)}</tenant> + <aic-cloud-region>${MsoUtils.xmlEscape(cloudSiteId)}</aic-cloud-region> + ${sdncVNFParamsXml} + </vnf-request-input> + </sdncadapterworkflow:SDNCRequestData> + </sdncadapterworkflow:SDNCAdapterWorkflowRequest>""" + + logger.debug("sdncRequest: " + sdncRequest) + return sdncRequest + } + + String buildSDNCParamsXml(DelegateExecution execution) { + String params = "" + StringBuilder sb = new StringBuilder() + Map<String, String> paramsMap = execution.getVariable("TNNSSMF_vnfParamsMap") + + for (Map.Entry<String, String> entry : paramsMap.entrySet()) { + String paramsXml + String key = entry.getKey(); + String value = entry.getValue() + paramsXml = """<${key}>$value</$key>""" + params = sb.append(paramsXml) + } + return params + } + + void validateSDNCResponse(DelegateExecution execution, String response, String method) { + validateSDNCResponse(execution, response, method, true) + } + + void validateSDNCResponse(DelegateExecution execution, String response, String method, boolean exceptionOnErr) { + logger.debug("STARTED ValidateSDNCResponse Process") + + String msg + + String prefix = execution.setVariable("prefix") + if (isBlank(prefix)) { + if (exceptionOnErr) { + msg = "validateSDNCResponse: prefix is null" + logger.error(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } + return + } + + WorkflowException workflowException = execution.getVariable("WorkflowException") + boolean successIndicator = execution.getVariable("SDNCA_SuccessIndicator") + + logger.debug("workflowException: " + workflowException) + + sdncAdapterUtils.validateSDNCResponse(execution, response, workflowException, successIndicator) + + String sdncResponse = response + if (execution.getVariable(prefix + 'sdncResponseSuccess') == true) { + logger.debug("Received a Good Response from SDNC Adapter for " + method + " SDNC Call. Response is: \n" + sdncResponse) + RollbackData rollbackData = execution.getVariable("rollbackData") + + if (method.equals("allocate")) { + rollbackData.put("VNFMODULE", "rollbackSDNCRequestAllocate", "true") + } else if (method.equals("deallocate")) { + rollbackData.put("VNFMODULE", "rollbackSDNCRequestDeallocate", "true") + } else if (method.equals("activate")) { + rollbackData.put("VNFMODULE", "rollbackSDNCRequestActivate", "true") + } else if (method.equals("deactivate")) { + rollbackData.put("VNFMODULE", "rollbackSDNCRequestDeactivate", "true") + } else if (method.equals("modify")) { + rollbackData.put("VNFMODULE", "rollbackSDNCRequestModify", "true") + } + execution.setVariable("rollbackData", rollbackData) + } else { + if (exceptionOnErr) { + msg = "validateSDNCResponse: bad Response from SDNC Adapter for " + method + " SDNC Call." + logger.error(msg) + exceptionUtil.buildAndThrowWorkflowException(execution, 500, msg) + } + } + + logger.debug("COMPLETED ValidateSDNCResponse Process") + } + + String getExecutionInputParams(DelegateExecution execution) { + String res = "msoRequestId=" + execution.getVariable("msoRequestId") + + ", modelInvariantUuid=" + execution.getVariable("modelInvariantUuid") + + ", modelUuid=" + execution.getVariable("modelUuid") + + ", serviceInstanceID=" + execution.getVariable("serviceInstanceID") + + ", operationType=" + execution.getVariable("operationType") + + ", globalSubscriberId=" + execution.getVariable("globalSubscriberId") + + ", dummyServiceId=" + execution.getVariable("dummyServiceId") + + ", nsiId=" + execution.getVariable("nsiId") + + ", networkType=" + execution.getVariable("networkType") + + ", subscriptionServiceType=" + execution.getVariable("subscriptionServiceType") + + ", jobId=" + execution.getVariable("jobId") + + ", sliceParams=" + execution.getVariable("sliceParams") + + ", servicename=" + execution.getVariable("servicename") + + return res + } + + String getFirstSnssaiFromSliceProfile(String sliceProfileStr) { + String snssaiListStr = jsonUtil.getJsonValue(sliceProfileStr, "snssaiList") + String snssai = jsonUtil.StringArrayToList(snssaiListStr).get(0) + + return snssai + } + + String getFirstPlmnIdFromSliceProfile(String sliceProfileStr) { + String plmnListStr = jsonUtil.getJsonValue(sliceProfileStr, "plmnIdList") + String res = jsonUtil.StringArrayToList(plmnListStr).get(0) + + return res + } +} |