Merge "Enhancement of Tacker API Policy for VNF tenant"

This commit is contained in:
Zuul
2023-09-14 13:25:54 +00:00
committed by Gerrit Code Review
17 changed files with 628 additions and 319 deletions

View File

@@ -25,9 +25,8 @@ area, vendor, and tenant.
where VIM or VNF is located.
* vendor: Vendor attribute is the name of the vendor. It is defined in the
definition file of VNF package. VNF obtains this attribute from VNF package.
* tenant: Tenant attribute is the name of the tenant. Tacker Antelope version
only supports the namespace of CNF. The tenant of VNF will be supported in
future releases.
* tenant: Tenant attribute is the name of the tenant. This attribute describes
the namespace of CNF, and the project name of VNF.
Enable Enhanced Tacker Policy
-----------------------------
@@ -141,7 +140,7 @@ following rules:
- vendor
- VENDOR_company-a -> {"vendor": ["company-a"]}
* - TENANT
- tenant value
- tenant
- TENANT_default -> {"tenant": ["default"]}
#. For special value in Enhanced Tacker Policy, the corresponding attribute
@@ -179,7 +178,7 @@ following rules:
- all
- {"vendor": "vendor_company-a"} -> {"vendor": ["company-a"]}
* - TENANT
- tenant value
- tenant
- all
- {"tenant": "default"} -> {"tenant": ["default"]}
@@ -309,18 +308,18 @@ Create roles
| options | {} |
+-------------+----------------------------------+
#. Create the ``TENANT_curry`` role:
#. Create the ``TENANT_tenant-a`` role:
.. code-block:: console
$ openstack role create TENANT_curry
$ openstack role create TENANT_tenant-a
+-------------+----------------------------------+
| Field | Value |
+-------------+----------------------------------+
| description | None |
| domain_id | None |
| id | cb98edb048ad49399701d4397708f397 |
| name | TENANT_curry |
| name | TENANT_tenant-a |
| options | {} |
+-------------+----------------------------------+
@@ -357,14 +356,14 @@ Create roles
Assign roles to user-project pairs
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
#. Assign ``AREA_tokyo@japan``, ``VENDOR_company-a`` and ``TENANT_curry``
#. Assign ``AREA_tokyo@japan``, ``VENDOR_company-a`` and ``TENANT_tenant-a``
to ``user-a``:
.. code-block:: console
$ openstack role add --user user-a --project nfv AREA_tokyo@japan
$ openstack role add --user user-a --project nfv VENDOR_company-a
$ openstack role add --user user-a --project nfv TENANT_curry
$ openstack role add --user user-a --project nfv TENANT_tenant-a
Verify the role assignment of ``user-a``:
@@ -376,7 +375,7 @@ Assign roles to user-project pairs
+------------------+----------------+-------+-------------+--------+--------+-----------+
| VENDOR_company-a | user-a@Default | | nfv@Default | | | False |
| AREA_tokyo@japan | user-a@Default | | nfv@Default | | | False |
| TENANT_curry | user-a@Default | | nfv@Default | | | False |
| TENANT_tenant-a | user-a@Default | | nfv@Default | | | False |
+------------------+----------------+-------+-------------+--------+--------+-----------+
#. Assign reader to ``user-b``:
@@ -433,6 +432,8 @@ When registering a vim, users can specify area attribute for the vim. This is
achieved by putting the area attribute into the extra field of the vim
configuration file. Please refer to VIM Management [#VIM_Management]_ for how
to register a vim.
And the project_name of the vim configuration file is used as tenant attribute
of instantiated VNF.
.. warning::
It is highly recommended that users who performs the VIM registration is
@@ -446,15 +447,26 @@ to register a vim.
.. code-block:: yaml
auth_url: 'http://192.168.10.115/identity/v3'
username: 'nfv_user'
username: 'vim-user'
password: 'devstack'
project_name: 'nfv'
project_name: 'tenant-a'
project_domain_name: 'default'
user_domain_name: 'default'
cert_verify: 'True'
extra:
area: tokyo@japan
.. note::
The project and VIM user which specified in the vim configuration file must
be created previously and assign the member role to VIM user.
.. code-block:: console
$ openstack project create tenant-a --domain default
$ openstack user create --project tenant-a --password devstack vim-user
$ openstack role add --user vim-user --project tenant-a member
Register OpenStack VIM:
.. code-block:: console
@@ -466,11 +478,11 @@ to register a vim.
| Field | Value |
+----------------+------------------------------------------------------+
| auth_cred | { |
| | "username": "nfv_user", |
| | "username": "vim-user", |
| | "user_domain_name": "default", |
| | "cert_verify": "True", |
| | "project_id": null, |
| | "project_name": "nfv", |
| | "project_name": "tenant-a" |
| | "project_domain_name": "default", |
| | "auth_url": "http://192.168.10.115/identity/v3", |
| | "key_type": "barbican_key", |
@@ -494,7 +506,7 @@ to register a vim.
| type | openstack |
| updated_at | None |
| vim_project | { |
| | "name": "nfv", |
| | "name": "tenant-a", |
| | "project_domain_name": "default" |
| | } |
+----------------+------------------------------------------------------+
@@ -506,9 +518,9 @@ to register a vim.
.. code-block:: yaml
auth_url: 'http://192.168.10.115/identity/v3'
username: 'nfv_user'
username: 'vim-user'
password: 'devstack'
project_name: 'nfv'
project_name: 'tenant-a'
project_domain_name: 'default'
user_domain_name: 'default'
cert_verify: 'True'
@@ -526,11 +538,11 @@ to register a vim.
| Field | Value |
+----------------+------------------------------------------------------+
| auth_cred | { |
| | "username": "nfv_user", |
| | "username": "vim-user", |
| | "user_domain_name": "default", |
| | "cert_verify": "True", |
| | "project_id": null, |
| | "project_name": "nfv", |
| | "project_name": "tenant-a", |
| | "project_domain_name": "default", |
| | "auth_url": "http://192.168.10.115/identity/v3", |
| | "key_type": "barbican_key", |
@@ -554,7 +566,7 @@ to register a vim.
| type | openstack |
| updated_at | None |
| vim_project | { |
| | "name": "nfv", |
| | "name": "tenant-a", |
| | "project_domain_name": "default" |
| | } |
+----------------+------------------------------------------------------+
@@ -716,7 +728,7 @@ configuration files that need to be modified in VNF package.
...
Create & Instantiate VNF with vendor, area and tenant attributes
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Create VNF with vendor attribute
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -734,18 +746,18 @@ Create a VNF with vnfd_id:
$ openstack vnflcm create <vnfd_id>
Instantiate VNF on VIM with area attributes
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Instantiate VNF on VIM with area and tenant attributes
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
The area attribute of the VNF comes from the used vim. In other
words, you need to specify a VIM in the area where you want to
The area and tenant attribute of the VNF comes from the used vim. In other
words, you need to specify a VIM in the area and tenant where you want to
instantiate a VNF.
For VNF LCM API version 1, please refer to [#VNF_Lifecycle_Management]_ to
instantiate VNF. Below are two samples of <param-file>.
#. If <param-file> contains the ``vimConnectionInfo`` parameter, the area
attribute comes from vim in it.
and tenant attributes come from vim in it.
.. code-block:: json
@@ -795,7 +807,7 @@ instantiate VNF. Below are two samples of <param-file>.
#. If <param-file> doesn't contains the ``vimConnectionInfo`` parameter, the
default vim is used and area attribute comes from it.
default vim is used and area and tenant attributes come from it.
.. code-block:: json
@@ -807,8 +819,8 @@ For VNF LCM API version 2, please refer to [#VNF_Lifecycle_Management]_ to
instantiate VNF. Below are two samples of <param-file>.
#. If the vim in the ``vimConnectionInfo`` parameter of <param-file> is an
existing vim in the DB, the vendor attribute of the instantiated VNF
comes from this vim.
existing vim in the DB, the area and tenant attribute of the instantiated
VNF comes from this vim.
.. code-block:: json
@@ -932,9 +944,9 @@ instantiate VNF. Below are two samples of <param-file>.
}
#. If the vim in the ``vimConnectionInfo`` parameter of <param-file> is not
existed in the DB, the vendor attribute of the instantiated VNF comes from
this vim. Users need to specify the area attribute in the
``vimConnectionInfo`` parameter.
existed in the DB, users need to specify the area and tenant attributes in
the ``vimConnectionInfo`` parameter. The tenant attribute uses the
``project`` in the ``accessInfo`` of the ``vimConnectionInfo``.
.. code-block:: json
@@ -1052,11 +1064,11 @@ instantiate VNF. Below are two samples of <param-file>.
"vim1": {
"accessInfo": {
"password": "devstack",
"project": "nfv",
"project": "tenant-a",
"projectDomain": "Default",
"region": "RegionOne",
"userDomain": "Default",
"username": "nfv_user"
"username": "vim-user"
},
"interfaceInfo": {
"endpoint": "http://localhost/identity/v3"
@@ -1071,9 +1083,8 @@ instantiate VNF. Below are two samples of <param-file>.
Instantiate CNF with tenant attribute
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
In Tacker Antelope verison, only CNF has the tenant attribute. When
instantiating CNF, the tenant attribute of CNF is specified by the namespace in
the additionalParams field of <param-file>.
When instantiating CNF, the tenant attribute of CNF is specified by the
namespace in the additionalParams field of <param-file>.
.. code-block:: json
@@ -1091,7 +1102,7 @@ the additionalParams field of <param-file>.
"Files/kubernetes/deployment.yaml",
"Files/kubernetes/namespace.yaml"
],
"namespace": "curry"
"namespace": "tenant-a"
}
}
@@ -1122,11 +1133,11 @@ an example.
| Field | Value |
+----------------+------------------------------------------------------+
| auth_cred | { |
| | "username": "nfv_user", |
| | "username": "vim-user", |
| | "user_domain_name": "default", |
| | "cert_verify": "True", |
| | "project_id": null, |
| | "project_name": "nfv", |
| | "project_name": "tenant-a", |
| | "project_domain_name": "default", |
| | "auth_url": "http://192.168.10.115/identity/v3", |
| | "key_type": "barbican_key", |
@@ -1150,7 +1161,7 @@ an example.
| type | openstack |
| updated_at | 2023-02-14 07:05:28 |
| vim_project | { |
| | "name": "nfv", |
| | "name": "tenant-a", |
| | "project_domain_name": "default" |
| | } |
+----------------+------------------------------------------------------+
@@ -1313,9 +1324,9 @@ enhanced tacker attributes supported by each API.
- No
* - LCM-List
- **GET** /vnflcm/v1/vnf_instances
- Yes(3)
- Yes
- Yes(2)
- Yes
- Yes(3)
* - LCM-Create
- **POST** /vnflcm/v1/vnf_instances
- No
@@ -1323,14 +1334,14 @@ enhanced tacker attributes supported by each API.
- No
* - LCM-Show
- **GET** /vnflcm/v1/vnf_instances/{vnfInstanceId}
- Yes(3)
- Yes
- Yes(2)
- Yes
- Yes(3)
* - LCM-Update
- **PATCH** /vnflcm/v1/vnf_instances/{vnfInstanceId}
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-Delete
- **DELETE** /vnflcm/v1/vnf_instances/{vnfInstanceId}
- No
@@ -1338,34 +1349,34 @@ enhanced tacker attributes supported by each API.
- No
* - LCM-Instantiate
- **POST** /vnflcm/v1/vnf_instances/{vnfInstanceId}/instantiate
- No
- Yes
- Yes
- Yes(2)
- No
* - LCM-Scale
- **POST** /vnflcm/v1/vnf_instances/{vnfInstanceId}/scale
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-Terminate
- **POST** /vnflcm/v1/vnf_instances/{vnfInstanceId}/terminate
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-Heal
- **POST** /vnflcm/v1/vnf_instances/{vnfInstanceId}/heal
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-Change-Connectivity
- **POST** /vnflcm/v1/vnf_instances/{vnfInstanceId}/change_ext_conn
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-ListV2
- **GET** /vnflcm/v2/vnf_instances
- Yes(4)
- Yes(3)
- Yes
- Yes(2)
- Yes(3)
* - LCM-CreateV2
- **POST** /vnflcm/v2/vnf_instances
- No
@@ -1373,14 +1384,14 @@ enhanced tacker attributes supported by each API.
- No
* - LCM-ShowV2
- **GET** /vnflcm/v2/vnf_instances/{vnfInstanceId}
- Yes(4)
- Yes(3)
- Yes
- Yes(2)
- Yes(3)
* - LCM-UpdateV2
- **PATCH** /vnflcm/v2/vnf_instances/{vnfInstanceId}
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-DeleteV2
- **DELETE** /vnflcm/v2/vnf_instances/{vnfInstanceId}
- No
@@ -1388,39 +1399,38 @@ enhanced tacker attributes supported by each API.
- No
* - LCM-InstantiateV2
- **POST** /vnflcm/v2/vnf_instances/{vnfInstanceId}/instantiate
- No
- Yes
- Yes
- Yes(2)
- No
* - LCM-ScaleV2
- **POST** /vnflcm/v2/vnf_instances/{vnfInstanceId}/scale
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-TerminateV2
- **POST** /vnflcm/v2/vnf_instances/{vnfInstanceId}/terminate
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-HealV2
- **POST** /vnflcm/v2/vnf_instances/{vnfInstanceId}/heal
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-Change-ConnectivityV2
- **POST** /vnflcm/v2/vnf_instances/{vnfInstanceId}/change_ext_conn
- Yes
- Yes
- Yes(2)
- Yes
* - LCM-Change-VnfPkgV2
- **POST** /vnflcm/v2/vnf_instances/{vnfInstanceId}/change_vnfpkg
- Yes
- Yes
- Yes(2)
- Yes
(1) This is ignored when the state is not `ONBOARDED`.
(2) This is ignored when the instance is vnf(not cnf).
(3) Default vim is used when the state is `NOT_INSTANTIATED`.
(4) This is ignored when the state is not `NOT_INSTANTIATED`.
(2) Default vim is used when the state is `NOT_INSTANTIATED`.
(3) This is ignored when the state is `NOT_INSTANTIATED`.
Sample policy.yaml file
~~~~~~~~~~~~~~~~~~~~~~~

View File

@@ -590,15 +590,7 @@ class VnfLcmController(wsgi.Controller):
if (vnf_instance.instantiation_state ==
fields.VnfInstanceState.INSTANTIATED):
if vnf_instance.vnf_metadata:
tenant = vnf_instance.vnf_metadata.get('namespace')
# TODO(kexuesheng): Add steps to get tenant of VNFs deployed
# in OpenStack VIM. This is a temporary workaround until that
# information is available.
if vnf_instance.vim_connection_info:
vim_type = vnf_instance.vim_connection_info[0].vim_type
if vim_type in ["openstack", "ETSINFV.OPENSTACK_KEYSTONE.v_2"]:
tenant = '*'
tenant = vnf_instance.vnf_metadata.get('tenant')
else:
tenant = '*'

View File

@@ -236,15 +236,8 @@ class VnfLcmControllerV2(sol_wsgi.SolAPIController):
if (vnf_instance.obj_attr_is_set('instantiatedVnfInfo') and
vnf_instance.instantiatedVnfInfo.obj_attr_is_set(
'metadata')):
tenant = (vnf_instance.instantiatedVnfInfo
.metadata.get('namespace'))
# TODO(kexuesheng): Add steps to get tenant of VNFs deployed
# in OpenStack VIM. This is a temporary workaround until that
# information is available.
if vim_type == "ETSINFV.OPENSTACK_KEYSTONE.V_3":
tenant = '*'
.metadata.get('tenant'))
target = {
'vendor': vendor,

View File

@@ -108,6 +108,7 @@ class KubernetesCommon(object):
vdu_reses, namespace):
metadata = {
'namespace': namespace,
'tenant': namespace,
'vdu_reses': {vdu_name: vdu_res.body
for vdu_name, vdu_res in vdu_reses.items()}
}

View File

@@ -1579,5 +1579,7 @@ class Openstack(object):
# store stack_id and nfv parameters into metadata
inst_vnf_info.metadata['stack_id'] = stack_id
inst_vnf_info.metadata['nfv'] = nfv_dict
# store tenant name for enhanced policy
inst_vnf_info.metadata['tenant'] = vim_info.accessInfo.get('project')
inst.instantiatedVnfInfo = inst_vnf_info

View File

@@ -20,6 +20,7 @@ import time
import yaml
import zipfile
from glanceclient.v2 import client as glance_client
from keystoneauth1.identity import v3
from keystoneauth1 import session
from keystoneclient.v3 import client as ks_client
@@ -46,15 +47,19 @@ class BaseEnhancedPolicyTest(object):
vim_base_url = "/v1.0/vims"
pkg_base_url = '/vnfpkgm/v1/vnf_packages'
user_role_map = {}
vim_user_project_map = {}
@classmethod
def setUpClass(cls, subclass_with_user_role_map):
cls.user_role_map = subclass_with_user_role_map.user_role_map
def setUpClass(cls, subclass_with_maps):
cls.user_role_map = subclass_with_maps.user_role_map
cls.vim_user_project_map = subclass_with_maps.vim_user_project_map
cls.ks_client = cls.keystone_client()
cls.project = cls._get_project()
cls._create_project()
cls._create_user_role()
cls.create_tacker_http_client_for_user()
cls.cleanup_list = []
cls.images_to_delete = []
@classmethod
def create_tacker_http_client_for_user(cls):
@@ -69,7 +74,9 @@ class BaseEnhancedPolicyTest(object):
@classmethod
def tearDownClass(cls):
cls._delete_image()
cls._delete_user_role()
cls._delete_project()
@classmethod
def keystone_client(cls):
@@ -151,25 +158,27 @@ class BaseEnhancedPolicyTest(object):
@classmethod
def _create_project(cls):
project_name = 'policy-test'
projects = cls.ks_client.projects.list()
project_exists = False
for project in projects:
if project_name == project.name:
project_exists = True
cls.project_id = project.id
cls.project = project
break
if not project_exists:
project = cls.ks_client.projects.create(project_name, 'default')
cls.project_id = project.id
cls.project = project
cls.projects = []
if cls.vim_user_project_map:
# create project
projects = cls.ks_client.projects.list()
project_names = [project.name for project in projects]
projects_to_create = [
project_name
for project_name in cls.vim_user_project_map.values()
if project_name not in project_names]
if projects_to_create:
for project_name in set(projects_to_create):
project = cls.ks_client.projects.create(project_name,
'default')
cls.projects.append(project)
@classmethod
def _get_project(cls):
vim_params = base.BaseTackerTest.get_credentials(
cls.local_vim_conf_file)
project_name = vim_params['project_name']
def _get_project(cls, project_name=None):
if not project_name:
vim_params = base.BaseTackerTest.get_credentials(
cls.local_vim_conf_file)
project_name = vim_params['project_name']
projects = cls.ks_client.projects.list()
for project in projects:
if project.name == project_name:
@@ -179,9 +188,9 @@ class BaseEnhancedPolicyTest(object):
@classmethod
def _delete_project(cls):
if hasattr(cls, 'project_id') and cls.project_id:
if hasattr(cls, 'ks_client') and cls.ks_client:
cls.ks_client.projects.delete(cls.project_id)
if cls.projects:
for project in cls.projects:
cls.ks_client.projects.delete(project.id)
@classmethod
def _get_user_by_name(cls, name):
@@ -229,6 +238,34 @@ class BaseEnhancedPolicyTest(object):
project=cls.project.id
)
@classmethod
def create_vim_user(cls):
if cls.vim_user_project_map:
vim_user_project_map = cls.vim_user_project_map
else:
raise Exception('vim_user_project_map is needed.')
users = cls.ks_client.users.list()
usernames = [user.name for user in users]
projects = cls.ks_client.projects.list()
password = 'devstack'
for username in vim_user_project_map.keys():
vim_username = f'vim_{username}'
if vim_username in usernames:
# already exist
continue
project_name = vim_user_project_map[username]
project_id = [project.id for project in projects
if project_name == project.name][0]
user = cls.ks_client.users.create(
vim_username, project=project_id, password=password)
cls.users.append(user)
# add member role to vim users
cls.ks_client.roles.grant(
cls.role_map.get('member'),
user=cls._get_user_by_name(vim_username),
project=project_id
)
@classmethod
def _create_role(cls, role_name):
role = cls.ks_client.roles.create(role_name)
@@ -286,11 +323,12 @@ class BaseEnhancedPolicyTest(object):
@classmethod
def register_vim(cls, client, url, vim_file, name, description, vim_type,
extra, is_default=False):
extra, is_default=False, username=None, tenant=None):
base_data = yaml.safe_load(read_file(vim_file))
if vim_type == 'openstack':
username = f'vim_{username}' if username else base_data['username']
auth_cred = {
'username': base_data['username'],
'username': username,
'password': base_data['password'],
'user_domain_name': base_data['user_domain_name']
}
@@ -299,7 +337,7 @@ class BaseEnhancedPolicyTest(object):
else:
raise Exception(f'unknown vim type: {vim_type}.')
vim_project = {
'name': base_data['project_name'],
'name': tenant if tenant else base_data['project_name'],
}
if 'project_domain_name' in base_data:
vim_project['project_domain_name'] = (
@@ -457,7 +495,7 @@ class BaseEnhancedPolicyTest(object):
@classmethod
def _step_vim_register(
cls, username, vim_type, local_vim, vim_name, area,
is_default=False):
is_default=False, tenant=None):
extra = {}
if area:
extra = {'area': area}
@@ -465,7 +503,8 @@ class BaseEnhancedPolicyTest(object):
cls.get_tk_http_client_by_user(username), cls.vim_base_url,
local_vim, vim_name,
"{}-{}".format(vim_name, uuidutils.generate_uuid()),
vim_type, extra, is_default=is_default)
vim_type, extra, is_default=is_default, username=username,
tenant=tenant)
if resp.status_code == 201:
return body.get('vim')
else:
@@ -488,6 +527,55 @@ class BaseEnhancedPolicyTest(object):
return csar_dir
@classmethod
def _glance_client(cls, username=None, tenant=None):
vim_params = base.BaseTackerTest.get_credentials()
auth = v3.Password(auth_url=vim_params['auth_url'],
username=username if username else vim_params['username'],
password=vim_params['password'],
project_name=tenant if tenant else vim_params['project_name'],
user_domain_name=vim_params['user_domain_name'],
project_domain_name=vim_params['project_domain_name'])
verify = 'True' == vim_params.pop('cert_verify', 'False')
auth_ses = session.Session(auth=auth, verify=verify)
return glance_client.Client(session=auth_ses)
@classmethod
def create_image(cls):
if cls.vim_user_project_map:
vim_user_project_map = cls.vim_user_project_map
else:
raise Exception('vim_user_project_map is needed.')
image_name = "cirros-0.5.2-x86_64-disk"
image_path = os.path.abspath(
os.path.join(os.path.dirname(__file__),
"../../etc/samples/etsi/nfv/common/Files/images",
f"{image_name}.img"))
image_data = {
'disk_format': 'qcow2',
'container_format': 'bare',
'visibility': 'private',
'name': image_name}
for username, projectname in vim_user_project_map.items():
glance_client = cls._glance_client(username=f'vim_{username}',
tenant=projectname)
images = glance_client.images.list()
images = list(filter(
lambda image: image.name == image_name, images))
if not images:
image = glance_client.images.create(**image_data)
with open(image_path, 'rb') as f:
glance_client.images.upload(image.id, f)
cls.images_to_delete.append(image)
@classmethod
def _delete_image(cls):
if not cls.images_to_delete:
return
glance_client = cls._glance_client()
for image in cls.images_to_delete:
glance_client.images.delete(image.id)
def _register_subscription(self, request_body, http_client=None):
if http_client is None:
http_client = self.http_client
@@ -684,18 +772,6 @@ class VimAPIsTest(BaseTackerTest, BaseEnhancedPolicyTest):
class VnflcmAPIsV1Base(vnflcm_base.BaseVnfLcmTest, BaseEnhancedPolicyTest):
user_role_map = {
'user_a': ['VENDOR_company_A', 'AREA_area_A@region_A',
'TENANT_namespace-a', 'manager'],
'user_a_1': ['VENDOR_company_A', 'manager'],
'user_b': ['VENDOR_company_B', 'AREA_area_B@region_B',
'TENANT_namespace-b', 'manager'],
'user_c': ['VENDOR_company_C', 'AREA_area_C@region_C',
'TENANT_namespace-c', 'manager'],
'user_all': ['VENDOR_all', 'AREA_all@all', 'TENANT_all', 'manager'],
'user_admin': ['admin']
}
@classmethod
def setUpClass(cls):
vnflcm_base.BaseVnfLcmTest.setUpClass()
@@ -704,6 +780,11 @@ class VnflcmAPIsV1Base(vnflcm_base.BaseVnfLcmTest, BaseEnhancedPolicyTest):
def setUp(self):
super().setUp()
@classmethod
def tearDownClass(cls):
BaseEnhancedPolicyTest.tearDownClass()
vnflcm_base.BaseVnfLcmTest.tearDownClass()
def _step_lcm_create(self, username, vnfd_id, vnf_instance_name,
expected_status_code):
client = self.get_tk_http_client_by_user(username)

View File

@@ -24,31 +24,56 @@ from tacker.tests.functional.sol_enhanced_policy.base import (
class VnflcmAPIsV1Test(VnflcmAPIsV1Base):
user_role_map = {
'user_a': ['VENDOR_company_A', 'AREA_area_A@region_A',
'TENANT_tenant_A', 'manager'],
'user_a_1': ['VENDOR_company_A', 'manager'],
'user_b': ['VENDOR_company_B', 'AREA_area_B@region_B',
'TENANT_tenant_B', 'manager'],
'user_c': ['VENDOR_company_C', 'AREA_area_C@region_C',
'TENANT_tenant_C', 'manager'],
'user_all': ['VENDOR_all', 'AREA_all@all',
'TENANT_all', 'manager'],
'user_admin': ['admin']
}
vim_user_project_map = {
'user_a': 'tenant_A',
'user_b': 'tenant_B',
'user_c': 'tenant_C'
}
@classmethod
def setUpClass(cls):
super().setUpClass()
cls.create_vim_user()
vim_type = 'openstack'
local_vim = 'local-vim.yaml'
cls.vim_a = cls._step_vim_register(
'user_a', vim_type, local_vim, 'vim_a', 'area_A@region_A')
'user_a', vim_type, local_vim, 'vim_a', 'area_A@region_A',
tenant='tenant_A')
cls.vim_a_1 = cls._step_vim_register(
'user_a', vim_type, local_vim, 'vim_a_1', 'area_A@region_A')
'user_a', vim_type, local_vim, 'vim_a_1', 'area_A@region_A',
tenant='tenant_A')
cls.vim_b = cls._step_vim_register(
'user_b', vim_type, local_vim, 'vim_b', 'area_B@region_B')
'user_b', vim_type, local_vim, 'vim_b', 'area_B@region_B',
tenant='tenant_B')
cls.vim_b_1 = cls._step_vim_register(
'user_b', vim_type, local_vim, 'vim_b_1', 'area_B@region_B')
'user_b', vim_type, local_vim, 'vim_b_1', 'area_B@region_B',
tenant='tenant_B')
cls.vim_c = cls._step_vim_register(
'user_b', vim_type, local_vim, 'vim_c', None)
'user_c', vim_type, local_vim, 'vim_c', None,
tenant='tenant_C')
cls.vim_c_1 = cls._step_vim_register(
'user_b', vim_type, local_vim, 'vim_c_1', None)
'user_c', vim_type, local_vim, 'vim_c_1', None,
tenant='tenant_C')
cls.pkg_a = cls._step_pkg_create('user_a')
@@ -130,6 +155,7 @@ class VnflcmAPIsV1Test(VnflcmAPIsV1Base):
port_uuid = self.create_port(neutron_client, network_uuid)
ext_vl = get_external_virtual_links(net0_id, net_mgmt_id,
port_uuid)
self.create_image()
request_body = self._instantiate_vnf_request(
"simple", vim_id=vim_id, ext_vl=ext_vl)

View File

@@ -33,20 +33,29 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
user_role_map = {
'user_a': ['VENDOR_company_A', 'AREA_area_A@region_A',
'TENANT_namespace_A', 'manager'],
'TENANT_tenant_A', 'manager'],
'user_a_1': ['VENDOR_company_A', 'manager'],
'user_b': ['VENDOR_company_B', 'AREA_area_B@region_B',
'TENANT_namespace_B', 'manager'],
'TENANT_tenant_B', 'manager'],
'user_c': ['VENDOR_company_C', 'AREA_area_C@region_C',
'TENANT_namespace-c', 'manager'],
'user_all': ['VENDOR_all', 'AREA_all@all', 'TENANT_all', 'manager'],
'TENANT_tenant_C', 'manager'],
'user_all': ['VENDOR_all', 'AREA_all@all',
'TENANT_all', 'manager'],
'user_admin': ['admin']
}
vim_user_project_map = {
'user_a': 'tenant_A',
'user_b': 'tenant_B',
'user_c': 'tenant_C',
'user_all': 'tenant_B',
'user_admin': 'tenant_C'
}
@classmethod
def setUpClass(cls):
CommonVnfLcmTest.setUpClass()
BaseEnhancedPolicyTest.setUpClass(cls)
cls.create_vim_user()
for user in cls.users:
client = cls.get_local_tacker_http_client(user.name)
@@ -153,7 +162,8 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
)
return http_client.HttpClient(auth)
def change_ext_conn_max(self, net_ids, subnets, auth_url, area):
def change_ext_conn_max(self, net_ids, subnets, auth_url, area,
username=None, tenant=None):
vim_id_1 = uuidutils.generate_uuid()
vim_id_2 = uuidutils.generate_uuid()
@@ -219,10 +229,10 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
"vimType": "ETSINFV.OPENSTACK_KEYSTONE.V_3",
"interfaceInfo": {"endpoint": auth_url},
"accessInfo": {
"username": "nfv_user",
"username": f'vim_{username}' if username else "nfv_user",
"region": "RegionOne",
"password": "devstack",
"project": "nfv",
"project": tenant if tenant else "nfv",
"projectDomain": "Default",
"userDomain": "Default"
},
@@ -266,7 +276,8 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
else:
return None
def instantiate_vnf(self, area=None, vim_id=None):
def instantiate_vnf(self, area=None, vim_id=None, username=None,
tenant=None):
# Omit except for required attributes
# NOTE: Only the following cardinality attributes are set.
# - 1
@@ -279,10 +290,10 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
"vimType": "ETSINFV.OPENSTACK_KEYSTONE.V_3",
"interfaceInfo": {"endpoint": self.auth_url},
"accessInfo": {
"username": "nfv_user",
"username": f'vim_{username}' if username else "nfv_user",
"region": "RegionOne",
"password": "devstack",
"project": "nfv",
"project": tenant if tenant else "nfv",
"projectDomain": "Default",
"userDomain": "Default"
},
@@ -320,14 +331,16 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
}
}
def _step_lcm_instantiate(self, username, inst_id, glance_image,
def _step_lcm_instantiate(self, username, inst_id, tenant, glance_image,
flavour_vdu_dict, zone_name_list, expected_status_code,
area=None, vim_id=None):
area=None, vim_id=None):
self.create_image()
self.tacker_client = self.get_tk_http_client_by_user(username)
self._set_grant_response(
False, 'INSTANTIATE', glance_image=glance_image,
flavour_vdu_dict=flavour_vdu_dict, zone_name_list=zone_name_list)
instantiate_req = self.instantiate_vnf(area, vim_id)
instantiate_req = self.instantiate_vnf(area, vim_id, username=username,
tenant=tenant)
resp, body = self.instantiate_vnf_instance(inst_id, instantiate_req)
self.assertEqual(expected_status_code, resp.status_code)
if expected_status_code == 202:
@@ -427,7 +440,7 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
# update and change_vnfpkg completion.
time.sleep(WAIT_LCMOCC_UPDATE_TIME)
def _step_lcm_change_ext_conn(self, username, inst_id, area,
def _step_lcm_change_ext_conn(self, username, inst_id, tenant, area,
zone_name_list, expected_status_code):
self.tacker_client = self.get_tk_http_client_by_user(username)
self._set_grant_response(
@@ -485,7 +498,8 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
self.addCleanup(self.delete_port, port_id)
change_ext_conn_req = self.change_ext_conn_max(
net_ids, subnet_ids, self.auth_url, area)
net_ids, subnet_ids, self.auth_url, area, username=username,
tenant=tenant)
resp, body = self.change_ext_conn(inst_id, change_ext_conn_req)
self.assertEqual(expected_status_code, resp.status_code)
if expected_status_code == 202:
@@ -639,16 +653,16 @@ class VnflcmAPIsV2VNFBase(CommonVnfLcmTest, BaseEnhancedPolicyTest):
self._step_lcm_update('user_all', inst_id_b, self.vnfd_id_b_1, 202)
# step 35 LCM-Change-ConnectivityV2, Resource Group A / User Group A
self._step_lcm_change_ext_conn(
'user_a', inst_id_a, 'area_A@region_A', zone_name_list, 202)
self._step_lcm_change_ext_conn('user_a', inst_id_a, 'tenant_A',
'area_A@region_A', zone_name_list, 202)
# step 36 LCM-Change-ConnectivityV2, Resource Group B / User Group A
self._step_lcm_change_ext_conn(
'user_a', inst_id_b, 'area_B@region_B', zone_name_list, 403)
self._step_lcm_change_ext_conn('user_a', inst_id_b, 'tenant_B',
'area_B@region_B', zone_name_list, 403)
# step 37 LCM-Change-ConnectivityV2, Resource Group B / User Group all
self._step_lcm_change_ext_conn(
'user_all', inst_id_b, 'area_B@region_B', zone_name_list, 202)
self._step_lcm_change_ext_conn('user_all', inst_id_b, 'tenant_B',
'area_B@region_B', zone_name_list, 202)
# step 38 LCM-Change-VnfPkgV2, Resource Group A / User Group A
self._step_lcm_update('user_a', inst_id_a, self.vnfd_id_a, 202)
@@ -703,18 +717,87 @@ class VnflcmAPIsV2VNFInstantiateWithArea(VnflcmAPIsV2VNFBase):
self.vnflcm_apis_v2_vnf_test_before_instantiate())
# step 12 LCM-InstantiateV2, Resource Group A / User Group A
self._step_lcm_instantiate('user_a', inst_id_a, glance_image,
flavour_vdu_dict, zone_name_list, 202, area='area_A@region_A')
self._step_lcm_instantiate('user_a', inst_id_a, 'tenant_A',
glance_image, flavour_vdu_dict,
zone_name_list, 202, area='area_A@region_A')
# step 13 LCM-InstantiateV2, Resource Group B / User Group A
self._step_lcm_instantiate('user_a', inst_id_b, glance_image,
flavour_vdu_dict, zone_name_list, 403,
area='area_B@region_B')
self._step_lcm_instantiate('user_a', inst_id_b, 'tenant_B',
glance_image, flavour_vdu_dict,
zone_name_list, 403, area='area_B@region_B')
# step 14 LCM-InstantiateV2, Resource Group B / User Group all
self._step_lcm_instantiate('user_all', inst_id_b, glance_image,
self._step_lcm_instantiate('user_all', inst_id_b, 'tenant_B',
glance_image, flavour_vdu_dict,
zone_name_list, 202, area='area_B@region_B')
self.vnflcm_apis_v2_vnf_test_after_instantiate(
sub_id, inst_id_a, inst_id_b, zone_name_list, glance_image,
flavour_vdu_dict)
class VnflcmAPIsV2VNFInstantiateWithAreaInRegisteredVim(VnflcmAPIsV2VNFBase):
@classmethod
def setUpClass(cls):
super().setUpClass()
vim_type = 'openstack'
local_vim = 'local-vim.yaml'
cls.vim_a = cls._step_vim_register(
'user_a', vim_type, local_vim, 'vim_a', 'area_A@region_A',
tenant='tenant_A')
cls.vim_a_1 = cls._step_vim_register(
'user_a', vim_type, local_vim, 'vim_a_1', 'area_A@region_A',
tenant='tenant_A')
cls.vim_b = cls._step_vim_register(
'user_b', vim_type, local_vim, 'vim_b', 'area_B@region_B',
tenant='tenant_B')
cls.vim_b_1 = cls._step_vim_register(
'user_b', vim_type, local_vim, 'vim_b_1', 'area_B@region_B',
tenant='tenant_B')
@classmethod
def tearDownClass(cls):
cls._step_vim_delete('user_a', cls.vim_a)
cls._step_vim_delete('user_a', cls.vim_a_1)
cls._step_vim_delete('user_b', cls.vim_b)
cls._step_vim_delete('user_b', cls.vim_b_1)
super().tearDownClass()
def test_vnflcm_apis_v2_vnf_with_area_in_registered_vim(self):
glance_image = None
flavour_vdu_dict = None
zone_name_list = None
sub_id, inst_id_a, inst_id_b = (
self.vnflcm_apis_v2_vnf_test_before_instantiate())
# step 12 LCM-InstantiateV2, Resource Group A / User Group A
self._step_lcm_instantiate('user_a', inst_id_a, 'tenant_A',
glance_image,
flavour_vdu_dict, zone_name_list, 202,
area='area_B@region_B')
vim_id=self.vim_a['id'])
# step 13 LCM-InstantiateV2, Resource Group B / User Group A
self._step_lcm_instantiate('user_a', inst_id_b, 'tenant_B',
glance_image,
flavour_vdu_dict, zone_name_list, 403,
vim_id=self.vim_b['id'])
# step 14 LCM-InstantiateV2, Resource Group B / User Group all
self._step_lcm_instantiate('user_all', inst_id_b, 'tenant_B',
glance_image,
flavour_vdu_dict, zone_name_list, 202,
vim_id=self.vim_b['id'])
self.vnflcm_apis_v2_vnf_test_after_instantiate(
sub_id, inst_id_a, inst_id_b, zone_name_list, glance_image,
@@ -723,70 +806,6 @@ class VnflcmAPIsV2VNFInstantiateWithArea(VnflcmAPIsV2VNFBase):
class VnflcmAPIsV2VNFInstantiateWithoutArea(VnflcmAPIsV2VNFBase):
@classmethod
def setUpClass(cls):
super().setUpClass()
vim_type = 'openstack'
local_vim = 'local-vim.yaml'
cls.vim_a = cls._step_vim_register(
'user_a', vim_type, local_vim, 'vim_a', 'area_A@region_A')
cls.vim_a_1 = cls._step_vim_register(
'user_a', vim_type, local_vim, 'vim_a_1', 'area_A@region_A')
cls.vim_b = cls._step_vim_register(
'user_b', vim_type, local_vim, 'vim_b', 'area_B@region_B')
cls.vim_b_1 = cls._step_vim_register(
'user_b', vim_type, local_vim, 'vim_b_1', 'area_B@region_B')
@classmethod
def tearDownClass(cls):
cls._step_vim_delete('user_a', cls.vim_a)
cls._step_vim_delete('user_a', cls.vim_a_1)
cls._step_vim_delete('user_b', cls.vim_b)
cls._step_vim_delete('user_b', cls.vim_b_1)
super().tearDownClass()
def test_vnflcm_apis_v2_vnf_without_area_in_vim_conn_info(self):
glance_image = None
flavour_vdu_dict = None
zone_name_list = None
sub_id, inst_id_a, inst_id_b = (
self.vnflcm_apis_v2_vnf_test_before_instantiate())
# step 12 LCM-InstantiateV2, Resource Group A / User Group A
self._step_lcm_instantiate('user_a', inst_id_a,
glance_image,
flavour_vdu_dict, zone_name_list, 202,
vim_id=self.vim_a['id'])
# step 13 LCM-InstantiateV2, Resource Group B / User Group A
self._step_lcm_instantiate('user_a', inst_id_b,
glance_image,
flavour_vdu_dict, zone_name_list, 403,
vim_id=self.vim_b['id'])
# step 14 LCM-InstantiateV2, Resource Group B / User Group all
self._step_lcm_instantiate('user_all', inst_id_b,
glance_image,
flavour_vdu_dict, zone_name_list, 202,
vim_id=self.vim_b['id'])
self.vnflcm_apis_v2_vnf_test_after_instantiate(
sub_id, inst_id_a, inst_id_b, zone_name_list, glance_image,
flavour_vdu_dict)
class VnflcmAPIsV2VNFInstanceWithoutArea(VnflcmAPIsV2VNFBase):
@classmethod
def setUpClass(cls):
super().setUpClass()
@@ -796,10 +815,12 @@ class VnflcmAPIsV2VNFInstanceWithoutArea(VnflcmAPIsV2VNFBase):
local_vim = 'local-vim.yaml'
cls.vim_c = cls._step_vim_register(
'user_c', vim_type, local_vim, 'vim_c', None)
'user_c', vim_type, local_vim, 'vim_c', None,
tenant='tenant_C')
cls.vim_c_1 = cls._step_vim_register(
'user_c', vim_type, local_vim, 'vim_c_1', None)
'user_c', vim_type, local_vim, 'vim_c_1', None,
tenant='tenant_C')
@classmethod
def tearDownClass(cls):
@@ -809,7 +830,7 @@ class VnflcmAPIsV2VNFInstanceWithoutArea(VnflcmAPIsV2VNFBase):
super().tearDownClass()
def test_vnflcm_apis_v2_vnf_instance_without_area(self):
def test_vnflcm_apis_v2_vnf_without_area(self):
glance_image = None
flavour_vdu_dict = None
@@ -857,7 +878,7 @@ class VnflcmAPIsV2VNFInstanceWithoutArea(VnflcmAPIsV2VNFBase):
self._step_lcm_list('user_admin', [inst_id_c])
# step 8 LCM-InstantiateV2, Resource Group C / User Group C
self._step_lcm_instantiate('user_c', inst_id_c,
self._step_lcm_instantiate('user_c', inst_id_c, 'tenant_C',
glance_image,
flavour_vdu_dict, zone_name_list, 202,
vim_id=self.vim_c['id'])
@@ -927,15 +948,15 @@ class VnflcmAPIsV2VNFInstanceWithoutArea(VnflcmAPIsV2VNFBase):
# step 27 LCM-Change-ConnectivityV2, Resource Group C / User Group C
self._step_lcm_change_ext_conn(
'user_c', inst_id_c, None, zone_name_list, 403)
'user_c', inst_id_c, 'tenant_C', None, zone_name_list, 403)
# step 28 LCM-Change-ConnectivityV2, Resource Group C / User Group A
self._step_lcm_change_ext_conn(
'user_all', inst_id_c, None, zone_name_list, 403)
'user_all', inst_id_c, 'tenant_C', None, zone_name_list, 403)
# step 29 LCM-Change-ConnectivityV2, Resource Group C / User Group all
self._step_lcm_change_ext_conn(
'user_admin', inst_id_c, None, zone_name_list, 202)
'user_admin', inst_id_c, 'tenant_C', None, zone_name_list, 202)
# step 30 LCM-Change-VnfPkgV2, Resource Group C / User Group C
self._step_lcm_change_vnfpkg('user_c', inst_id_c, self.vnfd_id_c_2,

View File

@@ -20,6 +20,18 @@ from tacker.tests.functional.sol_enhanced_policy.base import (
class VnflcmAPIsV1CNFTest(VnflcmAPIsV1Base):
user_role_map = {
'user_a': ['VENDOR_company_A', 'AREA_area_A@region_A',
'TENANT_namespace-a', 'manager'],
'user_a_1': ['VENDOR_company_A', 'manager'],
'user_b': ['VENDOR_company_B', 'AREA_area_B@region_B',
'TENANT_namespace-b', 'manager'],
'user_c': ['VENDOR_company_C', 'AREA_area_C@region_C',
'TENANT_namespace-c', 'manager'],
'user_all': ['VENDOR_all', 'AREA_all@all', 'TENANT_all', 'manager'],
'user_admin': ['admin']
}
@classmethod
def setUpClass(cls):
super().setUpClass()

View File

@@ -189,18 +189,18 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
# 'expected_status_code': success_status_code
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': success_status_code
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_all@all', 'VENDOR_all', 'TENANT_all'
@@ -209,7 +209,7 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_all@region_A', 'VENDOR_all', 'TENANT_all'
@@ -218,12 +218,12 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_vendor,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': success_status_code
},
@@ -235,18 +235,18 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates_without_area,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
@@ -258,66 +258,66 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_B@region_A',
'VENDOR_provider_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_B',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A',
'TENANT_namespace_B'
'TENANT_tenant_B'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'VENDOR_provider_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
@@ -327,40 +327,40 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_all@region_B',
'VENDOR_provider_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_vendor,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_B',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'tenant': 'namespace_A',
'tenant': 'tenant_A',
'rules': rule_vendor,
'roles': [
'AREA_area_A@region_A',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
@@ -372,7 +372,7 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'roles': [
'AREA_area_B@region_A',
'VENDOR_provider_B',
'TENANT_namespace_A'
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
},
@@ -400,6 +400,39 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
return test_data
def get_test_data_policy_delete():
rules = {POLICY_NAME.format('delete'): "vendor:%(vendor)s"}
test_data = [
# 'expected_status_code': http_client.NO_CONTENT
{
'vnf_instance_updates': {'vnfProvider': 'provider_A'},
'rules': rules,
'roles': ['VENDOR_provider_A'],
'expected_status_code': http_client.NO_CONTENT
},
{
'vnf_instance_updates': {'vnfProvider': 'provider_A'},
'rules': rules,
'roles': ['VENDOR_all'],
'expected_status_code': http_client.NO_CONTENT
},
# 'expected_status_code': http_client.FORBIDDEN
{
'vnf_instance_updates': {'vnfProvider': 'provider_A'},
'rules': rules,
'roles': [],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': {'vnfProvider': 'provider_A'},
'rules': rules,
'roles': ['VENDOR_provider_B'],
'expected_status_code': http_client.FORBIDDEN
},
]
return test_data
def make_vnf_instance(
vim_type, instantiation_state, vendor, area=None, tenant=None):
vim_connection_info = objects.VimConnectionInfo(
@@ -435,8 +468,8 @@ def make_vnf_instance(
objects.VnfInstanceV2_InstantiatedVnfInfo(
flavourId='fake_flavour_id',
vnfState='STARTED',
metadata={'namespace': tenant}))
vnf_inst_fields.update({'metadata': {'namespace': tenant}})
metadata={'tenant': tenant}))
vnf_inst_fields.update({'metadata': {'tenant': tenant}})
return vnf_instance
@@ -452,50 +485,59 @@ def get_test_data_policy_index():
inst_1 = make_vnf_instance(
'ETSINFV.OPENSTACK_KEYSTONE.V_3', 'INSTANTIATED', 'provider_A',
area='area_A@region_A')
area='area_A@region_A', tenant='tenant_A')
# OK
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': [inst_1.id]
})
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@all', 'VENDOR_all'],
'roles': ['AREA_all@all', 'VENDOR_all', 'TENANT_all'],
'expected_vnf_inst_ids': [inst_1.id]
})
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@region_A', 'VENDOR_all'],
'roles': ['AREA_all@region_A', 'VENDOR_all', 'TENANT_all'],
'expected_vnf_inst_ids': [inst_1.id]
})
# wrong region role
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@region_B', 'VENDOR_all'],
'roles': ['AREA_all@region_B', 'VENDOR_all', 'TENANT_all'],
'expected_vnf_inst_ids': []
})
# wrong area role
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_B@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_area_B@region_A', 'VENDOR_provider_A', 'TENANT_all'],
'expected_vnf_inst_ids': []
})
# wrong vendor role
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_B'],
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_B', 'TENANT_all'],
'expected_vnf_inst_ids': []
})
# wrong tenant role
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A', 'TENANT_B'],
'expected_vnf_inst_ids': []
})
# without area
inst_2 = make_vnf_instance(
'ETSINFV.OPENSTACK_KEYSTONE.V_3', 'INSTANTIATED', 'provider_A')
'ETSINFV.OPENSTACK_KEYSTONE.V_3', 'INSTANTIATED', 'provider_A',
tenant='tenant_A')
test_data.append({
'vnf_instance_list': [inst_2],
'rules': rule_area_vendor_tenant,
@@ -504,7 +546,8 @@ def get_test_data_policy_index():
})
# NOT_INSTANTIATED
inst_3 = make_vnf_instance(
'ETSINFV.OPENSTACK_KEYSTONE.V_3', 'NOT_INSTANTIATED', 'provider_A')
'ETSINFV.OPENSTACK_KEYSTONE.V_3', 'NOT_INSTANTIATED', 'provider_A',
tenant='tenant_A')
test_data.append({
'vnf_instance_list': [inst_3],
'rules': rule_area_vendor_tenant,
@@ -1837,7 +1880,7 @@ class TestVnflcmV2EnhancedPolicy(TestVnflcmV2):
objects.VnfInstanceV2_InstantiatedVnfInfo(
flavourId='fake_flavour_id',
vnfState='STARTED',
metadata={'namespace': 'namespace_A'}))
metadata={'tenant': 'tenant_A'}))
inst.create(self.context)
lcmocc.create(self.context)
@@ -1897,7 +1940,7 @@ class TestVnflcmV2EnhancedPolicy(TestVnflcmV2):
'maxScaleLevels': max_scale_levels,
}
if tenant:
instantiated_vnf_info.update({'metadata': {'namespace': tenant}})
instantiated_vnf_info.update({'metadata': {'tenant': tenant}})
inst.instantiatedVnfInfo = objects.VnfInstanceV2_InstantiatedVnfInfo(
**instantiated_vnf_info
)
@@ -1931,7 +1974,7 @@ class TestVnflcmV2EnhancedPolicy(TestVnflcmV2):
]
)
if tenant:
inst.instantiatedVnfInfo.metadata = {'namespace': tenant}
inst.instantiatedVnfInfo.metadata = {'tenant': tenant}
if not vnf_inst_updates:
inst.vimConnectionInfo = {
"vim1": objects.VimConnectionInfo.from_dict(
@@ -2100,17 +2143,15 @@ class TestVnflcmV2EnhancedPolicy(TestVnflcmV2):
if expected_status_code != http_client.FORBIDDEN:
raise
@ddt.data(*get_test_data_policy_vnf_instantiated(
'delete', http_client.NO_CONTENT))
@ddt.data(*get_test_data_policy_delete())
@ddt.unpack
@mock.patch.object(nfvo_client.NfvoClient, 'send_inst_delete_notification')
def test_delete_enhanced_policy(self, mock_delete, vnf_instance_updates,
tenant, rules, roles, expected_status_code):
rules, roles, expected_status_code):
self._overwrite_policy(rules)
inst_id, _ = self._create_inst_and_lcmocc('NOT_INSTANTIATED',
fields.LcmOperationStateType.COMPLETED,
vnf_inst_updates=vnf_instance_updates,
tenant=tenant)
vnf_inst_updates=vnf_instance_updates)
try:
result = self.controller.delete(
self._fake_request(roles), id=inst_id)
@@ -2205,11 +2246,11 @@ class TestVnflcmV2EnhancedPolicy(TestVnflcmV2):
]
)
if tenant:
inst.instantiatedVnfInfo.metadata = {'namespace': tenant}
inst.instantiatedVnfInfo.metadata = {'tenant': tenant}
# inst.instantiatedVnfInfo = objects.VnfInstanceV2_InstantiatedVnfInfo(
# flavourId='fake_flavour_id',
# vnfState='STARTED',
# metadata={'namespace': tenant}
# metadata={'tenant': tenant}
# )
inst.create(self.context)

View File

@@ -1658,7 +1658,8 @@ _inst_info_example = {
}
],
"metadata": {
"stack_id": STACK_ID
"stack_id": STACK_ID,
"tenant": "nfv"
}
# "vnfcInfo": omitted
}
@@ -2239,7 +2240,8 @@ _expected_inst_info = {
"VDU2": {"computeFlavourId": "m1.small",
"vcImageId": "image-VDU2"}
}
}
},
"tenant": "nfv"
}
}
@@ -2304,7 +2306,8 @@ _expected_inst_info_vnfc_updated["metadata"] = {
"fixed_ips": []
}
}
}
},
"tenant": "nfv"
}
@@ -2764,7 +2767,8 @@ _expected_inst_info_change_ext_conn = {
"fixed_ips": []
}
}
}
},
"tenant": "nfv"
}
}
@@ -3184,7 +3188,8 @@ _expected_inst_info_S = {
"VDU2-0": {"computeFlavourId": "m1.small"},
"VDU2-VirtualStorage-0": {"vcImageId": "image-VDU2"}
}
}
},
"tenant": "nfv"
}
}

View File

@@ -1986,65 +1986,95 @@ def get_test_data_policy_index():
}
test_data = []
inst_1 = make_vnf_instance('openstack', 'provider_A',
area='area_A@region_A')
area='area_A@region_A', tenant='tenant_A')
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': [inst_1.id]
})
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_all@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': [inst_1.id]
})
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@all', 'VENDOR_all'],
'roles': ['AREA_all@all', 'VENDOR_all',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': [inst_1.id]
})
test_data.append({
'vnf_instance_list': [inst_1],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@all', 'VENDOR_all',
'TENANT_all'],
'expected_vnf_inst_ids': [inst_1.id]
})
inst_2 = make_vnf_instance(
'openstack', 'provider_A', area='area_A@region_A',
'openstack', 'provider_A', area='area_A@region_A', tenant='tenant_A',
instantiated_state=fields.VnfInstanceState.INSTANTIATED)
test_data.append({
'vnf_instance_list': [inst_2],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': [inst_2.id]
})
test_data.append({
'vnf_instance_list': [inst_2],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_all@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': [inst_2.id]
})
test_data.append({
'vnf_instance_list': [inst_2],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@all', 'VENDOR_all'],
'roles': ['AREA_all@all', 'VENDOR_all',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': [inst_2.id]
})
test_data.append({
'vnf_instance_list': [inst_2],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@all', 'VENDOR_all',
'TENANT_all'],
'expected_vnf_inst_ids': [inst_2.id]
})
inst_3 = make_vnf_instance(
'openstack', 'provider_A',
'openstack', 'provider_A', tenant='tenant_A',
instantiated_state=fields.VnfInstanceState.INSTANTIATED)
test_data.append({
'vnf_instance_list': [inst_3],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': []
})
test_data.append({
'vnf_instance_list': [inst_3],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_all@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': []
})
test_data.append({
'vnf_instance_list': [inst_3],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@all', 'VENDOR_all'],
'roles': ['AREA_all@all', 'VENDOR_all',
'TENANT_tenant_A'],
'expected_vnf_inst_ids': []
})
test_data.append({
'vnf_instance_list': [inst_3],
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@all', 'VENDOR_all',
'TENANT_all'],
'expected_vnf_inst_ids': []
})
inst_4 = make_vnf_instance(
@@ -2130,6 +2160,50 @@ def get_test_data_policy_instantiate():
return test_data
def get_test_data_policy_delete():
test_data = [
# 'expected_status_code': http_client.NO_CONTENT
{
'vnf_instance_updates': {'vnf_provider': 'provider_A'},
'rules': {
"os_nfv_orchestration_api:vnf_instances:delete":
"vendor:%(vendor)s"
},
'roles': ['VENDOR_provider_A'],
'expected_status_code': http_client.NO_CONTENT
},
{
'vnf_instance_updates': {'vnf_provider': 'provider_A'},
'rules': {
"os_nfv_orchestration_api:vnf_instances:delete":
"vendor:%(vendor)s"
},
'roles': ['VENDOR_all'],
'expected_status_code': http_client.NO_CONTENT
},
# 'expected_status_code': http_client.FORBIDDEN
{
'vnf_instance_updates': {'vnf_provider': 'provider_A'},
'rules': {
"os_nfv_orchestration_api:vnf_instances:delete":
"vendor:%(vendor)s"
},
'roles': [],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': {'vnf_provider': 'provider_A'},
'rules': {
"os_nfv_orchestration_api:vnf_instances:delete":
"vendor:%(vendor)s"
},
'roles': ['VENDOR_provider_B'],
'expected_status_code': http_client.FORBIDDEN
},
]
return test_data
def get_test_data_policy_vnf_not_instantiated(
action, success_status_code=http_client.OK):
# openstack
@@ -2168,7 +2242,8 @@ def get_test_data_policy_vnf_not_instantiated(
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_status_code': success_status_code
},
{
@@ -2194,7 +2269,8 @@ def get_test_data_policy_vnf_not_instantiated(
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_vendor,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_status_code': success_status_code
},
{
@@ -2209,6 +2285,13 @@ def get_test_data_policy_vnf_not_instantiated(
'roles': ['AREA_all@region_A', 'VENDOR_all', 'TENANT_all'],
'expected_status_code': success_status_code
},
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_A',
'TENANT_tenant_B'],
'expected_status_code': success_status_code
},
# 'expected_status_code': http_client.FORBIDDEN
{
'vnf_instance_updates': vnf_instance_updates,
@@ -2231,37 +2314,49 @@ def get_test_data_policy_vnf_not_instantiated(
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_B'],
'roles': ['TENANT_tenant_A'],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_area_B@region_A', 'VENDOR_provider_A'],
'roles': ['AREA_area_A@region_A', 'VENDOR_provider_B',
'TENANT_tenant_A'],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@region_B', 'VENDOR_provider_A'],
'roles': ['AREA_area_B@region_A', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all', 'VENDOR_provider_A'],
'roles': ['AREA_all@region_B', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@', 'VENDOR_provider_A'],
'roles': ['AREA_all', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_status_code': http_client.FORBIDDEN
},
{
'vnf_instance_updates': vnf_instance_updates_with_wrong_area,
'rules': rule_area_vendor_tenant,
'roles': ['AREA_all@', 'VENDOR_provider_A'],
'roles': ['AREA_all@', 'VENDOR_provider_A',
'TENANT_tenant_A'],
'expected_status_code': http_client.FORBIDDEN
},
]
@@ -2283,7 +2378,7 @@ def make_vnf_instance_updates(
'vim_connection_info': [vim_connection_info]
}
if tenant:
vnf_instance_updates.update({'vnf_metadata': {"namespace": tenant}})
vnf_instance_updates.update({'vnf_metadata': {"tenant": tenant}})
return vnf_instance_updates
@@ -2298,13 +2393,15 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
test_data = []
# openstack
vnf_instance_updates_1 = make_vnf_instance_updates(
'openstack', 'provider_A', area='area_A@region_A')
'openstack', 'provider_A', area='area_A@region_A',
tenant='tenant_A')
test_data.append({
'vnf_instance_updates': vnf_instance_updates_1,
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A'
'VENDOR_provider_A',
'TENANT_tenant_A'
],
'expected_status_code': success_status_code
})
@@ -2313,7 +2410,8 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_all@region_A',
'VENDOR_provider_A'
'VENDOR_provider_A',
'TENANT_tenant_A'
],
'expected_status_code': success_status_code
})
@@ -2322,7 +2420,8 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_all@all',
'VENDOR_provider_A'
'VENDOR_provider_A',
'TENANT_tenant_A'
],
'expected_status_code': success_status_code
})
@@ -2331,7 +2430,8 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_all@all',
'VENDOR_all'
'VENDOR_all',
'TENANT_tenant_A'
],
'expected_status_code': success_status_code
})
@@ -2340,7 +2440,8 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_all@all',
'VENDOR_all'
'VENDOR_all',
'TENANT_all'
],
'expected_status_code': success_status_code
})
@@ -2350,7 +2451,8 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_B@region_A',
'VENDOR_provider_A'
'VENDOR_provider_A',
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
})
@@ -2360,7 +2462,8 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_B',
'VENDOR_provider_A'
'VENDOR_provider_A',
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
})
@@ -2370,11 +2473,22 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_B'
'VENDOR_provider_B',
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
})
# wrong tenant role
test_data.append({
'vnf_instance_updates': vnf_instance_updates_1,
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A',
'TENANT_tenant_B'
],
'expected_status_code': http_client.FORBIDDEN
})
vnf_instance_updates_2 = make_vnf_instance_updates(
'openstack', 'provider_A')
test_data.append({
@@ -2382,7 +2496,8 @@ def get_test_data_policy_vnf_instantiated(action, success_status_code):
'rules': rule_area_vendor_tenant,
'roles': [
'AREA_area_A@region_A',
'VENDOR_provider_A'
'VENDOR_provider_A',
'TENANT_tenant_A'
],
'expected_status_code': http_client.FORBIDDEN
})

View File

@@ -29,7 +29,6 @@ from oslo_config import cfg
from oslo_policy import policy as oslo_policy
from oslo_serialization import jsonutils
from tacker._i18n import _
from tacker.api.views import vnf_subscriptions as vnf_subscription_view
from tacker.api.vnflcm.v1 import controller
from tacker.api.vnflcm.v1 import sync_resource
@@ -5303,8 +5302,7 @@ class TestControllerEnhancedPolicy(TestController):
resp = req.get_response(fakes.wsgi_app_v1(fake_auth_context=ctx))
self.assertEqual(expected_status_code, resp.status_code)
@ddt.data(*fakes.get_test_data_policy_vnf_instantiated(
'delete', http_client.NO_CONTENT))
@ddt.data(*fakes.get_test_data_policy_delete())
@ddt.unpack
@mock.patch('tacker.api.vnflcm.v1.controller.'
'VnfLcmController._delete')

View File

@@ -2040,6 +2040,7 @@ class TestOpenStack(base.FixturedTestCase):
vnf_instance = fd_utils.get_vnf_instance_object(
instantiated_vnf_info=inst_vnf_info)
vnf_instance.vnf_metadata = None
vim_connection_info = fd_utils.get_vim_connection_info_object()
resources = [{'resource_name': vnfc_resource_info.vdu_id,
@@ -2080,6 +2081,10 @@ class TestOpenStack(base.FixturedTestCase):
vnf_virtual_link_resource_info[0].vnf_link_ports[0].
resource_handle.resource_id)
# Check if tenant data is stored in vnf_metadata
self.assertEqual(vnf_instance.vnf_metadata['tenant'],
vim_connection_info.access_info['project_name'])
def test_post_vnf_instantiation_with_ext_managed_virtual_link(self):
v_s_resource_info = fd_utils.get_virtual_storage_resource_info(
desc_id="storage1", set_resource_id=False)

View File

@@ -1733,6 +1733,7 @@ class Kubernetes(abstract_driver.VnfAbstractDriver,
if not vnf_instance.vnf_metadata:
vnf_instance.vnf_metadata = {}
vnf_instance.vnf_metadata['namespace'] = namespace
vnf_instance.vnf_metadata['tenant'] = namespace
vnf_instance.save()
return {}

View File

@@ -66,6 +66,7 @@ def check_and_save_namespace(
if not vnf_instance.vnf_metadata:
vnf_instance.vnf_metadata = {}
vnf_instance.vnf_metadata['namespace'] = namespace
vnf_instance.vnf_metadata['tenant'] = namespace
vnf_instance.save()

View File

@@ -2586,6 +2586,11 @@ class OpenStack(abstract_driver.VnfAbstractDriver,
vim_connection_info, instantiate_vnf_req):
self._update_vnfc_resources_and_info(
context, vnf_instance, vim_connection_info)
# store tenant information for enhanced policy
if not vnf_instance.vnf_metadata:
vnf_instance.vnf_metadata = {}
access_info = vim_connection_info.access_info
vnf_instance.vnf_metadata['tenant'] = access_info.get('project_name')
@log.log
def post_change_ext_conn_vnf(self, context, vnf_instance,