Merge "Fix vnfdId format for VNF package"

This commit is contained in:
Zuul
2023-09-05 04:46:11 +00:00
committed by Gerrit Code Review
18 changed files with 129 additions and 37 deletions

View File

@@ -112,6 +112,15 @@ in section 6.8.1 in `NFV-SOL001 v2.6.1`_. Its required properties are:
* *flavour_description* - is description of the deployment flavour. The
default can be "" (empty string).
.. note:: Section 6.8.1 of `NFV-SOL001 v2.6.1`_ states that the
``descriptor_id`` string shall be UUID (`IETF RFC 4122`_:
"A Universally Unique IDentifier (UUID) URN Namespace").
Tacker recommends using UUIDs according to `NFV-SOL001 v2.6.1`_,
but ``vnfdId`` defined in `NFV-SOL002 v3.3.1`_ /
`NFV-SOL003 v3.3.1`_ has no format restrictions, so any single-byte
character string (including alphabets, numbers, spaces, hyphens,
underscores, and periods) is also supported.
Topology Template Files
-----------------------
@@ -251,5 +260,8 @@ resources such as VDU and CP. The file includes:
.. _TOSCA-Simple-Profile-yaml-v1.2 : http://docs.oasis-open.org/tosca/TOSCA-Simple-Profile-YAML/v1.2/TOSCA-Simple-Profile-YAML-v1.2.html
.. _NFV-SOL001 v2.6.1 : https://www.etsi.org/deliver/etsi_gs/NFV-SOL/001_099/001/02.06.01_60/gs_NFV-SOL001v020601p.pdf
.. _IETF RFC 4122 : https://datatracker.ietf.org/doc/html/rfc4122
.. _NFV-SOL002 v3.3.1 : https://www.etsi.org/deliver/etsi_gs/NFV-SOL/001_099/002/03.03.01_60/gs_nfv-sol002v030301p.pdf
.. _NFV-SOL003 v3.3.1 : https://www.etsi.org/deliver/etsi_gs/NFV-SOL/001_099/003/03.03.01_60/gs_nfv-sol003v030301p.pdf
.. _etsi_nfv_sol001_common_types.yaml : https://forge.etsi.org/rep/nfv/SOL001/raw/v2.6.1/etsi_nfv_sol001_common_types.yaml
.. _etsi_nfv_sol001_vnfd_types.yaml : https://forge.etsi.org/rep/nfv/SOL001/raw/v2.6.1/etsi_nfv_sol001_vnfd_types.yaml

View File

@@ -137,7 +137,7 @@ class VnfPackageVnfd(model_base.BASE, VnfPackageVnfdSoftDeleteMixin,
package_uuid = sa.Column(sa.String(36),
sa.ForeignKey('vnf_packages.id'),
nullable=False)
vnfd_id = sa.Column(types.Uuid, nullable=False)
vnfd_id = sa.Column(sa.String(255), nullable=False)
vnf_provider = sa.Column(sa.String(255), nullable=False)
vnf_product_name = sa.Column(sa.String(255), nullable=False)
vnf_software_version = sa.Column(sa.String(255), nullable=False)
@@ -212,7 +212,7 @@ class VnfInstance(model_base.BASE, models.SoftDeleteMixin,
vnf_product_name = sa.Column(sa.String(255), nullable=False)
vnf_software_version = sa.Column(sa.String(255), nullable=False)
vnfd_version = sa.Column(sa.String(255), nullable=False)
vnfd_id = sa.Column(types.Uuid, nullable=False)
vnfd_id = sa.Column(sa.String(255), nullable=False)
instantiation_state = sa.Column(sa.String(255), nullable=False)
task_state = sa.Column(sa.String(255), nullable=True)
vim_connection_info = sa.Column(sa.JSON(), nullable=True)

View File

@@ -0,0 +1,64 @@
# Copyright 2023 OpenStack Foundation
#
# 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.
#
"""alter_vnfd_id_format
Revision ID: 4c0e2e2c2e02
Revises: 34cfceb25a49
Create Date: 2023-04-28 08:05:13.246214
"""
# revision identifiers, used by Alembic.
revision = '4c0e2e2c2e02'
down_revision = '34cfceb25a49'
from alembic import op
import sqlalchemy as sa
# flake8: noqa: E402
def upgrade(active_plugins=None, options=None):
bind = op.get_bind()
engine = bind.engine
fk_tables = ('servicetypes', 'vnf', 'vnfd_attribute')
fk_prefixes = {"servicetypes":"servicetypes", "vnf":"devices",
"vnfd_attribute":"devicetemplateattributes"}
for table in fk_tables:
if engine.name == 'postgresql':
alter_sql_drop_foreign_key = f"ALTER TABLE {table} \
DROP CONSTRAINT {fk_prefixes[table]}_template_id_fkey;"
else:
alter_sql_drop_foreign_key = f"ALTER TABLE {table} \
DROP FOREIGN KEY {table}_ibfk_1;"
op.execute(alter_sql_drop_foreign_key)
op.alter_column('vnfd', 'id', type_=sa.String(255),
existing_type=sa.String(36), nullable=False)
vnfd_id_tables = ('servicetypes', 'vnf', 'vnfd_attribute',
'vnf_instances', 'vnf_package_vnfd')
for table in vnfd_id_tables:
op.alter_column(table, 'vnfd_id', type_=sa.String(255),
existing_type=sa.String(36), nullable=False)
for table in fk_tables:
if engine.name == 'postgresql':
foreign_key = f"{fk_prefixes[table]}_template_id_fkey"
else:
foreign_key = f"{table}_ibfk_1"
op.create_foreign_key(foreign_key, table, 'vnfd', ['vnfd_id'],
['id'])

View File

@@ -1 +1 @@
34cfceb25a49
4c0e2e2c2e02

View File

@@ -59,11 +59,14 @@ CREATE_STATES = (constants.PENDING_CREATE, constants.DEAD)
###########################################################################
# db tables
class VNFD(model_base.BASE, models_v1.HasId, models_v1.HasTenant,
models_v1.Audit):
class VNFD(model_base.BASE, models_v1.HasTenant, models_v1.Audit):
"""Represents VNFD to create VNF."""
__tablename__ = 'vnfd'
# vnfdId
id = sa.Column(sa.String(255), primary_key=True,
default=uuidutils.generate_uuid)
# Descriptive name
name = sa.Column(sa.String(255), nullable=False)
description = sa.Column(sa.Text)
@@ -98,7 +101,7 @@ class ServiceType(model_base.BASE, models_v1.HasId, models_v1.HasTenant):
Since a vnf may provide many services, This is one-to-many
relationship.
"""
vnfd_id = sa.Column(types.Uuid, sa.ForeignKey('vnfd.id'),
vnfd_id = sa.Column(sa.String(255), sa.ForeignKey('vnfd.id'),
nullable=False)
service_type = sa.Column(sa.String(64), nullable=False)
@@ -111,7 +114,7 @@ class VNFDAttribute(model_base.BASE, models_v1.HasId):
"""
__tablename__ = 'vnfd_attribute'
vnfd_id = sa.Column(types.Uuid, sa.ForeignKey('vnfd.id'),
vnfd_id = sa.Column(sa.String(255), sa.ForeignKey('vnfd.id'),
nullable=False)
key = sa.Column(sa.String(255), nullable=False)
value = sa.Column(sa.TEXT(65535), nullable=True)
@@ -126,7 +129,7 @@ class VNF(model_base.BASE, models_v1.HasId, models_v1.HasTenant,
"""
__tablename__ = 'vnf'
vnfd_id = sa.Column(types.Uuid, sa.ForeignKey('vnfd.id'))
vnfd_id = sa.Column(sa.String(255), sa.ForeignKey('vnfd.id'))
vnfd = orm.relationship('VNFD')
name = sa.Column(sa.String(255), nullable=False)

View File

@@ -68,7 +68,7 @@ class VNF(base.TackerObject, base.TackerObjectDictCompat,
'id': fields.UUIDField(nullable=False),
'tenant_id': fields.UUIDField(nullable=False),
'name': fields.StringField(nullable=False),
'vnfd_id': fields.UUIDField(nullable=False),
'vnfd_id': fields.StringField(nullable=False),
'instance_id': fields.StringField(nullable=True),
'mgmt_ip_address': fields.StringField(nullable=True),
'status': fields.StringField(nullable=True),

View File

@@ -360,7 +360,7 @@ class VnfInstance(base.TackerObject, base.TackerPersistentObject,
'vnf_instance_description', 'string', 'VnfInstance'),
'instantiationState': ('instantiation_state', 'string', 'VnfInstance'),
'taskState': ('task_state', 'string', 'VnfInstance'),
'vnfdId': ('vnfd_id', 'uuid', 'VnfInstance'),
'vnfdId': ('vnfd_id', 'string', 'VnfInstance'),
'vnfProvider': ('vnf_provider', 'string', 'VnfInstance'),
'vnfProductName': ('vnf_product_name', 'string', 'VnfInstance'),
'vnfSoftwareVersion': (

View File

@@ -171,7 +171,7 @@ class VnfPackageVnfd(base.TackerObject, base.TackerObjectDictCompat,
fields = {
'id': fields.UUIDField(nullable=False),
'package_uuid': fields.UUIDField(nullable=False),
'vnfd_id': fields.UUIDField(nullable=False),
'vnfd_id': fields.StringField(nullable=False),
'vnf_provider': fields.StringField(nullable=False),
'vnf_product_name': fields.StringField(nullable=False),
'vnf_software_version': fields.StringField(nullable=False),

View File

@@ -88,7 +88,7 @@ class Vnfd(base.TackerObject, base.TackerObjectDictCompat,
VERSION = '1.0'
fields = {
'id': fields.UUIDField(nullable=False),
'id': fields.StringField(nullable=False),
'tenant_id': fields.UUIDField(nullable=False),
'name': fields.StringField(nullable=False),
'description': fields.StringField(nullable=True),

View File

@@ -80,7 +80,7 @@ class VnfdAttribute(base.TackerObject, base.TackerObjectDictCompat,
fields = {
'id': fields.UUIDField(nullable=False),
'vnfd_id': fields.UUIDField(nullable=False),
'vnfd_id': fields.StringField(nullable=False),
'key': fields.StringField(nullable=False),
'value': fields.StringField(nullable=True),
}

View File

@@ -118,9 +118,10 @@ class BaseTackerTestV2(base.BaseTestCase):
@classmethod
def create_vnf_package(cls, sample_path, user_data={},
image_path=None, nfvo=False, userdata_path=None,
provider=None, namespace=None):
provider=None, namespace=None, vnfd_id=None):
if vnfd_id is None:
vnfd_id = uuidutils.generate_uuid()
tmp_dir = tempfile.mkdtemp()
utils.make_zip(sample_path, tmp_dir, vnfd_id, image_path,

View File

@@ -49,12 +49,12 @@ class BaseSolV2Test(base_v2.BaseTackerTestV2):
@classmethod
def create_vnf_package(cls, sample_path, user_data={},
image_path=None, nfvo=False, userdata_path=None,
provider=None):
provider=None, vnfd_id=None):
return super().create_vnf_package(sample_path, user_data=user_data,
image_path=image_path, nfvo=nfvo,
userdata_path=userdata_path,
provider=provider)
provider=provider, vnfd_id=vnfd_id)
def get_network_ids(self, networks):
path = "/v2.0/networks"

View File

@@ -16,17 +16,17 @@
import json
import os
import shutil
import string
import tempfile
from oslo_utils import uuidutils
from tacker.tests.functional.sol_v2_common import paramgen
from tacker.tests.functional.sol_v2_common import utils
SUPPORT_STRING_FOR_VNFD_ID = string.ascii_letters + string.digits + "-._ "
vnfd_id = SUPPORT_STRING_FOR_VNFD_ID + "max_vnfd_id"
zip_file_name = os.path.basename(os.path.abspath(".")) + '.zip'
tmp_dir = tempfile.mkdtemp()
vnfd_id = uuidutils.generate_uuid()
# tacker/tests/etc...
image_dir = "../../../../etc/samples/etsi/nfv/common/Files/images/"

View File

@@ -16,17 +16,18 @@
import json
import os
import shutil
import string
import tempfile
from oslo_utils import uuidutils
from tacker.tests.functional.sol_v2_common import paramgen
from tacker.tests.functional.sol_v2_common import utils
SUPPORT_STRING_FOR_VNFD_ID = string.ascii_letters + string.digits + "-._ "
vnfd_id = SUPPORT_STRING_FOR_VNFD_ID + "min_vnfd_id"
zip_file_name = os.path.basename(os.path.abspath(".")) + '.zip'
tmp_dir = tempfile.mkdtemp()
vnfd_id = uuidutils.generate_uuid()
# tacker/sol_refactored/infra_drivers/openstack/userdata_standard.py
# /tests/functional/sol_v2_common/samples/sampleX
userdata_dir = "../../../../../sol_refactored/infra_drivers/openstack/"

View File

@@ -16,17 +16,17 @@
import json
import os
import shutil
import string
import tempfile
from oslo_utils import uuidutils
from tacker.tests.functional.sol_v2_common import paramgen
from tacker.tests.functional.sol_v2_common import utils
SUPPORT_STRING_FOR_VNFD_ID = string.ascii_letters + string.digits + "-._ "
vnfd_id = SUPPORT_STRING_FOR_VNFD_ID + "new_max_vnfd_id"
zip_file_name = os.path.basename(os.path.abspath(".")) + '.zip'
tmp_dir = tempfile.mkdtemp()
vnfd_id = uuidutils.generate_uuid()
# tacker/sol_refactored/infra_drivers/openstack/userdata_standard.py
# /tests/functional/sol_v2_common/samples/sampleX

View File

@@ -16,17 +16,17 @@
import json
import os
import shutil
import string
import tempfile
from oslo_utils import uuidutils
from tacker.tests.functional.sol_v2_common import paramgen
from tacker.tests.functional.sol_v2_common import utils
SUPPORT_STRING_FOR_VNFD_ID = string.ascii_letters + string.digits + "-._ "
vnfd_id = SUPPORT_STRING_FOR_VNFD_ID + "upd_new_min_vnfd_id"
zip_file_name = os.path.basename(os.path.abspath(".")) + '.zip'
tmp_dir = tempfile.mkdtemp()
vnfd_id = uuidutils.generate_uuid()
# tacker/tests/etc...
image_dir = "../../../../etc/samples/etsi/nfv/common/Files/images/"

View File

@@ -16,17 +16,17 @@
import json
import os
import shutil
import string
import tempfile
from oslo_utils import uuidutils
from tacker.tests.functional.sol_v2_common import paramgen
from tacker.tests.functional.sol_v2_common import utils
SUPPORT_STRING_FOR_VNFD_ID = string.ascii_letters + string.digits + "-._ "
vnfd_id = SUPPORT_STRING_FOR_VNFD_ID + "upd_max_vnfd_id"
zip_file_name = os.path.basename(os.path.abspath(".")) + '.zip'
tmp_dir = tempfile.mkdtemp()
vnfd_id = uuidutils.generate_uuid()
# tacker/tests/etc...
image_dir = "../../../../etc/samples/etsi/nfv/common/Files/images/"

View File

@@ -14,11 +14,19 @@
# under the License.
import os
import string
from tacker.objects import fields
from tacker.tests.functional.sol_v2_common import base_v2
from tacker.tests.functional.sol_v2_common import paramgen
SUPPORT_STRING_FOR_VNFD_ID = f"{string.ascii_letters}{string.digits}-._ "
MAX_VNFD_ID = f"{SUPPORT_STRING_FOR_VNFD_ID}max_vnfd_id"
MIN_VNFD_ID = f"{SUPPORT_STRING_FOR_VNFD_ID}min_vnfd_id"
UPD_MAX_VNFD_ID = f"{SUPPORT_STRING_FOR_VNFD_ID}upd_max_vnfd_id"
NEW_MAX_VNFD_ID = f"{SUPPORT_STRING_FOR_VNFD_ID}new_max_vnfd_id"
UPD_NEW_MIN_VNFD_ID = f"{SUPPORT_STRING_FOR_VNFD_ID}upd_new_min_vnfd_id"
class IndividualVnfcMgmtBasicTest(base_v2.BaseSolV2Test):
@@ -46,26 +54,28 @@ class IndividualVnfcMgmtBasicTest(base_v2.BaseSolV2Test):
"../sol_v2_common/samples/basic_lcms_max_individual_vnfc")
cls.max_pkg, cls.max_vnfd_id = cls.create_vnf_package(
pkg_path_1, image_path=image_path,
userdata_path=userdata_path)
userdata_path=userdata_path, vnfd_id=MAX_VNFD_ID)
# vnf package for basic lcms tests min pattern
pkg_path_2 = os.path.join(cur_dir,
"../sol_v2_common/samples/basic_lcms_min_individual_vnfc")
cls.min_pkg, cls.min_vnfd_id = cls.create_vnf_package(
pkg_path_2, userdata_path=userdata_path)
pkg_path_2, userdata_path=userdata_path,
vnfd_id=MIN_VNFD_ID)
# vnf package for update vnf max pattern
pkg_path_3 = os.path.join(cur_dir,
"../sol_v2_common/samples/update_vnf_max_individual_vnfc")
cls.upd_max_pkg, cls.upd_max_vnfd_id = cls.create_vnf_package(
pkg_path_3, image_path=image_path,
userdata_path=userdata_path)
userdata_path=userdata_path, vnfd_id=UPD_MAX_VNFD_ID)
# vnf package for change vnf package max pattern
pkg_path_4 = os.path.join(cur_dir,
"../sol_v2_common/samples/change_vnfpkg_max_individual_vnfc")
cls.new_max_pkg, cls.new_max_vnfd_id = cls.create_vnf_package(
pkg_path_4, userdata_path=userdata_path)
pkg_path_4, userdata_path=userdata_path,
vnfd_id=NEW_MAX_VNFD_ID)
# vnf package for change vnf package or update min pattern
pkg_path_5 = os.path.join(
@@ -73,7 +83,8 @@ class IndividualVnfcMgmtBasicTest(base_v2.BaseSolV2Test):
"../sol_v2_common/samples/"
"change_vnfpkg_or_update_min_individual_vnfc")
cls.upd_new_min_pkg, cls.upd_new_min_vnfd_id = cls.create_vnf_package(
pkg_path_5, image_path=image_path, userdata_path=userdata_path)
pkg_path_5, image_path=image_path, userdata_path=userdata_path,
vnfd_id=UPD_NEW_MIN_VNFD_ID)
cls.expected_list_attrs = [
'id',