aboutsummaryrefslogtreecommitdiffstats
path: root/tests/test_pnf.py
diff options
context:
space:
mode:
Diffstat (limited to 'tests/test_pnf.py')
-rw-r--r--tests/test_pnf.py485
1 files changed, 485 insertions, 0 deletions
diff --git a/tests/test_pnf.py b/tests/test_pnf.py
new file mode 100644
index 0000000..0f606a0
--- /dev/null
+++ b/tests/test_pnf.py
@@ -0,0 +1,485 @@
+"""Test pnf module."""
+# Copyright 2022 Orange, Deutsche Telekom AG
+#
+# 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.
+
+from unittest import mock
+from unittest.mock import MagicMock
+from pathlib import Path
+
+import pytest
+
+import onapsdk.constants as const
+from onapsdk.exceptions import ParameterError, RequestError, StatusError
+from onapsdk.sdc.category_management import ResourceCategory
+from onapsdk.sdc.properties import Property
+from onapsdk.sdc.sdc_resource import SdcResource
+from onapsdk.sdc.pnf import Pnf
+from onapsdk.sdc.vsp import Vsp
+from onapsdk.sdc.vsp import Vendor
+
+
+@mock.patch.object(Pnf, 'send_message_json')
+def test_get_all_no_pnf(mock_send):
+ """Returns empty array if no pnfs."""
+ mock_send.return_value = {}
+ assert Pnf.get_all() == []
+ mock_send.assert_called_once_with("GET", 'get Pnfs', 'https://sdc.api.be.simpledemo.onap.org:30204/sdc/v1/catalog/resources?resourceType=PNF')
+
+
+@mock.patch.object(Pnf, 'send_message_json')
+def test_get_all_some_pnfs(mock_send):
+ """Returns a list of pnfs."""
+ mock_send.return_value = [
+ {'resourceType': 'PNF', 'name': 'one', 'uuid': '1234', 'invariantUUID': '5678', 'version': '1.0', 'lifecycleState': 'CERTIFIED', 'category': 'Generic', "subCategory": "Abstract"},
+ {'resourceType': 'PNF', 'name': 'two', 'uuid': '1235', 'invariantUUID': '5679', 'version': '1.0', 'lifecycleState': 'NOT_CERTIFIED_CHECKOUT', 'category': 'Generic', "subCategory": "Abstract"}]
+ all_pnfs = Pnf.get_all()
+ assert len(all_pnfs) == 2
+ pnf_1 = all_pnfs[0]
+ assert pnf_1.name == "one"
+ assert pnf_1.identifier == "1234"
+ assert pnf_1.unique_uuid == "5678"
+ assert pnf_1.version == "1.0"
+ assert pnf_1.status == const.CERTIFIED
+ assert pnf_1.created()
+ pnf_2 = all_pnfs[1]
+ assert pnf_2.name == "two"
+ assert pnf_2.identifier == "1235"
+ assert pnf_2.unique_uuid == "5679"
+ assert pnf_2.status == const.DRAFT
+ assert pnf_2.version == "1.0"
+ assert pnf_2.created()
+ mock_send.assert_called_once_with("GET", 'get Pnfs', 'https://sdc.api.be.simpledemo.onap.org:30204/sdc/v1/catalog/resources?resourceType=PNF')
+
+
+def test_init_no_name():
+ """Check init with no names."""
+ pnf = Pnf()
+ assert isinstance(pnf, SdcResource)
+ assert pnf._identifier is None
+ assert pnf._version is None
+ assert pnf.name == "ONAP-test-PNF"
+ assert pnf.headers["USER_ID"] == "cs0008"
+ assert pnf.vsp is None
+ assert pnf.vendor is None
+ assert isinstance(pnf._base_url(), str)
+
+@mock.patch.object(Pnf, 'exists')
+def test_init_with_name(mock_exists):
+ """Check init with names."""
+ mock_exists.return_value = False
+ pnf = Pnf(name="YOLO")
+ assert pnf._identifier == None
+ assert pnf._version == None
+ assert pnf.name == "YOLO"
+ assert pnf.created() == False
+ assert pnf.headers["USER_ID"] == "cs0008"
+ assert pnf.vsp == None
+ assert isinstance(pnf._base_url(), str)
+
+
+def test_equality_really_equals():
+ """Check two pnfs are equals if name is the same."""
+ pnf_1 = Pnf(name="equal")
+ pnf_1.identifier = "1234"
+ pnf_2 = Pnf(name="equal")
+ pnf_2.identifier = "1235"
+ assert pnf_1 == pnf_2
+
+
+def test_equality_not_equals():
+ """Check two pnfs are not equals if name is not the same."""
+ pnf_1 = Pnf(name="equal")
+ pnf_1.identifier = "1234"
+ pnf_2 = Pnf(name="not_equal")
+ pnf_2.identifier = "1234"
+ assert pnf_1 != pnf_2
+
+
+def test_equality_not_equals_not_same_object():
+ """Check a pnf and something different are not equals."""
+ pnf_1 = Pnf(name="equal")
+ pnf_1.identifier = "1234"
+ pnf_2 = SdcResource()
+ pnf_2.name = "equal"
+ assert pnf_1 != pnf_2
+
+
+@mock.patch.object(Pnf, 'get_all')
+def test_exists_not_exists(mock_get_all):
+ """Return False if pnf doesn't exist in SDC."""
+ pnf_1 = Pnf(name="one")
+ pnf_1.identifier = "1234"
+ mock_get_all.return_value = [pnf_1]
+ pnf = Pnf(name="two")
+ assert not pnf.exists()
+
+
+@mock.patch.object(Pnf, 'get_all')
+def test_exists(mock_get_all):
+ """Return True if pnf exists in SDC."""
+ pnf_1 = Pnf(name="one")
+ pnf_1.identifier = "1234"
+ pnf_1.unique_uuid = "5689"
+ pnf_1.unique_identifier = "71011"
+ pnf_1.status = const.DRAFT
+ pnf_1.version = "1.1"
+ mock_get_all.return_value = [pnf_1]
+ pnf = Pnf(name="one")
+ assert pnf.exists()
+ assert pnf.identifier == "1234"
+ assert pnf.unique_uuid == "5689"
+ assert pnf.unique_identifier == "71011"
+ assert pnf.status == const.DRAFT
+ assert pnf.version == "1.1"
+
+
+@mock.patch.object(Pnf, 'exists')
+def test_load_created(mock_exists):
+ """Load is a wrapper around exists()."""
+ pnf = Pnf(name="one")
+ pnf.load()
+ mock_exists.assert_called_once()
+
+
+@mock.patch.object(Pnf, 'exists')
+def test_create_no_vsp_no_vendor(mock_exists):
+ """Do nothing if no vsp and no vendor"""
+ pnf = Pnf()
+ mock_exists.return_value = False
+ with pytest.raises(ParameterError) as err:
+ pnf.create()
+ assert err.type == ParameterError
+ assert str(err.value) == "Neither Vsp nor Vendor provided."
+
+
+@mock.patch.object(Pnf, 'exists')
+@mock.patch.object(Pnf, 'send_message_json')
+@mock.patch.object(Pnf, "category")
+def test_create_already_exists(mock_category, mock_send, mock_exists):
+ """Do nothing if already created in SDC."""
+ pnf = Pnf()
+ vsp = Vsp()
+ vsp._identifier = "1232"
+ pnf.vsp = vsp
+ mock_exists.return_value = True
+ pnf.create()
+ mock_send.assert_not_called()
+
+
+@mock.patch.object(Pnf, 'exists')
+@mock.patch.object(Pnf, 'send_message_json')
+@mock.patch.object(Pnf, "category", new_callable=mock.PropertyMock)
+def test_create_issue_in_creation(mock_category, mock_send, mock_exists):
+# def test_create_issue_in_creation(mock_send, mock_exists):
+ """Do nothing if not created but issue during creation."""
+ pnf = Pnf()
+ vsp = Vsp()
+ vendor = Vendor()
+ vsp._identifier = "1232"
+ vsp.create_csar = MagicMock(return_value=True)
+ vsp.vendor = vendor
+ pnf.vsp = vsp
+ expected_data = '{\n "artifacts": {},\n "attributes": [],\n "capabilities": {},\n "categories": [\n {\n "normalizedName": "generic",\n "name": "Generic",\n "uniqueId": "resourceNewCategory.generic",\n "subcategories": [{"empty": false, "groupings": null, "icons": ["objectStorage", "compute"], "name": "Abstract", "normalizedName": "abstract", "ownerId": null, "type": null, "uniqueId": "resourceNewCategory.generic.abstract", "version": null}],\n "version": null,\n "ownerId": null,\n "empty": false,\n "type": null,\n "icons": null\n }\n ],\n "componentInstances": [],\n "componentInstancesAttributes": {},\n "componentInstancesProperties": {},\n "componentType": "RESOURCE",\n "contactId": "cs0008",\n \n "csarUUID": "None",\n "csarVersion": "1.0",\n "vendorName": "Generic-Vendor",\n \n "deploymentArtifacts": {},\n "description": "PNF",\n "icon": "defaulticon",\n "name": "ONAP-test-PNF",\n "properties": [],\n "groups": [],\n "requirements": {},\n "resourceType": "PNF",\n "tags": ["ONAP-test-PNF"],\n "toscaArtifacts": {},\n "vendorRelease": "1.0"\n}'
+ mock_exists.return_value = False
+ mock_send.side_effect = RequestError
+ rc = ResourceCategory(
+ name="Generic"
+ )
+ rc.normalized_name="generic"
+ rc.unique_id="resourceNewCategory.generic"
+ rc.subcategories=[{"empty": False, "groupings": None, "icons": ["objectStorage", "compute"], "name": "Abstract", "normalizedName": "abstract", "ownerId": None, "type": None, "uniqueId": "resourceNewCategory.generic.abstract", "version": None}]
+ rc.version=None
+ rc.owner_id=None
+ rc.empty=False
+ rc.type=None
+ rc.icons=None
+ mock_category.return_value = rc
+ with pytest.raises(RequestError) as exc:
+ pnf.create()
+ mock_send.assert_called_once_with("POST", "create Pnf", 'https://sdc.api.fe.simpledemo.onap.org:30207/sdc1/feProxy/rest/v1/catalog/resources', data=expected_data)
+ assert not pnf.created()
+
+
+@mock.patch.object(Pnf, 'exists')
+@mock.patch.object(Pnf, 'send_message_json')
+@mock.patch.object(Pnf, "category", new_callable=mock.PropertyMock)
+def test_create_OK(mock_category, mock_send, mock_exists):
+ """Create and update object."""
+ pnf = Pnf()
+ vsp = Vsp()
+ vendor = Vendor()
+ vsp._identifier = "1232"
+ pnf.vsp = vsp
+ vsp.vendor = vendor
+ vsp._csar_uuid = "1234"
+ expected_data = '{\n "artifacts": {},\n "attributes": [],\n "capabilities": {},\n "categories": [\n {\n "normalizedName": "generic",\n "name": "Generic",\n "uniqueId": "resourceNewCategory.generic",\n "subcategories": [{"empty": false, "groupings": null, "icons": ["objectStorage", "compute"], "name": "Abstract", "normalizedName": "abstract", "ownerId": null, "type": null, "uniqueId": "resourceNewCategory.generic.abstract", "version": null}],\n "version": null,\n "ownerId": null,\n "empty": false,\n "type": null,\n "icons": null\n }\n ],\n "componentInstances": [],\n "componentInstancesAttributes": {},\n "componentInstancesProperties": {},\n "componentType": "RESOURCE",\n "contactId": "cs0008",\n \n "csarUUID": "1234",\n "csarVersion": "1.0",\n "vendorName": "Generic-Vendor",\n \n "deploymentArtifacts": {},\n "description": "PNF",\n "icon": "defaulticon",\n "name": "ONAP-test-PNF",\n "properties": [],\n "groups": [],\n "requirements": {},\n "resourceType": "PNF",\n "tags": ["ONAP-test-PNF"],\n "toscaArtifacts": {},\n "vendorRelease": "1.0"\n}'
+ mock_exists.return_value = False
+ mock_send.return_value = {'resourceType': 'PNF', 'name': 'one', 'uuid': '1234', 'invariantUUID': '5678', 'version': '1.0', 'uniqueId': '91011', 'lifecycleState': 'NOT_CERTIFIED_CHECKOUT'}
+ rc = ResourceCategory(
+ name="Generic"
+ )
+ rc.normalized_name="generic"
+ rc.unique_id="resourceNewCategory.generic"
+ rc.subcategories=[{"empty": False, "groupings": None, "icons": ["objectStorage", "compute"], "name": "Abstract", "normalizedName": "abstract", "ownerId": None, "type": None, "uniqueId": "resourceNewCategory.generic.abstract", "version": None}]
+ rc.version=None
+ rc.owner_id=None
+ rc.empty=False
+ rc.type=None
+ rc.icons=None
+ mock_category.return_value = rc
+ pnf.create()
+ mock_send.assert_called_once_with("POST", "create Pnf", 'https://sdc.api.fe.simpledemo.onap.org:30207/sdc1/feProxy/rest/v1/catalog/resources', data=expected_data)
+ assert pnf.created()
+ assert pnf._status == const.DRAFT
+ assert pnf.identifier == "1234"
+ assert pnf.unique_uuid == "5678"
+ assert pnf.version == "1.0"
+
+@mock.patch.object(Pnf, 'exists')
+@mock.patch.object(Pnf, 'load')
+def test_version_no_load_no_created(mock_load, mock_exists):
+ """Test versions when not created."""
+ mock_exists.return_value = False
+ pnf = Pnf()
+ assert pnf.version is None
+ mock_load.assert_not_called()
+
+@mock.patch.object(Pnf, 'load')
+def test_version_no_load_created(mock_load):
+ """Test versions when created."""
+ pnf = Pnf()
+ pnf.identifier = "1234"
+ pnf._version = "64"
+ assert pnf.version == "64"
+ mock_load.assert_not_called()
+
+
+@mock.patch.object(Pnf, 'load')
+def test_version_with_load(mock_load):
+ """Test versions when not created but with identifier."""
+ pnf = Pnf()
+ pnf.identifier = "1234"
+ assert pnf.version is None
+ mock_load.assert_called_once()
+
+@mock.patch.object(Pnf, 'exists')
+@mock.patch.object(Pnf, 'load')
+def test_status_no_load_no_created(mock_load, mock_exists):
+ """Test status when not created."""
+ mock_exists.return_value = False
+ pnf = Pnf()
+ assert pnf.status is None
+
+
+@pytest.mark.parametrize("status", [const.COMMITED, const.CERTIFIED, const.UPLOADED, const.VALIDATED])
+@mock.patch.object(Pnf, 'exists')
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'send_message')
+def test_submit_not_Commited(mock_send, mock_load, mock_exists, status):
+ """Do nothing if not created."""
+ mock_exists.return_value = False
+ pnf = Pnf()
+ pnf._status = status
+ pnf.submit()
+ mock_send.assert_not_called()
+
+@mock.patch.object(Pnf, 'exists')
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'send_message')
+def test_submit_OK(mock_send, mock_load, mock_exists):
+ """Don't update status if submission NOK."""
+ mock_exists.return_value = True
+ pnf = Pnf()
+ pnf._status = const.COMMITED
+ expected_data = '{\n "userRemarks": "certify"\n}'
+ pnf._version = "1234"
+ pnf._unique_identifier = "12345"
+ pnf.submit()
+ mock_send.assert_called_once_with(
+ "POST", "Certify Pnf",
+ 'https://sdc.api.fe.simpledemo.onap.org:30207/sdc1/feProxy/rest/v1/catalog/resources/12345/lifecycleState/Certify',
+ data=expected_data)
+
+
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'certify')
+@mock.patch.object(Pnf, 'submit')
+@mock.patch.object(Pnf, 'create')
+def test_onboard_new_pnf(mock_create, mock_submit, mock_certify, mock_load):
+ getter_mock = mock.Mock(wraps=Pnf.status.fget)
+ mock_status = Pnf.status.getter(getter_mock)
+ with mock.patch.object(Pnf, 'status', mock_status):
+ getter_mock.side_effect = [None, const.APPROVED, const.APPROVED,
+ const.APPROVED, const.APPROVED]
+ vsp = Vsp()
+ pnf = Pnf(vsp=vsp)
+ pnf._time_wait = 0
+ pnf.onboard()
+ mock_create.assert_called_once()
+ mock_submit.assert_not_called()
+ mock_certify.assert_not_called()
+ mock_load.assert_not_called()
+
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'certify')
+@mock.patch.object(Pnf, 'submit')
+@mock.patch.object(Pnf, 'create')
+def test_onboard_pnf_submit(mock_create, mock_submit, mock_certify, mock_load):
+ getter_mock = mock.Mock(wraps=Pnf.status.fget)
+ mock_status = Pnf.status.getter(getter_mock)
+ with mock.patch.object(Pnf, 'status', mock_status):
+ getter_mock.side_effect = [const.DRAFT, const.DRAFT, const.APPROVED,
+ const.APPROVED, const.APPROVED, const.APPROVED]
+ pnf = Pnf()
+ pnf._time_wait = 0
+ pnf.onboard()
+ mock_create.assert_not_called()
+ mock_submit.assert_called_once()
+ mock_certify.assert_not_called()
+ mock_load.assert_not_called()
+
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'certify')
+@mock.patch.object(Pnf, 'submit')
+@mock.patch.object(Pnf, 'create')
+def test_onboard_pnf_certify(mock_create, mock_submit, mock_certify, mock_load):
+ getter_mock = mock.Mock(wraps=Pnf.status.fget)
+ mock_status = Pnf.status.getter(getter_mock)
+ with mock.patch.object(Pnf, 'status', mock_status):
+ getter_mock.side_effect = [const.CHECKED_IN, const.CHECKED_IN, const.CHECKED_IN,
+ const.APPROVED, const.APPROVED, const.APPROVED,
+ const.APPROVED]
+ pnf = Pnf()
+ pnf._time_wait = 0
+ pnf.onboard()
+ mock_create.assert_not_called()
+ mock_submit.assert_not_called()
+ mock_certify.assert_called_once()
+ mock_load.assert_not_called()
+
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'certify')
+@mock.patch.object(Pnf, 'submit')
+@mock.patch.object(Pnf, 'create')
+def test_onboard_pnf_load(mock_create, mock_submit, mock_certify, mock_load):
+ getter_mock = mock.Mock(wraps=Pnf.status.fget)
+ mock_status = Pnf.status.getter(getter_mock)
+ with mock.patch.object(Pnf, 'status', mock_status):
+ getter_mock.side_effect = [const.CERTIFIED, const.CERTIFIED,
+ const.CERTIFIED, const.CERTIFIED,
+ const.APPROVED, const.APPROVED,
+ const.APPROVED]
+ pnf = Pnf()
+ pnf._time_wait = 0
+ pnf.onboard()
+ mock_create.assert_not_called()
+ mock_submit.assert_not_called()
+ mock_certify.assert_not_called()
+ mock_load.assert_called_once()
+
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'submit')
+@mock.patch.object(Pnf, 'create')
+@mock.patch.object(Pnf, 'certify')
+def test_onboard_whole_pnf_vsp(mock_certify, mock_create, mock_submit, mock_load):
+ """Test onboarding with vsp"""
+ getter_mock = mock.Mock(wraps=Pnf.status.fget)
+ mock_status = Pnf.status.getter(getter_mock)
+ with mock.patch.object(Pnf, 'status', mock_status):
+ getter_mock.side_effect = [None, const.DRAFT, const.DRAFT,
+ const.CHECKED_IN, const.CHECKED_IN, const.CHECKED_IN,
+ const.CERTIFIED, const.CERTIFIED, const.CERTIFIED,
+ const.CERTIFIED, const.APPROVED, const.APPROVED,
+ const.APPROVED, const.APPROVED]
+ vsp = Vsp()
+ pnf = Pnf(vsp=vsp)
+ pnf._time_wait = 0
+ pnf.onboard()
+ mock_create.assert_called_once()
+ mock_submit.assert_called_once()
+ mock_load.assert_called_once()
+ mock_certify.assert_called_once()
+
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'submit')
+@mock.patch.object(Pnf, 'create')
+@mock.patch.object(Pnf, 'certify')
+def test_onboard_whole_pnf_vendor(mock_certify, mock_create, mock_submit, mock_load):
+ """Test onboarding with vendor"""
+ getter_mock = mock.Mock(wraps=Pnf.status.fget)
+ mock_status = Pnf.status.getter(getter_mock)
+ with mock.patch.object(Pnf, 'status', mock_status):
+ getter_mock.side_effect = [None, const.DRAFT, const.DRAFT,
+ const.CHECKED_IN, const.CHECKED_IN, const.CHECKED_IN,
+ const.CERTIFIED, const.CERTIFIED, const.CERTIFIED,
+ const.CERTIFIED, const.APPROVED, const.APPROVED,
+ const.APPROVED, const.APPROVED]
+ vendor = Vendor()
+ pnf = Pnf(vendor=vendor)
+ pnf._time_wait = 0
+ pnf.onboard()
+ mock_create.assert_called_once()
+ mock_submit.assert_called_once()
+ mock_load.assert_called_once()
+ mock_certify.assert_called_once()
+
+@mock.patch.object(Pnf, "send_message_json")
+def test_add_properties(mock_send_message_json):
+ pnf = Pnf(name="test")
+ pnf._identifier = "toto"
+ pnf._unique_identifier = "toto"
+ pnf._status = const.CERTIFIED
+ with pytest.raises(StatusError) as err:
+ pnf.add_property(Property(name="test", property_type="string"))
+ pnf._status = const.DRAFT
+ pnf.add_property(Property(name="test", property_type="string"))
+ mock_send_message_json.assert_called_once()
+
+@mock.patch.object(Pnf, 'load')
+@mock.patch.object(Pnf, 'send_message')
+def test_add_artifact_to_pnf(mock_send_message, mock_load):
+ """Test Pnf add artifact"""
+ pnf = Pnf(name="test")
+ pnf.status = const.DRAFT
+ mycbapath = Path(Path(__file__).resolve().parent, "data/vLB_CBA_Python.zip")
+
+ result = pnf.add_deployment_artifact(artifact_label="cba",
+ artifact_type="CONTROLLER_BLUEPRINT_ARCHIVE",
+ artifact_name="vLB_CBA_Python.zip",
+ artifact=mycbapath)
+ mock_send_message.assert_called()
+ method, description, url = mock_send_message.call_args[0]
+ assert method == "POST"
+ assert description == "Add deployment artifact for test sdc resource"
+ assert url == ("https://sdc.api.fe.simpledemo.onap.org:30207/sdc1/feProxy/rest/v1/catalog/resources/"
+ f"{pnf.unique_identifier}/artifacts")
+
+
+@mock.patch.object(Pnf, "created")
+@mock.patch.object(ResourceCategory, "get")
+def test_pnf_category(mock_resource_category, mock_created):
+ mock_created.return_value = False
+ pnf = Pnf(name="test")
+ _ = pnf.category
+ mock_resource_category.assert_called_once_with(name="Generic", subcategory="Abstract")
+ mock_resource_category.reset_mock()
+
+ pnf = Pnf(name="test", category="test", subcategory="test")
+ _ = pnf.category
+ mock_resource_category.assert_called_once_with(name="test", subcategory="test")
+ mock_resource_category.reset_mock()
+
+ mock_created.return_value = True
+ _ = pnf.category
+ mock_resource_category.assert_called_once_with(name="test", subcategory="test")