ADD UT for ns_vnfs Issue-ID: VFC-1429 Signed-off-by: zhuerlei <zhu.erlei@zte.com.cn>
[vfc/nfvo/lcm.git] / lcm / ns_vnfs / tests / tests.py
1 # Copyright 2016-2017 ZTE Corporation.
2 #
3 # Licensed under the Apache License, Version 2.0 (the "License");
4 # you may not use this file except in compliance with the License.
5 # You may obtain a copy of the License at
6 #
7 #         http://www.apache.org/licenses/LICENSE-2.0
8 #
9 # Unless required by applicable law or agreed to in writing, software
10 # distributed under the License is distributed on an "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 # See the License for the specific language governing permissions and
13 # limitations under the License.
14 import json
15 import uuid
16 import time
17 import mock
18
19 from django.test import TestCase, Client
20 from rest_framework import status
21
22 from lcm.pub.database.models import VLInstModel, NfInstModel, JobModel, NSInstModel, VmInstModel, \
23     OOFDataModel, VNFCInstModel
24 from lcm.pub.exceptions import NSLCMException
25 from lcm.pub.utils import restcall
26 from lcm.jobs.enum import JOB_MODEL_STATUS, JOB_TYPE, JOB_ACTION, JOB_PROGRESS
27 from lcm.pub.utils.jobutil import JobUtil
28 from lcm.pub.utils.timeutil import now_time
29 from lcm.pub.utils.values import ignore_case_get
30 from lcm.ns_vnfs.biz.grant_vnf import GrantVnf
31 from lcm.ns_vnfs.biz.heal_vnfs import NFHealService
32 from lcm.ns_vnfs.biz.scale_vnfs import NFManualScaleService
33 from lcm.ns_vnfs.biz.subscribe import SubscriptionDeletion
34 from lcm.ns_vnfs.biz.terminate_nfs import TerminateVnfs
35 from lcm.ns_vnfs.enum import VNF_STATUS, LIFE_CYCLE_OPERATION, RESOURCE_CHANGE_TYPE
36 from lcm.ns_vnfs.biz.place_vnfs import PlaceVnfs
37 from lcm.pub.msapi import resmgr
38 from lcm.ns_vnfs.tests.test_data import vnfm_info, vim_info, vnf_place_request
39 from lcm.ns_vnfs.tests.test_data import nf_package_info, nsd_model_dict, subscription_response_data
40 from lcm.ns_vnfs.biz.create_vnfs import CreateVnfs
41 from lcm.ns_vnfs.biz import create_vnfs
42 from lcm.ns_vnfs.biz.grant_vnfs import GrantVnfs
43 from lcm.ns.enum import OWNER_TYPE
44
45
46 class TestGetVnfViews(TestCase):
47     def setUp(self):
48         self.client = Client()
49         self.nf_inst_id = str(uuid.uuid4())
50         NfInstModel(nfinstid=self.nf_inst_id, nf_name="vnf1", vnfm_inst_id="1", vnf_id="vnf_id1",
51                     status=VNF_STATUS.ACTIVE, create_time=now_time(), lastuptime=now_time()).save()
52
53     def tearDown(self):
54         NfInstModel.objects.all().delete()
55
56     def test_get_vnf(self):
57         response = self.client.get("/api/nslcm/v1/ns/vnfs/%s" % self.nf_inst_id)
58         self.assertEqual(status.HTTP_200_OK, response.status_code)
59         context = json.loads(response.content)
60         self.assertEqual(self.nf_inst_id, context["vnfInstId"])
61
62
63 class TestTerminateVnfViews(TestCase):
64     def setUp(self):
65         self.client = Client()
66         self.data = {
67             "terminationType": "forceful",
68             "gracefulTerminationTimeout": "600"
69         }
70         self.ns_inst_id = str(uuid.uuid4())
71         self.nf_inst_id = "1"
72         self.vim_id = str(uuid.uuid4())
73         self.job_id = str(uuid.uuid4())
74         self.nf_uuid = "111"
75         self.vnfd_model = {"metadata": {"vnfdId": "1"}}
76         NSInstModel.objects.all().delete()
77         NfInstModel.objects.all().delete()
78         VmInstModel.objects.all().delete()
79         NSInstModel(id=self.ns_inst_id, name="ns_name").save()
80         NfInstModel.objects.create(nfinstid=self.nf_inst_id,
81                                    vnfm_inst_id="1",
82                                    status="active",
83                                    mnfinstid=self.nf_uuid,
84                                    vnfd_model=self.vnfd_model
85                                    )
86         VmInstModel.objects.create(vmid="1",
87                                    vimid='{"cloud_owner": "VCPE", "cloud_regionid": "RegionOne"}',
88                                    instid=self.nf_inst_id
89                                    )
90
91     def tearDown(self):
92         NSInstModel.objects.all().delete()
93         NfInstModel.objects.all().delete()
94
95     @mock.patch.object(TerminateVnfs, "run")
96     def test_terminate_vnf_url(self, mock_run):
97         req_data = {
98             "terminationType": "forceful",
99             "gracefulTerminationTimeout": "600"}
100
101         response = self.client.post("/api/nslcm/v1/ns/terminatevnf/%s" % self.nf_inst_id, data=req_data)
102         self.assertEqual(status.HTTP_202_ACCEPTED, response.status_code)
103
104     @mock.patch.object(time, "sleep")
105     @mock.patch.object(restcall, "call_req")
106     @mock.patch.object(SubscriptionDeletion, "send_subscription_deletion_request")
107     def test_terminate_vnf(self, mock_send_subscription_deletion_request, mock_call_req, mock_sleep):
108         job_id = JobUtil.create_job(JOB_TYPE.VNF, JOB_ACTION.TERMINATE, self.nf_inst_id)
109         job_info = {
110             "jobId": job_id,
111             "responsedescriptor": {"status": JOB_MODEL_STATUS.FINISHED}
112         }
113         mock_vals = {
114             "/external-system/esr-vnfm-list/esr-vnfm/1?depth=all":
115                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
116             "/api/ztevnfmdriver/v1/1/vnfs/111/terminate":
117                 [0, json.JSONEncoder().encode({"jobId": job_id}), "200"],
118             "/api/ztevnfmdriver/v1/1/jobs/" + job_id + "?responseId=0":
119                 [0, json.JSONEncoder().encode(job_info), "200"],
120             "/api/resmgr/v1/vnf/1":
121                 [0, json.JSONEncoder().encode({"jobId": job_id}), "200"]
122         }
123
124         def side_effect(*args):
125             return mock_vals[args[4]]
126         mock_call_req.side_effect = side_effect
127         TerminateVnfs(self.data, self.nf_inst_id, job_id).run()
128         nfinst = NfInstModel.objects.filter(nfinstid=self.nf_inst_id)
129         if nfinst:
130             self.assertEqual(1, 0)
131         else:
132             self.assertEqual(1, 1)
133         self.assertEqual(JobModel.objects.get(jobid=job_id).progress, 100)
134
135     def test_terminate_vnf_when_vnf_is_dealing(self):
136         NfInstModel.objects.filter(nfinstid=self.nf_inst_id).update(status=VNF_STATUS.TERMINATING)
137         job_id = JobUtil.create_job(JOB_TYPE.VNF, JOB_ACTION.TERMINATE, self.nf_inst_id)
138         TerminateVnfs(self.data, self.nf_inst_id, job_id).run()
139         self.assertEqual(NfInstModel.objects.get(nfinstid=self.nf_inst_id).status, VNF_STATUS.FAILED)
140         self.assertEqual(JobModel.objects.get(jobid=job_id).progress, 255)
141
142     @mock.patch.object(time, "sleep")
143     @mock.patch.object(restcall, "call_req")
144     @mock.patch.object(SubscriptionDeletion, "send_subscription_deletion_request")
145     def test_terminate_vnf_when_job_error(self, mock_send_subscription_deletion_request, mock_call_req, mock_sleep):
146         job_id = JobUtil.create_job(JOB_TYPE.VNF, JOB_ACTION.TERMINATE, self.nf_inst_id)
147         job_info = {
148             "jobId": job_id,
149             "responsedescriptor": {"status": JOB_MODEL_STATUS.ERROR}
150         }
151         mock_vals = {
152             "/external-system/esr-vnfm-list/esr-vnfm/1?depth=all":
153                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
154             "/api/ztevnfmdriver/v1/1/vnfs/111/terminate":
155                 [0, json.JSONEncoder().encode({"jobId": job_id}), "200"],
156             "/api/ztevnfmdriver/v1/1/jobs/" + job_id + "?responseId=0":
157                 [0, json.JSONEncoder().encode(job_info), "200"]
158         }
159
160         def side_effect(*args):
161             return mock_vals[args[4]]
162
163         mock_call_req.side_effect = side_effect
164         TerminateVnfs(self.data, self.nf_inst_id, job_id).run()
165         self.assertEqual(NfInstModel.objects.get(nfinstid=self.nf_inst_id).status, VNF_STATUS.FAILED)
166         self.assertEqual(JobModel.objects.get(jobid=job_id).progress, 255)
167
168
169 class TestScaleVnfViews(TestCase):
170     def setUp(self):
171         self.client = Client()
172         self.nf_inst_id = str(uuid.uuid4())
173         self.url = "/api/nslcm/v1/ns/ns_vnfs/%s/scaling" % self.nf_inst_id
174         self.data = {
175             "scaleVnfData":
176                 {
177                     "type": "SCALE_OUT",
178                     "aspectId": "demo_aspect1",
179                     "numberOfSteps": 1,
180                     "additionalParam": {}
181                 }
182         }
183         NfInstModel.objects.create(nfinstid=self.nf_inst_id, vnfm_inst_id="vnfm_inst_id_001",
184                                    mnfinstid="m_nf_inst_id_001")
185
186     def tearDown(self):
187         NfInstModel.objects.all().delete()
188
189     # def test_scale_vnf_view(self):
190     #     response = self.client.post(self.url, self.data)
191     #     self.assertEqual(response.status_code, status.HTTP_202_ACCEPTED)
192
193     @mock.patch.object(time, "sleep")
194     @mock.patch.object(restcall, "call_req")
195     def test_scale_vnf_success(self, mock_call_req, mock_sleep):
196         scale_service = NFManualScaleService(self.nf_inst_id, self.data)
197         job_info = {
198             "jobId": scale_service.job_id,
199             "responsedescriptor": {"status": JOB_MODEL_STATUS.FINISHED}
200         }
201         mock_vals = {
202             "/external-system/esr-vnfm-list/esr-vnfm/vnfm_inst_id_001?depth=all":
203                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
204             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/vnfs/m_nf_inst_id_001/scale":
205                 [0, json.JSONEncoder().encode({"jobId": scale_service.job_id}), "200"],
206             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/jobs/" + scale_service.job_id + "?responseId=0":
207                 [0, json.JSONEncoder().encode(job_info), "200"]
208         }
209
210         def side_effect(*args):
211             return mock_vals[args[4]]
212         mock_call_req.side_effect = side_effect
213         scale_service.run()
214         nsIns = NfInstModel.objects.get(nfinstid=self.nf_inst_id)
215         self.assertEqual(nsIns.status, VNF_STATUS.ACTIVE)
216
217         jobs = JobModel.objects.get(jobid=scale_service.job_id)
218         self.assertEqual(JOB_PROGRESS.FINISHED, jobs.progress)
219
220     @mock.patch.object(time, "sleep")
221     @mock.patch.object(restcall, "call_req")
222     def test_scale_vnf_when_job_fail(self, mock_call_req, mock_sleep):
223         scale_service = NFManualScaleService(self.nf_inst_id, self.data)
224         job_info = {
225             "jobId": scale_service.job_id,
226             "responsedescriptor": {"status": JOB_MODEL_STATUS.ERROR}
227         }
228         mock_vals = {
229             "/external-system/esr-vnfm-list/esr-vnfm/vnfm_inst_id_001?depth=all":
230                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
231             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/vnfs/m_nf_inst_id_001/scale":
232                 [0, json.JSONEncoder().encode({"jobId": scale_service.job_id}), "200"],
233             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/jobs/" + scale_service.job_id + "?responseId=0":
234                 [0, json.JSONEncoder().encode(job_info), "200"]
235         }
236
237         def side_effect(*args):
238             return mock_vals[args[4]]
239
240         mock_call_req.side_effect = side_effect
241         scale_service.run()
242         nsIns = NfInstModel.objects.get(nfinstid=self.nf_inst_id)
243         self.assertEqual(nsIns.status, VNF_STATUS.ACTIVE)
244         jobs = JobModel.objects.get(jobid=scale_service.job_id)
245         self.assertEqual(JOB_PROGRESS.ERROR, jobs.progress)
246
247     def test_scale_vnf_when_exception(self):
248         req_data = {
249             "scaleVnfData": [
250                 {
251                     "type": "SCALE_OUT",
252                     "aspectId": "demo_aspect1",
253                     "numberOfSteps": 1,
254                 },
255                 {
256                     "type": "SCALE_OUT",
257                     "aspectId": "demo_aspect2",
258                     "numberOfSteps": 1,
259                 }
260             ]
261         }
262         scale_service = NFManualScaleService(self.nf_inst_id, req_data)
263         scale_service.run()
264         nsIns = NfInstModel.objects.get(nfinstid=self.nf_inst_id)
265         self.assertEqual(nsIns.status, VNF_STATUS.ACTIVE)
266
267         jobs = JobModel.objects.get(jobid=scale_service.job_id)
268         self.assertEqual(JOB_PROGRESS.ERROR, jobs.progress)
269
270     def test_scale_vnf_when_nf_instance_does_not_exist(self):
271         req_data = {
272             "scaleVnfData":
273                 {
274                     "type": "SCALE_OUT",
275                     "aspectId": "demo_aspect1",
276                     "numberOfSteps": 1,
277                 }
278         }
279         scale_service = NFManualScaleService("nf_instance_does_not_exist", req_data)
280         scale_service.run()
281
282         jobs = JobModel.objects.get(jobid=scale_service.job_id)
283         self.assertEqual(JOB_PROGRESS.ERROR, jobs.progress)
284
285     def test_scale_vnf_when_scale_vnf_data_does_not_exist(self):
286         req_data = {
287             "scaleVnfData": {}
288         }
289         scale_service = NFManualScaleService(self.nf_inst_id, req_data)
290         scale_service.run()
291         nsIns = NfInstModel.objects.get(nfinstid=self.nf_inst_id)
292         self.assertEqual(nsIns.status, VNF_STATUS.ACTIVE)
293
294         jobs = JobModel.objects.get(jobid=scale_service.job_id)
295         self.assertEqual(JOB_PROGRESS.ERROR, jobs.progress)
296
297
298 class TestHealVnfViews(TestCase):
299     def setUp(self):
300         self.client = Client()
301         self.ns_inst_id = str(uuid.uuid4())
302         self.nf_inst_id = str(uuid.uuid4())
303         self.nf_uuid = "111"
304         self.data = {
305             "action": "vmReset",
306             "affectedvm": {
307                 "vmid": "1",
308                 "vduid": "1",
309                 "vmname": "name",
310             },
311             "additionalParams": {
312                 "actionvminfo": {
313                     "vmid": "vm_id_001",
314                 }
315             }
316         }
317         NSInstModel(id=self.ns_inst_id, name="ns_name").save()
318         NfInstModel.objects.create(nfinstid=self.nf_inst_id, status=VNF_STATUS.NULL, vnfm_inst_id="vnfm_inst_id_001",
319                                    mnfinstid="m_nf_inst_id_001")
320         NfInstModel.objects.create(nfinstid="non_vud_id", status=VNF_STATUS.NULL, vnfm_inst_id="vnfm_inst_id_001",
321                                    mnfinstid="m_nf_inst_id_001")
322         VNFCInstModel.objects.create(nfinstid=self.nf_inst_id, vmid="vm_id_001", vduid="vdu_id_001")
323         VmInstModel.objects.create(resouceid="vm_id_001", vmname="vm_name_001")
324
325     def tearDown(self):
326         NSInstModel.objects.all().delete()
327         NfInstModel.objects.all().delete()
328
329     @mock.patch.object(time, "sleep")
330     @mock.patch.object(restcall, "call_req")
331     def test_heal_vnf_success(self, mock_call_req, mock_sleep):
332         heal_service = NFHealService(self.nf_inst_id, self.data)
333         mock_vals = {
334             "/test/bins/1?timeout=15000":
335                 [0, json.JSONEncoder().encode(['{"powering-off": "", "instance_id": "vm_id_001", '
336                                                '"display_name": ""}']), "200"],
337             "/external-system/esr-vnfm-list/esr-vnfm/vnfm_inst_id_001?depth=all":
338                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
339             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/vnfs/m_nf_inst_id_001/heal":
340                 [0, json.JSONEncoder().encode({"jobId": heal_service.job_id}), "200"],
341             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/jobs/" + heal_service.job_id + "?responseId=0":
342                 [0, json.JSONEncoder().encode({
343                     "jobId": heal_service.job_id,
344                     "responsedescriptor": {
345                         "status": JOB_MODEL_STATUS.FINISHED,
346                         "responsehistorylist": [{
347                             "progress": "0",
348                             "status": JOB_MODEL_STATUS.PROCESSING,
349                             "responseid": "2",
350                             "statusdescription": "creating",
351                             "errorcode": "0"
352                         }]
353                     }
354                 }), "200"]
355         }
356
357         def side_effect(*args):
358             return mock_vals[args[4]]
359
360         mock_call_req.side_effect = side_effect
361         heal_service.run()
362         self.assertEqual(NfInstModel.objects.get(nfinstid=self.nf_inst_id).status, VNF_STATUS.ACTIVE)
363         jobs = JobModel.objects.get(jobid=heal_service.job_id)
364         self.assertEqual(JOB_PROGRESS.FINISHED, jobs.progress)
365
366     def test_heal_vnf_when_non_existing_vnf(self, ):
367         heal_service = NFHealService("on_existing_vnf", self.data)
368         heal_service.run()
369         self.assertEqual(NfInstModel.objects.get(nfinstid=self.nf_inst_id).status, VNF_STATUS.NULL)
370         jobs = JobModel.objects.get(jobid=heal_service.job_id)
371         self.assertEqual(JOB_PROGRESS.ERROR, jobs.progress)
372
373     def test_heal_vnf_when_additional_params_non_exist(self):
374         data = {"action": "vmReset"}
375         heal_service = NFHealService(self.nf_inst_id, data)
376         heal_service.run()
377         self.assertEqual(NfInstModel.objects.get(nfinstid=self.nf_inst_id).status, VNF_STATUS.NULL)
378         jobs = JobModel.objects.get(jobid=heal_service.job_id)
379         self.assertEqual(JOB_PROGRESS.ERROR, jobs.progress)
380
381     def test_heal_vnf_when_non_vud_id(self, ):
382         heal_service = NFHealService("non_vud_id", self.data)
383         heal_service.run()
384         self.assertEqual(NfInstModel.objects.get(nfinstid="non_vud_id").status, VNF_STATUS.NULL)
385         jobs = JobModel.objects.get(jobid=heal_service.job_id)
386         self.assertEqual(JOB_PROGRESS.ERROR, jobs.progress)
387
388     @mock.patch.object(restcall, "call_req")
389     def test_heal_vnf_when_no_vnfm_job_id(self, mock_call_req):
390         heal_service = NFHealService(self.nf_inst_id, self.data)
391         mock_vals = {
392             "/test/bins/1?timeout=15000":
393                 [0, json.JSONEncoder().encode(['{"powering-off": "", "instance_id": "vm_id_001", '
394                                                '"display_name": ""}']), "200"],
395             "/external-system/esr-vnfm-list/esr-vnfm/vnfm_inst_id_001?depth=all":
396                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
397             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/vnfs/m_nf_inst_id_001/heal":
398                 [0, json.JSONEncoder().encode({}), "200"]
399         }
400
401         def side_effect(*args):
402             return mock_vals[args[4]]
403
404         mock_call_req.side_effect = side_effect
405         heal_service.run()
406         self.assertEqual(NfInstModel.objects.get(nfinstid=self.nf_inst_id).status, VNF_STATUS.ACTIVE)
407         jobs = JobModel.objects.get(jobid=heal_service.job_id)
408         self.assertEqual(JOB_PROGRESS.FINISHED, jobs.progress)
409
410     @mock.patch.object(time, "sleep")
411     @mock.patch.object(restcall, "call_req")
412     def test_heal_vnf_when_job_bot_finish(self, mock_call_req, mock_sleep):
413         heal_service = NFHealService(self.nf_inst_id, self.data)
414         mock_vals = {
415             "/test/bins/1?timeout=15000":
416                 [0, json.JSONEncoder().encode(['{"powering-off": "", "instance_id": "vm_id_001", '
417                                                '"display_name": ""}']), "200"],
418             "/external-system/esr-vnfm-list/esr-vnfm/vnfm_inst_id_001?depth=all":
419                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
420             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/vnfs/m_nf_inst_id_001/heal":
421                 [0, json.JSONEncoder().encode({"jobId": heal_service.job_id}), "200"],
422             "/api/ztevnfmdriver/v1/vnfm_inst_id_001/jobs/" + heal_service.job_id + "?responseId=0":
423                 [0, json.JSONEncoder().encode({
424                     "jobId": heal_service.job_id,
425                     "responsedescriptor": {
426                         "status": JOB_MODEL_STATUS.ERROR,
427                         "responsehistorylist": [{
428                             "progress": "0",
429                             "status": JOB_MODEL_STATUS.PROCESSING,
430                             "responseid": "2",
431                             "statusdescription": "creating",
432                             "errorcode": "0"
433                         }]
434                     }
435                 }), "200"]
436         }
437
438         def side_effect(*args):
439             return mock_vals[args[4]]
440
441         mock_call_req.side_effect = side_effect
442         heal_service.run()
443         self.assertEqual(NfInstModel.objects.get(nfinstid=self.nf_inst_id).status, VNF_STATUS.HEALING)
444         jobs = JobModel.objects.get(jobid=heal_service.job_id)
445         self.assertEqual(JOB_PROGRESS.ERROR, jobs.progress)
446
447
448 class TestGetVnfmInfoViews(TestCase):
449     def setUp(self):
450         self.client = Client()
451         self.vnfm_id = str(uuid.uuid4())
452
453     def tearDown(self):
454         pass
455
456     @mock.patch.object(restcall, "call_req")
457     def test_get_vnfm_info(self, mock_call_req):
458         vnfm_info_aai = {
459             "vnfm-id": "example-vnfm-id-val-62576",
460             "vim-id": "example-vim-id-val-35114",
461             "certificate-url": "example-certificate-url-val-90242",
462             "esr-system-info-list": {
463                 "esr-system-info": [
464                     {
465                         "esr-system-info-id": "example-esr-system-info-id-val-78484",
466                         "system-name": "example-system-name-val-23790",
467                         "type": "example-type-val-52596",
468                         "vendor": "example-vendor-val-47399",
469                         "version": "example-version-val-42051",
470                         "service-url": "example-service-url-val-10731",
471                         "user-name": "example-user-name-val-65946",
472                         "password": "example-password-val-22505",
473                         "system-type": "example-system-type-val-27221",
474                         "protocal": "example-protocal-val-54632",
475                         "ssl-cacert": "example-ssl-cacert-val-45965",
476                         "ssl-insecure": True,
477                         "ip-address": "example-ip-address-val-19212",
478                         "port": "example-port-val-57641",
479                         "cloud-domain": "example-cloud-domain-val-26296",
480                         "default-tenant": "example-default-tenant-val-87724"
481                     }
482                 ]
483             }
484         }
485         r1 = [0, json.JSONEncoder().encode(vnfm_info_aai), "200"]
486         mock_call_req.side_effect = [r1]
487         esr_system_info = ignore_case_get(ignore_case_get(vnfm_info_aai, "esr-system-info-list"), "esr-system-info")
488         expect_data = {
489             "vnfmId": vnfm_info_aai["vnfm-id"],
490             "name": vnfm_info_aai["vnfm-id"],
491             "type": ignore_case_get(esr_system_info[0], "type"),
492             "vimId": vnfm_info_aai["vim-id"],
493             "vendor": ignore_case_get(esr_system_info[0], "vendor"),
494             "version": ignore_case_get(esr_system_info[0], "version"),
495             "description": "vnfm",
496             "certificateUrl": vnfm_info_aai["certificate-url"],
497             "url": ignore_case_get(esr_system_info[0], "service-url"),
498             "userName": ignore_case_get(esr_system_info[0], "user-name"),
499             "password": ignore_case_get(esr_system_info[0], "password"),
500             "createTime": ""
501         }
502
503         response = self.client.get("/api/nslcm/v1/vnfms/%s" % self.vnfm_id)
504         self.assertEqual(status.HTTP_200_OK, response.status_code, response.content)
505         context = json.loads(response.content)
506         self.assertEqual(expect_data, context)
507
508
509 class TestGetVimInfoViews(TestCase):
510     def setUp(self):
511         self.client = Client()
512         self.vim_id = {"cloud_owner": "VCPE", "cloud_regionid": "RegionOne"}
513
514     def tearDown(self):
515         pass
516
517     @mock.patch.object(restcall, "call_req")
518     def test_get_vim_info(self, mock_call_req):
519         r1 = [0, json.JSONEncoder().encode(vim_info), "200"]
520         mock_call_req.side_effect = [r1]
521         esr_system_info = ignore_case_get(ignore_case_get(vim_info, "esr-system-info-list"), "esr-system-info")
522         expect_data = {
523             "vimId": self.vim_id,
524             "name": self.vim_id,
525             "url": ignore_case_get(esr_system_info[0], "service-url"),
526             "userName": ignore_case_get(esr_system_info[0], "user-name"),
527             "password": ignore_case_get(esr_system_info[0], "password"),
528             # "tenant": ignore_case_get(tenants[0], "tenant-id"),
529             "tenant": ignore_case_get(esr_system_info[0], "default-tenant"),
530             "vendor": ignore_case_get(esr_system_info[0], "vendor"),
531             "version": ignore_case_get(esr_system_info[0], "version"),
532             "description": "vim",
533             "domain": "",
534             "type": ignore_case_get(esr_system_info[0], "type"),
535             "createTime": ""
536         }
537
538         # response = self.client.get("/api/nslcm/v1/vims/%s" % self.vim_id)
539         response = self.client.get("/api/nslcm/v1/vims/%s/%s" % (self.vim_id["cloud_owner"], self.vim_id["cloud_regionid"]))
540         self.assertEqual(status.HTTP_200_OK, response.status_code)
541         context = json.loads(response.content)
542         self.assertEqual(expect_data["url"], context["url"])
543
544
545 class TestPlaceVnfViews(TestCase):
546     def setUp(self):
547         self.vnf_inst_id = "1234"
548         self.vnf_id = "vG"
549         self.client = Client()
550         OOFDataModel.objects.all().delete()
551         OOFDataModel.objects.create(
552             request_id="1234",
553             transaction_id="1234",
554             request_status="init",
555             request_module_name=self.vnf_id,
556             service_resource_id=self.vnf_inst_id,
557             vim_id="",
558             cloud_owner="",
559             cloud_region_id="",
560             vdu_info="",
561         )
562
563     def tearDown(self):
564         OOFDataModel.objects.all().delete()
565
566     @mock.patch.object(restcall, "call_req")
567     def test_place_vnf(self, mock_call_req):
568         vdu_info_json = [{
569             "vduName": "vG_0",
570             "flavorName": "HPA.flavor.1",
571             "flavorId": "12345",
572             "directive": []
573         }]
574         PlaceVnfs(vnf_place_request).extract()
575         db_info = OOFDataModel.objects.filter(request_id=vnf_place_request.get("requestId"), transaction_id=vnf_place_request.get("transactionId"))
576         self.assertEqual(db_info[0].request_status, "completed")
577         self.assertEqual(db_info[0].vim_id, "CloudOwner1_DLLSTX1A")
578         self.assertEqual(db_info[0].cloud_owner, "CloudOwner1")
579         self.assertEqual(db_info[0].cloud_region_id, "DLLSTX1A")
580         self.assertEqual(db_info[0].vdu_info, json.dumps(vdu_info_json))
581
582     def test_place_vnf_with_invalid_response(self):
583         resp = {
584             "requestId": "1234",
585             "transactionId": "1234",
586             "statusMessage": "xx",
587             "requestStatus": "pending",
588             "solutions": {
589                 "placementSolutions": [
590                     [
591                         {
592                             "resourceModuleName": self.vnf_id,
593                             "serviceResourceId": self.vnf_inst_id,
594                             "solution": {
595                                 "identifierType": "serviceInstanceId",
596                                 "identifiers": [
597                                     "xx"
598                                 ],
599                                 "cloudOwner": "CloudOwner1 "
600                             },
601                             "assignmentInfo": []
602                         }
603                     ]
604                 ],
605                 "licenseSolutions": [
606                     {
607                         "resourceModuleName": "string",
608                         "serviceResourceId": "string",
609                         "entitlementPoolUUID": [
610                             "string"
611                         ],
612                         "licenseKeyGroupUUID": [
613                             "string"
614                         ],
615                         "entitlementPoolInvariantUUID": [
616                             "string"
617                         ],
618                         "licenseKeyGroupInvariantUUID": [
619                             "string"
620                         ]
621                     }
622                 ]
623             }
624         }
625         PlaceVnfs(resp).extract()
626         db_info = OOFDataModel.objects.filter(request_id=resp.get("requestId"), transaction_id=resp.get("transactionId"))
627         self.assertEqual(db_info[0].request_status, "pending")
628         self.assertEqual(db_info[0].vim_id, "none")
629         self.assertEqual(db_info[0].cloud_owner, "none")
630         self.assertEqual(db_info[0].cloud_region_id, "none")
631         self.assertEqual(db_info[0].vdu_info, "none")
632
633     def test_place_vnf_with_no_assignment_info(self):
634         resp = {
635             "requestId": "1234",
636             "transactionId": "1234",
637             "statusMessage": "xx",
638             "requestStatus": "completed",
639             "solutions": {
640                 "placementSolutions": [
641                     [
642                         {
643                             "resourceModuleName": self.vnf_id,
644                             "serviceResourceId": self.vnf_inst_id,
645                             "solution": {
646                                 "identifierType": "serviceInstanceId",
647                                 "identifiers": [
648                                     "xx"
649                                 ],
650                                 "cloudOwner": "CloudOwner1 "
651                             }
652                         }
653                     ]
654                 ],
655                 "licenseSolutions": [
656                     {
657                         "resourceModuleName": "string",
658                         "serviceResourceId": "string",
659                         "entitlementPoolUUID": [
660                             "string"
661                         ],
662                         "licenseKeyGroupUUID": [
663                             "string"
664                         ],
665                         "entitlementPoolInvariantUUID": [
666                             "string"
667                         ],
668                         "licenseKeyGroupInvariantUUID": [
669                             "string"
670                         ]
671                     }
672                 ]
673             }
674         }
675         PlaceVnfs(resp).extract()
676         db_info = OOFDataModel.objects.filter(request_id=resp.get("requestId"), transaction_id=resp.get("transactionId"))
677         self.assertEqual(db_info[0].request_status, "completed")
678         self.assertEqual(db_info[0].vim_id, "none")
679         self.assertEqual(db_info[0].cloud_owner, "none")
680         self.assertEqual(db_info[0].cloud_region_id, "none")
681         self.assertEqual(db_info[0].vdu_info, "none")
682
683     def test_place_vnf_no_directives(self):
684         resp = {
685             "requestId": "1234",
686             "transactionId": "1234",
687             "statusMessage": "xx",
688             "requestStatus": "completed",
689             "solutions": {
690                 "placementSolutions": [
691                     [
692                         {
693                             "resourceModuleName": self.vnf_id,
694                             "serviceResourceId": self.vnf_inst_id,
695                             "solution": {
696                                 "identifierType": "serviceInstanceId",
697                                 "identifiers": [
698                                     "xx"
699                                 ],
700                                 "cloudOwner": "CloudOwner1 "
701                             },
702                             "assignmentInfo": [
703                                 {"key": "locationId",
704                                  "value": "DLLSTX1A"
705                                  }
706                             ]
707                         }
708                     ]
709                 ],
710                 "licenseSoutions": [
711                     {
712                         "resourceModuleName": "string",
713                         "serviceResourceId": "string",
714                         "entitlementPoolUUID": [
715                             "string"
716                         ],
717                         "licenseKeyGroupUUID": [
718                             "string"
719                         ],
720                         "entitlementPoolInvariantUUID": [
721                             "string"
722                         ],
723                         "licenseKeyGroupInvariantUUID": [
724                             "string"
725                         ]
726                     }
727                 ]
728             }
729         }
730         PlaceVnfs(resp).extract()
731         db_info = OOFDataModel.objects.filter(request_id=resp.get("requestId"), transaction_id=resp.get("transactionId"))
732         self.assertEqual(db_info[0].request_status, "completed")
733         self.assertEqual(db_info[0].vim_id, "none")
734         self.assertEqual(db_info[0].cloud_owner, "none")
735         self.assertEqual(db_info[0].cloud_region_id, "none")
736         self.assertEqual(db_info[0].vdu_info, "none")
737
738     def test_place_vnf_with_no_solution(self):
739         resp = {
740             "requestId": "1234",
741             "transactionId": "1234",
742             "statusMessage": "xx",
743             "requestStatus": "completed",
744             "solutions": {
745                 "placementSolutions": [],
746                 "licenseSoutions": []
747             }
748         }
749         PlaceVnfs(resp).extract()
750         db_info = OOFDataModel.objects.filter(request_id=resp.get("requestId"), transaction_id=resp.get("transactionId"))
751         self.assertEqual(db_info[0].request_status, "completed")
752         self.assertEqual(db_info[0].vim_id, "none")
753         self.assertEqual(db_info[0].cloud_owner, "none")
754         self.assertEqual(db_info[0].cloud_region_id, "none")
755         self.assertEqual(db_info[0].vdu_info, "none")
756
757
758 class TestGrantVnfsViews(TestCase):
759     def setUp(self):
760         self.vnf_inst_id = str(uuid.uuid4())
761         self.data = {
762             "vnfInstanceId": self.vnf_inst_id,
763             "lifecycleOperation": LIFE_CYCLE_OPERATION.INSTANTIATE,
764             "addResource": [{"type": RESOURCE_CHANGE_TYPE.VDU, "vdu": "vdu_grant_vnf_add_resources"}],
765             "additionalParam": {
766                 "vnfmid": "vnfm_inst_id_001",
767                 "vimid": '{"cloud_owner": "VCPE", "cloud_regionid": "RegionOne"}'
768             }
769         }
770         self.client = Client()
771         self.url = "/api/nslcm/v1/ns/grantvnf"
772         NfInstModel(mnfinstid=self.vnf_inst_id, nfinstid="vnf_inst_id_001", package_id="package_id_001",
773                     vnfm_inst_id="vnfm_inst_id_001").save()
774
775     def tearDown(self):
776         OOFDataModel.objects.all().delete()
777         NfInstModel.objects.all().delete()
778
779     # @mock.patch.object(restcall, "call_req")
780     # def test_nf_grant_view(self, mock_call_req):
781     #     mock_vals = {
782     #         "/api/catalog/v1/vnfpackages/package_id_001":
783     #             [0, json.JSONEncoder().encode(nf_package_info), "200"],
784     #         "/api/resmgr/v1/resource/grant":
785     #             [1, json.JSONEncoder().encode({}), "200"],
786     #         "/cloud-infrastructure/cloud-regions/cloud-region/VCPE/RegionOne?depth=all":
787     #             [0, json.JSONEncoder().encode(vim_info), "201"],
788     #     }
789     #
790     #     def side_effect(*args):
791     #         return mock_vals[args[4]]
792     #
793     #     mock_call_req.side_effect = side_effect
794     #     data = {
795     #         "vnfInstanceId": self.vnf_inst_id,
796     #         "lifecycleOperation": LIFE_CYCLE_OPERATION.INSTANTIATE
797     #     }
798     #     response = self.client.post(self.url, data=data)
799     #     self.assertEqual(response.status_code, status.HTTP_201_CREATED)
800
801     @mock.patch.object(restcall, "call_req")
802     def test_nf_grant_view_when_add_resource(self, mock_call_req):
803         mock_vals = {
804             "/api/catalog/v1/vnfpackages/package_id_001":
805                 [0, json.JSONEncoder().encode(nf_package_info), "200"],
806             "/api/resmgr/v1/resource/grant":
807                 [1, json.JSONEncoder().encode({}), "200"],
808             "/cloud-infrastructure/cloud-regions/cloud-region/VCPE/RegionOne?depth=all":
809                 [0, json.JSONEncoder().encode(vim_info), "201"],
810         }
811
812         def side_effect(*args):
813             return mock_vals[args[4]]
814         mock_call_req.side_effect = side_effect
815         resp = GrantVnfs(json.dumps(self.data), "").send_grant_vnf_to_resMgr()
816         return_success = {"vim": {"accessInfo": {"tenant": "admin"},
817                                   "vimId": "example-cloud-owner-val-97336_example-cloud-region-id-val-35532"}}
818         self.assertEqual(resp, return_success)
819
820     @mock.patch.object(restcall, "call_req")
821     def test_nf_grant_view_when_remove_resource(self, mock_call_req):
822         mock_vals = {
823             "/api/catalog/v1/vnfpackages/package_id_001":
824                 [0, json.JSONEncoder().encode(nf_package_info), "200"],
825             "/api/resmgr/v1/resource/grant":
826                 [1, json.JSONEncoder().encode({}), "200"],
827             "/cloud-infrastructure/cloud-regions/cloud-region/VCPE/RegionOne?depth=all":
828                 [0, json.JSONEncoder().encode(vim_info), "201"],
829         }
830
831         def side_effect(*args):
832             return mock_vals[args[4]]
833
834         mock_call_req.side_effect = side_effect
835         self.data.pop("addResource")
836         self.data["removeResource"] = [{"vdu": "vdu_grant_vnf_remove_resources"}]
837         resp = GrantVnfs(json.dumps(self.data), "").send_grant_vnf_to_resMgr()
838         return_success = {"vim": {"accessInfo": {"tenant": "admin"},
839                                   "vimId": "example-cloud-owner-val-97336_example-cloud-region-id-val-35532"}}
840         self.assertEqual(resp, return_success)
841
842
843 class TestGrantVnfViews(TestCase):
844     def setUp(self):
845         self.vnf_inst_id = str(uuid.uuid4())
846         self.data = {
847             "vnfInstanceId": self.vnf_inst_id,
848             "vnfLcmOpOccId": "vnf_lcm_op_occ_id",
849             "addResources": [{"vdu": "vdu_grant_vnf_add_resources"}],
850             "operation": "INSTANTIATE"
851         }
852         self.client = Client()
853         vdu_info_dict = [{"vduName": "vg", "flavorName": "flavor_1", "flavorId": "flavor_id_001", "directive": []}]
854         OOFDataModel(request_id="request_id_001", transaction_id="transaction_id_001", request_status="done",
855                      request_module_name="vg", service_resource_id=self.vnf_inst_id, vim_id="cloudOwner_casa",
856                      cloud_owner="cloudOwner", cloud_region_id="casa", vdu_info=json.dumps(vdu_info_dict)).save()
857         NfInstModel(mnfinstid=self.vnf_inst_id, nfinstid="vnf_inst_id_001", package_id="package_id_001",
858                     vnfm_inst_id="vnfm_id_001").save()
859
860     def tearDown(self):
861         OOFDataModel.objects.all().delete()
862         NfInstModel.objects.all().delete()
863
864     @mock.patch.object(resmgr, "grant_vnf")
865     def test_vnf_grant_view(self, mock_grant):
866         resmgr_grant_resp = {
867             "vim": {
868                 "vimId": "cloudOwner_casa",
869                 "accessInfo": {
870                     "tenant": "tenantA"
871                 }
872             }
873         }
874         mock_grant.return_value = resmgr_grant_resp
875         self.data.pop("addResources")
876         response = self.client.post("/api/nslcm/v2/grants", data=self.data)
877         self.assertEqual(response.status_code, status.HTTP_201_CREATED)
878         self.assertEqual(response.data["vimAssets"]["computeResourceFlavours"][0]["vimConnectionId"], "cloudOwner_casa")
879         self.assertEqual(response.data["vimAssets"]["computeResourceFlavours"][0]["resourceProviderId"], "vg")
880         self.assertEqual(response.data["vimAssets"]["computeResourceFlavours"][0]["vimFlavourId"], "flavor_id_001")
881
882     @mock.patch.object(restcall, "call_req")
883     @mock.patch.object(resmgr, "grant_vnf")
884     def test_exec_grant_when_add_resources_success(self, mock_grant, mock_call_req):
885         mock_vals = {
886             "/api/catalog/v1/vnfpackages/package_id_001":
887                 [0, json.JSONEncoder().encode(nf_package_info), "200"],
888         }
889
890         def side_effect(*args):
891             return mock_vals[args[4]]
892
893         mock_call_req.side_effect = side_effect
894         resmgr_grant_resp = {
895             "vim": {
896                 "vimId": "cloudOwner_casa",
897                 "accessInfo": {
898                     "tenant": "tenantA"
899                 }
900             }
901         }
902         mock_grant.return_value = resmgr_grant_resp
903         resp = GrantVnf(json.dumps(self.data)).exec_grant()
904         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["vimConnectionId"], "cloudOwner_casa")
905         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["resourceProviderId"], "vg")
906         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["vimFlavourId"], "flavor_id_001")
907
908     def test_exec_grant_when_add_resources_but_no_vnfinst(self):
909         self.data["vnfInstanceId"] = "no_vnfinst"
910         resp = None
911         try:
912             resp = GrantVnf(json.dumps(self.data)).exec_grant()
913         except NSLCMException as e:
914             self.assertEqual(type(e), NSLCMException)
915         finally:
916             self.assertEqual(resp, None)
917
918     @mock.patch.object(time, "sleep")
919     @mock.patch.object(restcall, "call_req")
920     @mock.patch.object(resmgr, "grant_vnf")
921     def test_exec_grant_when_add_resources_but_no_off(self, mock_grant, mock_call_req, mock_sleep):
922         NfInstModel(mnfinstid="add_resources_but_no_off", nfinstid="vnf_inst_id_002",
923                     package_id="package_id_002").save()
924         mock_sleep.return_value = None
925         mock_vals = {
926             "/api/catalog/v1/vnfpackages/package_id_002":
927                 [0, json.JSONEncoder().encode(nf_package_info), "200"],
928         }
929
930         def side_effect(*args):
931             return mock_vals[args[4]]
932
933         mock_call_req.side_effect = side_effect
934         resmgr_grant_resp = {
935             "vim": {
936                 "vimId": "cloudOwner_casa",
937                 "accessInfo": {
938                     "tenant": "tenantA"
939                 }
940             }
941         }
942         mock_grant.return_value = resmgr_grant_resp
943         self.data["vnfInstanceId"] = "add_resources_but_no_off"
944         resp = GrantVnf(json.dumps(self.data)).exec_grant()
945         self.assertEqual(resp["vnfInstanceId"], "add_resources_but_no_off")
946         self.assertEqual(resp["vnfLcmOpOccId"], "vnf_lcm_op_occ_id")
947         vimConnections = [{
948             "id": "cloudOwner_casa",
949             "vimId": "cloudOwner_casa",
950             "vimType": None,
951             "interfaceInfo": None,
952             "accessInfo": {"tenant": "tenantA"},
953             "extra": None
954         }]
955         self.assertEqual(resp["vimConnections"], vimConnections)
956
957     @mock.patch.object(resmgr, "grant_vnf")
958     def test_exec_grant_when_resource_template_in_add_resources(self, mock_grant):
959         resmgr_grant_resp = {
960             "vim": {
961                 "vimId": "cloudOwner_casa",
962                 "accessInfo": {
963                     "tenant": "tenantA"
964                 }
965             }
966         }
967         mock_grant.return_value = resmgr_grant_resp
968         self.data["addResources"] = [{"vdu": "vdu_grant_vnf_add_resources"}, "resourceTemplate"]
969         resp = GrantVnf(json.dumps(self.data)).exec_grant()
970         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["vimConnectionId"], "cloudOwner_casa")
971         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["resourceProviderId"], "vg")
972         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["vimFlavourId"], "flavor_id_001")
973
974     @mock.patch.object(restcall, "call_req")
975     @mock.patch.object(resmgr, "grant_vnf")
976     def test_exec_grant_when_remove_resources_success(self, mock_grant, mock_call_req):
977         mock_vals = {
978             "/api/catalog/v1/vnfpackages/package_id_001":
979                 [0, json.JSONEncoder().encode(nf_package_info), "200"],
980         }
981
982         def side_effect(*args):
983             return mock_vals[args[4]]
984
985         mock_call_req.side_effect = side_effect
986         resmgr_grant_resp = {
987             "vim": {
988                 "vimId": "cloudOwner_casa",
989                 "accessInfo": {
990                     "tenant": "tenantA"
991                 }
992             }
993         }
994         mock_grant.return_value = resmgr_grant_resp
995         self.data.pop("addResources")
996         self.data["removeResources"] = [{"vdu": "vdu_grant_vnf_remove_resources"}]
997         self.data["additionalparams"] = {"vnfmid": "vnfm_id_001"}
998         resp = GrantVnf(json.dumps(self.data)).exec_grant()
999         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["vimConnectionId"], "cloudOwner_casa")
1000         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["resourceProviderId"], "vg")
1001         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["vimFlavourId"], "flavor_id_001")
1002
1003     def test_exec_grant_when_remove_resources_no_vnfinst(self):
1004         self.data.pop("addResources")
1005         self.data["removeResources"] = [{"vdu": "vdu_grant_vnf_remove_resources"}]
1006         self.data["additionalparams"] = {"vnfmid": "vnfm_id_002"}
1007         resp = None
1008         try:
1009             resp = GrantVnf(json.dumps(self.data)).exec_grant()
1010         except NSLCMException as e:
1011             self.assertEqual(type(e), NSLCMException)
1012         finally:
1013             self.assertEqual(resp, None)
1014
1015     @mock.patch.object(time, "sleep")
1016     @mock.patch.object(restcall, "call_req")
1017     @mock.patch.object(resmgr, "grant_vnf")
1018     def test_exec_grant_when_remove_resources_but_no_off(self, mock_grant, mock_call_req, mock_sleep):
1019         NfInstModel(mnfinstid="remove_resources_but_no_off", nfinstid="vnf_inst_id_002", package_id="package_id_002",
1020                     vnfm_inst_id="vnfm_id_002").save()
1021         mock_sleep.return_value = None
1022         mock_vals = {
1023             "/api/catalog/v1/vnfpackages/package_id_002":
1024                 [0, json.JSONEncoder().encode(nf_package_info), "200"],
1025         }
1026
1027         def side_effect(*args):
1028             return mock_vals[args[4]]
1029
1030         mock_call_req.side_effect = side_effect
1031         resmgr_grant_resp = {
1032             "vim": {
1033                 "vimId": "cloudOwner_casa",
1034                 "accessInfo": {
1035                     "tenant": "tenantA"
1036                 }
1037             }
1038         }
1039         mock_grant.return_value = resmgr_grant_resp
1040         self.data["vnfInstanceId"] = "remove_resources_but_no_off"
1041         self.data.pop("addResources")
1042         self.data["removeResources"] = [{"vdu": "vdu_grant_vnf_remove_resources"}]
1043         self.data["additionalparams"] = {"vnfmid": "vnfm_id_002"}
1044         resp = GrantVnf(json.dumps(self.data)).exec_grant()
1045         self.assertEqual(resp["vnfInstanceId"], "remove_resources_but_no_off")
1046         self.assertEqual(resp["vnfLcmOpOccId"], "vnf_lcm_op_occ_id")
1047         vimConnections = [{
1048             "id": "cloudOwner_casa",
1049             "vimId": "cloudOwner_casa",
1050             "vimType": None,
1051             "interfaceInfo": None,
1052             "accessInfo": {"tenant": "tenantA"},
1053             "extra": None
1054         }]
1055         self.assertEqual(resp["vimConnections"], vimConnections)
1056
1057     @mock.patch.object(resmgr, "grant_vnf")
1058     def test_exec_grant_when_resource_template_in_remove_resources(self, mock_grant):
1059         resmgr_grant_resp = {
1060             "vim": {
1061                 "vimId": "cloudOwner_casa",
1062                 "accessInfo": {
1063                     "tenant": "tenantA"
1064                 }
1065             }
1066         }
1067         mock_grant.return_value = resmgr_grant_resp
1068         self.data.pop("addResources")
1069         self.data["removeResources"] = [{"vdu": "vdu_grant_vnf_remove_resources"}, "resourceTemplate"]
1070         resp = GrantVnf(json.dumps(self.data)).exec_grant()
1071         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["vimConnectionId"], "cloudOwner_casa")
1072         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["resourceProviderId"], "vg")
1073         self.assertEqual(resp["vimAssets"]["computeResourceFlavours"][0]["vimFlavourId"], "flavor_id_001")
1074
1075
1076 class TestCreateVnfViews(TestCase):
1077     def setUp(self):
1078         self.ns_inst_id = str(uuid.uuid4())
1079         self.job_id = str(uuid.uuid4())
1080         self.data = {
1081             "vnfIndex": "1",
1082             "nsInstanceId": self.ns_inst_id,
1083             # "additionalParamForNs": {"inputs": json.dumps({})},
1084             "additionalParamForVnf": [
1085                 {
1086                     "vnfprofileid": "VBras",
1087                     "additionalparam": {
1088                         "inputs": json.dumps({
1089                             "vnf_param1": "11",
1090                             "vnf_param2": "22"
1091                         }),
1092                         "vnfminstanceid": "1",
1093                         # "vimId": "zte_test",
1094                         "vimId": '{"cloud_owner": "VCPE", "cloud_regionid": "RegionOne"}'
1095                     }
1096                 }
1097             ]
1098         }
1099         self.client = Client()
1100         NSInstModel(id=self.ns_inst_id, name="ns", nspackage_id="1", nsd_id="nsd_id", description="description",
1101                     status="instantiating", nsd_model=json.dumps(nsd_model_dict), create_time=now_time(),
1102                     lastuptime=now_time()).save()
1103         VLInstModel(vldid="ext_mnet_network", ownertype=OWNER_TYPE.NS, ownerid=self.ns_inst_id,
1104                     vimid="{}").save()
1105
1106     def tearDown(self):
1107         NfInstModel.objects.all().delete()
1108         JobModel.objects.all().delete()
1109
1110     @mock.patch.object(CreateVnfs, "run")
1111     def test_create_vnf_view(self, mock_run):
1112         response = self.client.post("/api/nslcm/v1/ns/vnfs", data=self.data)
1113         self.assertEqual(status.HTTP_202_ACCEPTED, response.status_code)
1114         context = json.loads(response.content)
1115         self.assertTrue(NfInstModel.objects.filter(nfinstid=context["vnfInstId"]).exists())
1116
1117     @mock.patch.object(time, "sleep")
1118     @mock.patch.object(restcall, "call_req")
1119     def test_create_vnf_thread_sucess(self, mock_call_req, mock_sleep):
1120         mock_sleep.return_value = None
1121         nf_inst_id, job_id = create_vnfs.prepare_create_params()
1122         mock_vals = {
1123             "/api/catalog/v1/vnfpackages/zte_vbras":
1124                 [0, json.JSONEncoder().encode(nf_package_info), "200"],
1125             "/external-system/esr-vnfm-list/esr-vnfm/1?depth=all":
1126                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
1127             "/api/ztevnfmdriver/v1/1/vnfs":
1128                 [0, json.JSONEncoder().encode({"jobId": self.job_id, "vnfInstanceId": 3}), "200"],
1129             "/api/oof/v1/placement":
1130                 [0, json.JSONEncoder().encode({}), "202"],
1131             "/api/resmgr/v1/vnf":
1132                 [0, json.JSONEncoder().encode({}), "200"],
1133             "/api/ztevnfmdriver/v1/1/jobs/" + self.job_id + "?responseId=0":
1134                 [0, json.JSONEncoder().encode({"jobid": self.job_id,
1135                                                "responsedescriptor": {"progress": "100",
1136                                                                       "status": JOB_MODEL_STATUS.FINISHED,
1137                                                                       "responseid": "3",
1138                                                                       "statusdescription": "creating",
1139                                                                       "errorcode": "0",
1140                                                                       "responsehistorylist": [
1141                                                                           {"progress": "0",
1142                                                                            "status": JOB_MODEL_STATUS.PROCESSING,
1143                                                                            "responseid": "2",
1144                                                                            "statusdescription": "creating",
1145                                                                            "errorcode": "0"}]}}), "200"],
1146             "api/gvnfmdriver/v1/1/subscriptions":
1147                 [0, json.JSONEncoder().encode({}), "200"],
1148             "/api/resmgr/v1/vnfinfo":
1149                 [0, json.JSONEncoder().encode(subscription_response_data), "200"],
1150
1151             # "/network/generic-vnfs/generic-vnf/%s" % nf_inst_id:
1152             #     [0, json.JSONEncoder().encode({}), "201"],
1153             # "/cloud-infrastructure/cloud-regions/cloud-region/zte/test?depth=all":
1154             #     [0, json.JSONEncoder().encode(vim_info), "201"],
1155             # "/cloud-infrastructure/cloud-regions/cloud-region/zte/test/tenants/tenant/admin/vservers/vserver/1":
1156             #     [0, json.JSONEncoder().encode({}), "201"],
1157
1158         }
1159
1160         def side_effect(*args):
1161             return mock_vals[args[4]]
1162         mock_call_req.side_effect = side_effect
1163         data = {
1164             "ns_instance_id": ignore_case_get(self.data, "nsInstanceId"),
1165             "additional_param_for_ns": ignore_case_get(self.data, "additionalParamForNs"),
1166             "additional_param_for_vnf": ignore_case_get(self.data, "additionalParamForVnf"),
1167             "vnf_index": ignore_case_get(self.data, "vnfIndex")
1168         }
1169         CreateVnfs(data, nf_inst_id, job_id).run()
1170         self.assertEqual(NfInstModel.objects.get(nfinstid=nf_inst_id).status, VNF_STATUS.ACTIVE)
1171         self.assertEqual(JobModel.objects.get(jobid=job_id).progress, JOB_PROGRESS.FINISHED)
1172
1173     def test_create_vnf_thread_when_the_name_of_vnf_instance_already_exists(self):
1174         NfInstModel(nf_name="").save()
1175         nf_inst_id, job_id = create_vnfs.prepare_create_params()
1176         data = {
1177             "ns_instance_id": ignore_case_get(self.data, "nsInstanceId"),
1178             "additional_param_for_ns": ignore_case_get(self.data, "additionalParamForNs"),
1179             "additional_param_for_vnf": ignore_case_get(self.data, "additionalParamForVnf"),
1180             "vnf_index": ignore_case_get(self.data, "vnfIndex")
1181         }
1182         CreateVnfs(data, nf_inst_id, job_id).run()
1183         self.assertEqual(NfInstModel.objects.get(nfinstid=nf_inst_id).status, VNF_STATUS.FAILED)
1184         self.assertEqual(JobModel.objects.get(jobid=job_id).progress, JOB_PROGRESS.ERROR)
1185
1186     @mock.patch.object(time, "sleep")
1187     @mock.patch.object(restcall, "call_req")
1188     def test_create_vnf_thread_when_data_has_vnfd_id(self, mock_call_req, mock_sleep):
1189         mock_sleep.return_value = None
1190         nf_inst_id, job_id = create_vnfs.prepare_create_params()
1191         mock_vals = {
1192             "/api/catalog/v1/vnfpackages/data_has_vnfd_id":
1193                 [0, json.JSONEncoder().encode(nf_package_info), "200"],
1194             "/external-system/esr-vnfm-list/esr-vnfm/1?depth=all":
1195                 [0, json.JSONEncoder().encode(vnfm_info), "200"],
1196             "/api/ztevnfmdriver/v1/1/vnfs":
1197                 [0, json.JSONEncoder().encode({"jobId": self.job_id, "vnfInstanceId": 3}), "200"],
1198             "/api/oof/v1/placement":
1199                 [0, json.JSONEncoder().encode({}), "202"],
1200             "/api/resmgr/v1/vnf":
1201                 [0, json.JSONEncoder().encode({}), "200"],
1202             "/api/ztevnfmdriver/v1/1/jobs/" + self.job_id + "?responseId=0":
1203                 [0, json.JSONEncoder().encode({"jobid": self.job_id,
1204                                                "responsedescriptor": {"progress": "100",
1205                                                                       "status": JOB_MODEL_STATUS.FINISHED,
1206                                                                       "responseid": "3",
1207                                                                       "statusdescription": "creating",
1208                                                                       "errorcode": "0",
1209                                                                       "responsehistorylist": [
1210                                                                           {"progress": "0",
1211                                                                            "status": JOB_MODEL_STATUS.PROCESSING,
1212                                                                            "responseid": "2",
1213                                                                            "statusdescription": "creating",
1214                                                                            "errorcode": "0"}]}}), "200"],
1215             "api/gvnfmdriver/v1/1/subscriptions":
1216                 [0, json.JSONEncoder().encode({}), "200"],
1217             "/api/resmgr/v1/vnfinfo":
1218                 [0, json.JSONEncoder().encode(subscription_response_data), "200"]
1219         }
1220
1221         def side_effect(*args):
1222             return mock_vals[args[4]]
1223
1224         mock_call_req.side_effect = side_effect
1225         self.data["additionalParamForVnf"][0]["additionalparam"]["vnfdId"] = "data_has_vnfd_id"
1226         data = {
1227             "ns_instance_id": ignore_case_get(self.data, "nsInstanceId"),
1228             "additional_param_for_ns": ignore_case_get(self.data, "additionalParamForNs"),
1229             "additional_param_for_vnf": ignore_case_get(self.data, "additionalParamForVnf"),
1230             "vnf_index": ignore_case_get(self.data, "vnfIndex")
1231         }
1232         CreateVnfs(data, nf_inst_id, job_id).run()
1233         self.assertEqual(NfInstModel.objects.get(nfinstid=nf_inst_id).status, VNF_STATUS.ACTIVE)
1234         self.assertEqual(JobModel.objects.get(jobid=job_id).progress, JOB_PROGRESS.FINISHED)
1235
1236     @mock.patch.object(restcall, "call_req")
1237     @mock.patch.object(CreateVnfs, "build_homing_request")
1238     def test_send_homing_request(self, mock_build_req, mock_call_req):
1239         nf_inst_id, job_id = create_vnfs.prepare_create_params()
1240         OOFDataModel.objects.all().delete()
1241         resp = {
1242             "requestId": "1234",
1243             "transactionId": "1234",
1244             "requestStatus": "accepted"
1245         }
1246         mock_build_req.return_value = {
1247             "requestInfo": {
1248                 "transactionId": "1234",
1249                 "requestId": "1234",
1250                 "callbackUrl": "xx",
1251                 "sourceId": "vfc",
1252                 "requestType": "create",
1253                 "numSolutions": 1,
1254                 "optimizers": ["placement"],
1255                 "timeout": 600
1256             },
1257             "placementInfo": {
1258                 "placementDemands": [
1259                     {
1260                         "resourceModuleName": "vG",
1261                         "serviceResourceId": "1234",
1262                         "resourceModelInfo": {
1263                             "modelInvariantId": "1234",
1264                             "modelVersionId": "1234"
1265                         }
1266                     }
1267                 ]
1268             },
1269             "serviceInfo": {
1270                 "serviceInstanceId": "1234",
1271                 "serviceName": "1234",
1272                 "modelInfo": {
1273                     "modelInvariantId": "5678",
1274                     "modelVersionId": "7890"
1275                 }
1276             }
1277         }
1278         mock_call_req.return_value = [0, json.JSONEncoder().encode(resp), "202"]
1279         data = {
1280             "ns_instance_id": ignore_case_get(self.data, "nsInstanceId"),
1281             "additional_param_for_ns": ignore_case_get(self.data, "additionalParamForNs"),
1282             "additional_param_for_vnf": ignore_case_get(self.data, "additionalParamForVnf"),
1283             "vnf_index": ignore_case_get(self.data, "vnfIndex")
1284         }
1285         CreateVnfs(data, nf_inst_id, job_id).send_homing_request_to_OOF()
1286         ret = OOFDataModel.objects.filter(request_id="1234", transaction_id="1234")
1287         self.assertIsNotNone(ret)