Refactor gvnfmadapter inst and terminate 15/14515/1
authorying.yunlong <ying.yunlong@zte.com.cn>
Fri, 22 Sep 2017 07:47:34 +0000 (15:47 +0800)
committerying.yunlong <ying.yunlong@zte.com.cn>
Fri, 22 Sep 2017 07:47:34 +0000 (15:47 +0800)
Change-Id: I8ca6399d42f7cc2747d3cb50e45e30ed5a7910e8
Issue-ID: VFC-418
Signed-off-by: ying.yunlong <ying.yunlong@zte.com.cn>
gvnfmadapter/driver/interfaces/tests.py
gvnfmadapter/driver/interfaces/views.py
gvnfmadapter/driver/pub/exceptions.py [new file with mode: 0644]

index 4874354..e0c18c6 100644 (file)
@@ -49,7 +49,7 @@ class InterfacesTest(TestCase):
         }
         vnflcm_info = {
             "vnfInstanceId":"8",
-            "vnfLcOpId":"NF-CREATE-8-b384535c-9f45-11e6-8749-fa163e91c2f9"
+            "vnfLcOpId":"NF-INST-8-6ffa8083-6705-49b3-ae54-cbd6265fbe7a"
         }
 
         r1 = [0, json.JSONEncoder().encode(vnfm_info), "200"]
@@ -75,9 +75,11 @@ class InterfacesTest(TestCase):
         response = self.client.post("/api/gvnfmdriver/v1/1/vnfs",
                                     data=json.dumps(req_data), content_type="application/json")
         self.assertEqual(status.HTTP_201_CREATED, response.status_code)
-        print job_info
-        print response.data
-        self.assertEqual(job_info, response.data)
+        expect_data = {
+            "vnfInstanceId": "8",
+            "jobId": "NF-INST-8-6ffa8083-6705-49b3-ae54-cbd6265fbe7a"
+        }
+        self.assertEqual(expect_data, response.data)
 
     @mock.patch.object(restcall, 'call_req')
     def test_terminate_vnf(self, mock_call_req):
@@ -96,7 +98,26 @@ class InterfacesTest(TestCase):
             "createTime": "2016-07-06 15:33:18"
         }
         job_info = {"vnfInstanceId": "1", "vnfLcOpId": "1"}
-        job_status_info = {"VnfLcOpResponseDescriptor":{"progress":"100"}}
+        # job_status_info = {"responseDescriptor":{"progress":"100"}}
+        job_status_info = {
+            "jobId": "1",
+            "responseDescriptor": {
+                "status": "",
+                "progress": 100,
+                "statusDescription": "",
+                "errorCode": "",
+                "responseId": "2",
+                "responseHistoryList": [
+                    {
+                        "status": "",
+                        "progress": "",
+                        "statusDescription": "",
+                        "errorCode": "",
+                        "responseId": ""
+                    }
+                ]
+            }
+        }
         r1 = [0, json.JSONEncoder().encode(vnfm_info), "200"]
         r2 = [0, json.JSONEncoder().encode(job_info), "200"]
         job_ret = [0,  json.JSONEncoder().encode(job_status_info), "200"]
@@ -105,92 +126,92 @@ class InterfacesTest(TestCase):
         self.assertEqual(status.HTTP_204_NO_CONTENT, response.status_code)
         self.assertEqual(job_info, response.data)
 
-    @mock.patch.object(restcall, 'call_req')
-    def test_query_vnf(self, mock_call_req):
-        vnfm_info = {
-            "vnfmId": "19ecbb3a-3242-4fa3-9926-8dfb7ddc29ee",
-            "name": "g_vnfm",
-            "type": "vnfm",
-            "vimId": "",
-            "vendor": "ZTE",
-            "version": "v1.0",
-            "description": "vnfm",
-            "certificateUrl": "",
-            "url": "http://10.74.44.11",
-            "userName": "admin",
-            "password": "admin",
-            "createTime": "2016-07-06 15:33:18"
-        }
-        job_info = {"ResponseInfo": {"vnfInstanceId":"88","instantiationState":"INSTANTIATED","vnfSoftwareVersion":"v1.2.3"}}
-        r1 = [0, json.JSONEncoder().encode(vnfm_info), "200"]
-        r2 = [0, json.JSONEncoder().encode(job_info), "200"]
-        mock_call_req.side_effect = [r1, r2]
-        response = self.client.get("/api/gvnfmdriver/v1/19ecbb3a-3242-4fa3-9926-8dfb7ddc29ee/vnfs/88")
-        self.assertEqual(status.HTTP_200_OK, response.status_code)
-        expect_resp_data = {"vnfInfo": {"vnfInstanceId": "88", "vnfStatus": "ACTIVE","version":"v1.2.3"}}
-        self.assertEqual(expect_resp_data, response.data)
+    @mock.patch.object(restcall, 'call_req')
+    def test_query_vnf(self, mock_call_req):
+        vnfm_info = {
+            "vnfmId": "19ecbb3a-3242-4fa3-9926-8dfb7ddc29ee",
+            "name": "g_vnfm",
+            "type": "vnfm",
+            "vimId": "",
+            "vendor": "ZTE",
+            "version": "v1.0",
+            "description": "vnfm",
+            "certificateUrl": "",
+            "url": "http://10.74.44.11",
+            "userName": "admin",
+            "password": "admin",
+            "createTime": "2016-07-06 15:33:18"
+        }
+        job_info = {"ResponseInfo": {"vnfInstanceId":"88","instantiationState":"INSTANTIATED","vnfSoftwareVersion":"v1.2.3"}}
+        r1 = [0, json.JSONEncoder().encode(vnfm_info), "200"]
+        r2 = [0, json.JSONEncoder().encode(job_info), "200"]
+        mock_call_req.side_effect = [r1, r2]
+        response = self.client.get("/api/gvnfmdriver/v1/19ecbb3a-3242-4fa3-9926-8dfb7ddc29ee/vnfs/88")
+        self.assertEqual(status.HTTP_200_OK, response.status_code)
+        expect_resp_data = {"vnfInfo": {"vnfInstanceId": "88", "vnfStatus": "ACTIVE","version":"v1.2.3"}}
+        self.assertEqual(expect_resp_data, response.data)
 
-    @mock.patch.object(restcall, 'call_req')
-    def test_operation_status(self, mock_call_req):
-        vnfm_info = {
-            'userName': 'admin',
-             'vendor': 'ZTE',
-             'name': 'ZTE_VNFM_237_62',
-             'vimId': '516cee95-e8ca-4d26-9268-38e343c2e31e',
-             'url': 'http://192.168.237.165:2324',
-             'certificateUrl': '',
-             'version': 'V1.0',
-             'vnfmId': 'b0797c9b-3da9-459c-b25c-3813e9d8fd70',
-             'password': 'admin',
-             'type': 'ztevmanagerdriver',
-             'createTime': '2016-10-31 11:08:39',
-             'description': ''
-        }
-        expected_body = {
-            "jobId": "NF-CREATE-11-ec6c2f2a-9f48-11e6-9405-fa163e91c2f9",
-            "responseDescriptor":{
-                "responseId": 3,
-                "progress": 40,
-                "status": "PROCESSING",
-                "statusDescription": "OMC VMs are decommissioned in VIM",
-                "errorCode": "null",
-                "responseHistoryList": [
-                     {
-                         "status": "error",
-                          "progress": 255,
-                          "errorcode": "",
-                          "responseid": 20,
-                          "statusdescription": "'JsonParser' object has no attribute 'parser_info'"
-                     }
-                ]
-            }
-        }
-        resp_body = {
-            "ResponseInfo": {
-                "vnfLcOpId":"NF-CREATE-11-ec6c2f2a-9f48-11e6-9405-fa163e91c2f9",
-                "responseDescriptor":{
-                    "responseId": 3,
-                    "progress": 40,
-                    "lcmOperationStatus": "PROCESSING",
-                    "statusDescription": "OMC VMs are decommissioned in VIM",
-                    "errorCode": "null",
-                    "responseHistoryList": [
-                             {"status": "error",
-                              "progress": 255,
-                              "errorcode": "",
-                              "responseid": 20,
-                              "statusdescription": "'JsonParser' object has no attribute 'parser_info'"}]
-                }
-            }
-        }
-        r1 = [0, json.JSONEncoder().encode(vnfm_info), '200']
-        r2 = [0, json.JSONEncoder().encode(resp_body), '200']
-        mock_call_req.side_effect = [r1, r2]
-        response = self.client.get("/api/gvnfmdriver/v1/{vnfmid}/jobs/{jobid}?responseId={responseId}".
-            format(vnfmid=vnfm_info["vnfmId"],jobid=resp_body["ResponseInfo"]["vnfLcOpId"],
-                   responseId=resp_body["ResponseInfo"]["responseDescriptor"]["responseId"]))
-        self.assertEqual(status.HTTP_200_OK, response.status_code)
-        self.assertDictEqual(expected_body, response.data)
+    @mock.patch.object(restcall, 'call_req')
+    def test_operation_status(self, mock_call_req):
+        vnfm_info = {
+            'userName': 'admin',
+             'vendor': 'ZTE',
+             'name': 'ZTE_VNFM_237_62',
+             'vimId': '516cee95-e8ca-4d26-9268-38e343c2e31e',
+             'url': 'http://192.168.237.165:2324',
+             'certificateUrl': '',
+             'version': 'V1.0',
+             'vnfmId': 'b0797c9b-3da9-459c-b25c-3813e9d8fd70',
+             'password': 'admin',
+             'type': 'ztevmanagerdriver',
+             'createTime': '2016-10-31 11:08:39',
+             'description': ''
+        }
+        expected_body = {
+            "jobId": "NF-CREATE-11-ec6c2f2a-9f48-11e6-9405-fa163e91c2f9",
+            "responseDescriptor":{
+                "responseId": 3,
+                "progress": 40,
+                "status": "PROCESSING",
+                "statusDescription": "OMC VMs are decommissioned in VIM",
+                "errorCode": "null",
+                "responseHistoryList": [
+                     {
+                         "status": "error",
+                          "progress": 255,
+                          "errorcode": "",
+                          "responseid": 20,
+                          "statusdescription": "'JsonParser' object has no attribute 'parser_info'"
+                     }
+                ]
+            }
+        }
+        resp_body = {
+            "ResponseInfo": {
+                "vnfLcOpId":"NF-CREATE-11-ec6c2f2a-9f48-11e6-9405-fa163e91c2f9",
+                "responseDescriptor":{
+                    "responseId": 3,
+                    "progress": 40,
+                    "lcmOperationStatus": "PROCESSING",
+                    "statusDescription": "OMC VMs are decommissioned in VIM",
+                    "errorCode": "null",
+                    "responseHistoryList": [
+                             {"status": "error",
+                              "progress": 255,
+                              "errorcode": "",
+                              "responseid": 20,
+                              "statusdescription": "'JsonParser' object has no attribute 'parser_info'"}]
+                }
+            }
+        }
+        r1 = [0, json.JSONEncoder().encode(vnfm_info), '200']
+        r2 = [0, json.JSONEncoder().encode(resp_body), '200']
+        mock_call_req.side_effect = [r1, r2]
+        response = self.client.get("/api/gvnfmdriver/v1/{vnfmid}/jobs/{jobid}?responseId={responseId}".
+            format(vnfmid=vnfm_info["vnfmId"],jobid=resp_body["ResponseInfo"]["vnfLcOpId"],
+                   responseId=resp_body["ResponseInfo"]["responseDescriptor"]["responseId"]))
+        self.assertEqual(status.HTTP_200_OK, response.status_code)
+        self.assertDictEqual(expected_body, response.data)
 
     @mock.patch.object(restcall, 'call_req')
     def test_grantvnf(self, mock_call_req):
index b7da997..f0d5213 100644 (file)
@@ -16,11 +16,13 @@ import inspect
 import json
 import logging
 import time
+import traceback
 
 from rest_framework import status
 from rest_framework.decorators import api_view
 from rest_framework.response import Response
 
+from driver.pub.exceptions import GvnfmDriverException
 from driver.pub.utils import restcall
 from driver.pub.utils.restcall import req_by_msb
 
@@ -30,57 +32,78 @@ logger = logging.getLogger(__name__)
 @api_view(http_method_names=['POST'])
 def instantiate_vnf(request, *args, **kwargs):
     try:
+        logger.debug("instantiate_vnf--post::> %s" % request.data)
+        logger.info("Create vnf begin!")
         input_data = {}
         input_data["vnfdId"] = ignorcase_get(request.data, "vnfDescriptorId")
         input_data["vnfInstanceName"] = ignorcase_get(request.data, "vnfInstanceName")
         input_data["vnfInstanceDescription"] = ignorcase_get(request.data, "vnfInstanceDescription")
         vnfm_id = ignorcase_get(kwargs, "vnfmid")
-        ret, resp = do_createvnf(request, input_data, vnfm_id)
-        if ret != 0:
-            return resp
-        logger.info("[%s]resp_data=%s", fun_name(), resp)
+        logger.debug("do_createvnf: request data=[%s],input_data=[%s],vnfm_id=[%s]", request.data, input_data, vnfm_id)
+        resp = do_createvnf(vnfm_id, input_data)
+        logger.debug("do_createvnf: response data=[%s]", resp)
+        logger.debug("Create vnf end!")
+
+        logger.debug("Instantiate vnf start!")
         vnfInstanceId = resp["vnfInstanceId"]
-        logger.info("[%s]vnfInstanceId=%s", fun_name(), vnfInstanceId)
         input_data = {}
         input_data["flavourId"] = ignorcase_get(request.data, "flavourId")
         input_data["extVirtualLinks"] = ignorcase_get(request.data, "extVirtualLink")
-        input_data["additionalParams"] = ignorcase_get(request.data, "additionalParams")
-        input_data["flavourId"] = ignorcase_get(request.data, "flavourId")
-        ret, resp = do_instvnf(vnfInstanceId, request, input_data, vnfm_id)
-        if ret != 0:
-            return resp
-        resp_data = {"jobId":"", "vnfInstanceId":""}
-        resp_data["vnfInstanceId"] = vnfInstanceId
-        resp_data["jobId"] = resp["vnfLcOpId"]
-    except Exception as e:
-        logger.error("Error occurred when instantiating VNF")
-        raise e
-    return Response(data=resp_data, status=status.HTTP_201_CREATED)
+        input_data["additionalParams"] = ignorcase_get(request.data, "additionalParam")
+        logger.debug("do_instvnf: vnfInstanceId=[%s],request data=[%s],input_data=[%s],vnfm_id=[%s]",
+                     vnfInstanceId, request.data, input_data, vnfm_id)
+        resp = do_instvnf(vnfInstanceId, vnfm_id, input_data)
+        logger.debug("do_instvnf: response data=[%s]", resp)
+        resp_data = {
+            "vnfInstanceId": vnfInstanceId,
+            "jobId": ignorcase_get(resp, "vnfLcOpId")
+        }
+        logger.debug("Instantiate vnf end!")
+        return Response(data=resp_data, status=status.HTTP_201_CREATED)
+    except GvnfmDriverException as e:
+        logger.error('instantiate vnf failed, detail message: %s' % e.message)
+        return Response(data={'error': e.message}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
+    except:
+        logger.error(traceback.format_exc())
+        return Response(data={'error': 'unexpected exception'}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
 
 
 @api_view(http_method_names=['POST'])
 def terminate_vnf(request, *args, **kwargs):
+    logger.debug("terminate_vnf--post::> %s" % request.data)
+    logger.info("Terminate vnf begin!")
     vnfm_id = ignorcase_get(kwargs, "vnfmid")
     vnfInstanceId = ignorcase_get(kwargs, "vnfInstanceId")
     try:
         input_data = {}
         input_data["terminationType"] = ignorcase_get(request.data, "terminationType")
         input_data["gracefulTerminationTimeout"] = ignorcase_get(request.data, "gracefulTerminationTimeout")
-        ret, resp = do_terminatevnf(request, input_data, vnfm_id, vnfInstanceId)
-        if ret != 0:
-            return resp
+        logger.debug("do_terminatevnf: vnfm_id=[%s],vnfInstanceId=[%s],input_data=[%s]",
+                     vnfm_id, vnfInstanceId, input_data)
+        resp = do_terminatevnf(vnfm_id, vnfInstanceId, input_data)
+        logger.debug("terminate_vnf: response data=[%s]", resp)
+
         jobId = ignorcase_get(resp, "vnfLcOpId")
         gracefulTerminationTimeout = ignorcase_get(request.data, "gracefulTerminationTimeout")
-        ret, response = wait4job(vnfm_id,jobId,gracefulTerminationTimeout)
-        if ret != 0:
-            return response
-        ret, resp = do_deletevnf(request, vnfm_id, vnfInstanceId)
-        if ret != 0:
-            return resp
-    except Exception as e:
-        logger.error("Error occurred when terminating VNF")
-        raise e
-    return Response(data=resp, status=status.HTTP_204_NO_CONTENT)
+        logger.debug("wait4job: vnfm_id=[%s],jobId=[%s],gracefulTerminationTimeout=[%s]",
+                     vnfm_id, jobId, gracefulTerminationTimeout)
+        resp = wait4job(vnfm_id, jobId, gracefulTerminationTimeout)
+        logger.info("[wait4job] response=[%s]", resp)
+
+        logger.debug("Delete vnf start!")
+        logger.debug("do_deletevnf: vnfm_id=[%s],vnfInstanceId=[%s],request data=[%s]",
+                     vnfm_id, vnfInstanceId, request.data)
+        resp = do_deletevnf(vnfm_id, vnfInstanceId, request.data)
+        logger.debug("do_deletevnf: response data=[%s]", resp)
+        logger.debug("Delete vnf end!")
+
+        return Response(data=resp, status=status.HTTP_204_NO_CONTENT)
+    except GvnfmDriverException as e:
+        logger.error('Terminate vnf failed, detail message: %s' % e.message)
+        return Response(data={'error': e.message}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
+    except:
+        logger.error(traceback.format_exc())
+        return Response(data={'error': 'unexpected exception'}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
 
 
 @api_view(http_method_names=['GET'])
@@ -220,8 +243,9 @@ def mapping_conv(keyword_map, rest_return):
                 resp_data[param] = ignorcase_get(rest_return, param)
     return resp_data
 
+
 def fun_name():
-    return "=================%s==================" % inspect.stack()[1][3]
+    return "=========%s=========" % inspect.stack()[1][3]
 
 
 def ignorcase_get(args, key):
@@ -240,105 +264,126 @@ def ignorcase_get(args, key):
 def get_vnfminfo_from_nslcm(vnfm_id):
     ret = req_by_msb("api/aai-esr-server/v1/vnfms/%s" % vnfm_id, "GET")
     if ret[0] != 0:
-        return 255, Response(data={'error': ret[1]}, status=ret[2])
-    vnfm_info = json.JSONDecoder().decode(ret[1])
-    logger.debug("[%s] vnfm_info=%s", fun_name(), vnfm_info)
-    return 0, vnfm_info
-
-
-def wait4job(vnfm_id,jobId,gracefulTerminationTimeout):
-    begin_time = time.time()
-    try:
-        ret, vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
-        if ret != 0:
-            return 255, Response(data={"error":"Fail to get VNFM!"}, status=status.HTTP_412_PRECONDITION_FAILED)
-
-        responseId = None
-        while ret == 0:
-            cur_time = time.time()
-            if gracefulTerminationTimeout and (cur_time - begin_time > gracefulTerminationTimeout):
-                return 255, Response(data={"error":"Fail to terminate VNF!"}, status=status.HTTP_408_REQUEST_TIMEOUT)
-            ret = call_vnfm("api/vnflcm/v1/vnf_lc_ops/%s?responseId=%s" % (jobId, responseId), "GET", vnfm_info)
-            if ret[0] != 0:
-                return 255, Response(data={"error":"Fail to get job status!"}, status=status.HTTP_412_PRECONDITION_FAILED)
-            if json.JSONDecoder().decode(ret[2]) != 200:
-                return 255, Response(data={"error":"Fail to get job status!"}, status=status.HTTP_412_PRECONDITION_FAILED)
-            job_info = json.JSONDecoder().decode(ret[1])
-            responseId = ignorcase_get(ignorcase_get(job_info, "VnfLcOpResponseDescriptor"), "responseId")
-            progress = ignorcase_get(ignorcase_get(job_info, "VnfLcOpResponseDescriptor"), "progress")
-            if progress == "100":
-                return 0, Response(data={"success":"success"}, status=status.HTTP_204_NO_CONTENT)
-    except Exception as e:
-        logger.error("Error occurred when do_createvnf")
-        return 255, Response(data={"error":"Exception caught! Fail to get job status!"}, status=status.HTTP_412_PRECONDITION_FAILED)
-
-
-def do_createvnf(request, data, vnfm_id):
-    logger.debug("[%s] request.data=%s", fun_name(), request.data)
-    try:
-        ret, vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
-        if ret != 0:
-            return ret, vnfm_info
-        ret = call_vnfm("api/vnflcm/v1/vnf_instances", "POST", vnfm_info, data)
-        logger.debug("[%s] call_req ret=%s", fun_name(), ret)
+        logger.error("Status code is %s, detail is %s.", ret[2], ret[1])
+        raise GvnfmDriverException("Failed to query vnfm(%s) from nslcm." % vnfm_id)
+    return json.JSONDecoder().decode(ret[1])
+
+
+# def wait4job(vnfm_id, jobId, gracefulTerminationTimeout):
+#     begin_time = time.time()
+#     try:
+#         logger.debug("[wait4job] vnfm_id=[%s],jobId=[%s],gracefulTerminationTimeout=[%s]",
+#                      vnfm_id, jobId, gracefulTerminationTimeout)
+#         vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
+#         logger.debug("[do_terminatevnf] vnfm_info=[%s]", vnfm_info)
+#
+#         ret, vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
+#         if ret != 0:
+#             return 255, Response(data={"error":"Fail to get VNFM!"}, status=status.HTTP_412_PRECONDITION_FAILED)
+#
+#         responseId = None
+#         while ret == 0:
+#             cur_time = time.time()
+#             if gracefulTerminationTimeout and (cur_time - begin_time > gracefulTerminationTimeout):
+#                 return 255, Response(data={"error":"Fail to terminate VNF!"}, status=status.HTTP_408_REQUEST_TIMEOUT)
+#             ret = call_vnfm("api/vnflcm/v1/vnf_lc_ops/%s?responseId=%s" % (jobId, responseId), "GET", vnfm_info)
+#             if ret[0] != 0:
+#                 return 255, Response(data={"error":"Fail to get job status!"}, status=status.HTTP_412_PRECONDITION_FAILED)
+#             if json.JSONDecoder().decode(ret[2]) != 200:
+#                 return 255, Response(data={"error":"Fail to get job status!"}, status=status.HTTP_412_PRECONDITION_FAILED)
+#             job_info = json.JSONDecoder().decode(ret[1])
+#             responseId = ignorcase_get(ignorcase_get(job_info, "VnfLcOpResponseDescriptor"), "responseId")
+#             progress = ignorcase_get(ignorcase_get(job_info, "VnfLcOpResponseDescriptor"), "progress")
+#             if progress == "100":
+#                 return 0, Response(data={"success":"success"}, status=status.HTTP_204_NO_CONTENT)
+#     except Exception as e:
+#         logger.error("Error occurred when do_createvnf")
+#         return 255, Response(data={"error":"Exception caught! Fail to get job status!"}, status=status.HTTP_412_PRECONDITION_FAILED)
+
+def wait4job(vnfm_id, job_id, gracefulTerminationTimeout=1200, retry_count=60, interval_second=3):
+    logger.debug("[wait4job] vnfm_id=[%s],jobId=[%s],gracefulTerminationTimeout=[%s]",
+                 vnfm_id, job_id, gracefulTerminationTimeout)
+    count = 0
+    response_id, new_response_id = 0, 0
+    job_end_normal, job_timeout = False, True
+    vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
+    logger.debug("[do_terminatevnf] vnfm_info=[%s]", vnfm_info)
+
+    while count < retry_count:
+        count = count + 1
+        time.sleep(interval_second)
+        ret = call_vnfm("api/vnflcm/v1/vnf_lc_ops/%s?responseId=%s" % (job_id, response_id), "GET", vnfm_info)
         if ret[0] != 0:
-            return 255, Response(data={'error': ret[1]}, status=ret[2])
-        resp = json.JSONDecoder().decode(ret[1])
-    except Exception as e:
-        logger.error("Error occurred when do_createvnf")
-        raise e
-    return 0, resp
+            logger.error("Failed to query job: %s:%s", ret[2], ret[1])
+            continue
+        job_result = json.JSONDecoder().decode(ret[1])
+        if "responseDescriptor" not in job_result:
+            logger.error("Job(%s) does not exist.", job_id)
+            continue
+        progress = job_result["responseDescriptor"]["progress"]
+        new_response_id = job_result["responseDescriptor"]["responseId"]
+        job_desc = job_result["responseDescriptor"]["statusDescription"]
+        if new_response_id != response_id:
+            logger.debug("%s:%s:%s", progress, new_response_id, job_desc)
+            response_id = new_response_id
+            count = 0
+        if progress == 255:
+            job_timeout = False
+            logger.error("Job(%s) failed: %s", job_id, job_desc)
+            break
+        elif progress == 100:
+            job_end_normal, job_timeout = True, False
+            logger.info("Job(%s) ended normally", job_id)
+            return {"success": "success"}
+    if job_timeout:
+        logger.error("Job(%s) timeout", job_id)
+    raise GvnfmDriverException("Fail to get job status!")
+
+
+def do_createvnf(vnfm_id, data):
+    logger.debug("[%s] request.data=%s", fun_name(), data)
+    vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
+    logger.debug("[do_createvnf] vnfm_info=[%s]", vnfm_info)
+    ret = call_vnfm("api/vnflcm/v1/vnf_instances", "POST", vnfm_info, data)
+    logger.debug("[%s] call_req ret=%s", fun_name(), ret)
+    if ret[0] != 0:
+        logger.error("Status code is %s, detail is %s.", ret[2], ret[1])
+        raise GvnfmDriverException('Failed to create vnf.')
+    return json.JSONDecoder().decode(ret[1])
 
 
-def do_instvnf(vnfInstanceId, request, data, vnfm_id):
-    logger.debug("[%s] request.data=%s", fun_name(), request.data)
-    try:
-        ret, vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
-        if ret != 0:
-            return ret, vnfm_info
-        ret = call_vnfm("api/vnflcm/v1/vnf_instances/%s/instantiate" % vnfInstanceId, "POST", vnfm_info, data)
-        logger.debug("[%s] call_req ret=%s", fun_name(), ret)
-        if ret[0] != 0:
-            return 255, Response(data={'error': ret[1]}, status=ret[2])
-        resp = json.JSONDecoder().decode(ret[1])
-    except Exception as e:
-        logger.error("Error occurred when do_instvnf")
-        raise e
-    return 0, resp
+def do_instvnf(vnfInstanceId, vnfm_id, data):
+    logger.debug("[%s] request.data=%s", fun_name(), data)
+    vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
+    logger.debug("[do_instvnf] vnfm_info=[%s]", vnfm_info)
+    ret = call_vnfm("api/vnflcm/v1/vnf_instances/%s/instantiate" % vnfInstanceId, "POST", vnfm_info, data)
+    logger.debug("[%s] call_req ret=%s", fun_name(), ret)
+    if ret[0] != 0:
+        logger.error("Status code is %s, detail is %s.", ret[2], ret[1])
+        raise GvnfmDriverException('Failed to inst vnf.')
+    return json.JSONDecoder().decode(ret[1])
 
 
-def do_terminatevnf(request, data, vnfm_id, vnfInstanceId):
-    logger.debug("[%s] request.data=%s", fun_name(), request.data)
-    try:
-        ret, vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
-        if ret != 0:
-            return ret,vnfm_info
-        ret = call_vnfm("api/vnflcm/v1/vnf_instances/%s/terminate"% vnfInstanceId,"POST", vnfm_info, data)
-        if ret[0] != 0:
-            return 255, Response(data={'error': ret[1]}, status=ret[2])
-        resp_data = json.JSONDecoder().decode(ret[1])
-        logger.debug("[%s]resp_data=%s", fun_name(), resp_data)
-    except Exception as e:
-        logger.error("Error occurred when do_terminatevnf")
-        raise e
-    return 0, resp_data
+def do_terminatevnf(vnfm_id, vnfInstanceId, data):
+    logger.debug("[%s] request.data=%s", fun_name(), data)
+    vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
+    logger.debug("[do_terminatevnf] vnfm_info=[%s]", vnfm_info)
+    ret = call_vnfm("api/vnflcm/v1/vnf_instances/%s/terminate"% vnfInstanceId,"POST", vnfm_info, data)
+    if ret[0] != 0:
+        logger.error("Status code is %s, detail is %s.", ret[2], ret[1])
+        raise GvnfmDriverException('Failed to terminate vnf.')
+    return json.JSONDecoder().decode(ret[1])
 
 
-def do_deletevnf(request, vnfm_id, vnfInstanceId):
-    logger.debug("[%s] request.data=%s", fun_name(), request.data)
-    try:
-        ret, vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
-        if ret != 0:
-            return ret, vnfm_info
-        ret = call_vnfm("api/vnflcm/v1/vnf_instances/%s" % vnfInstanceId, "DELETE", vnfm_info)
-        if ret[0] != 0:
-            return 255, Response(data={'error': ret[1]}, status=ret[2])
-        resp_data = json.JSONDecoder().decode(ret[1])
-        logger.debug("[%s]resp_data=%s", fun_name(), resp_data)
-    except Exception as e:
-        logger.error("Error occurred when do_deletevnf")
-        raise e
-    return 0, resp_data
+def do_deletevnf(vnfm_id, vnfInstanceId, data):
+    logger.debug("[%s] request.data=%s", fun_name(), data)
+    vnfm_info = get_vnfminfo_from_nslcm(vnfm_id)
+    logger.debug("[do_deletevnf] vnfm_info=[%s]", vnfm_info)
+    ret = call_vnfm("api/vnflcm/v1/vnf_instances/%s" % vnfInstanceId, "DELETE", vnfm_info)
+    if ret[0] != 0:
+        logger.error("Status code is %s, detail is %s.", ret[2], ret[1])
+        raise GvnfmDriverException('Failed to delete vnf.')
+    return json.JSONDecoder().decode(ret[1])
 
 
 def do_queryvnf(request, vnfm_id, vnfInstanceId):
diff --git a/gvnfmadapter/driver/pub/exceptions.py b/gvnfmadapter/driver/pub/exceptions.py
new file mode 100644 (file)
index 0000000..8b08d47
--- /dev/null
@@ -0,0 +1,16 @@
+# Copyright 2017 ZTE Corporation.
+#
+# 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.
+
+class GvnfmDriverException(Exception):
+    pass