class TerminateVnfRequest(base.TackerObject, base.TackerPersistentObject): # Version 1.0: Initial version VERSION = '1.0' fields = { 'termination_type': fields.VnfInstanceTerminationTypeField(nullable=False), 'graceful_termination_timeout': fields.IntegerField(nullable=True, default=0), 'additional_params': fields.DictOfStringsField(nullable=True, default={}), } @classmethod def obj_from_primitive(cls, primitive, context): if 'tacker_object.name' in primitive: obj_terminate_vnf_req = super(TerminateVnfRequest, cls).obj_from_primitive( primitive, context) else: obj_terminate_vnf_req = TerminateVnfRequest._from_dict(primitive) return obj_terminate_vnf_req @classmethod def _from_dict(cls, data_dict): termination_type = data_dict.get('termination_type') graceful_termination_timeout = \ data_dict.get('graceful_termination_timeout', 0) additional_params = data_dict.get('additional_params', {}) return cls(termination_type=termination_type, graceful_termination_timeout=graceful_termination_timeout, additional_params=additional_params)
class ScaleVnfRequest(base.TackerObject): # Version 1.0: Initial version VERSION = '1.0' fields = { 'type': fields.StringField(nullable=False), 'aspect_id': fields.StringField(nullable=False), 'number_of_steps': fields.IntegerField(nullable=True, default=1), 'additional_params': fields.DictOfStringsField(nullable=True, default={}), } @classmethod def obj_from_primitive(cls, primitive, context): if 'tacker_object.name' in primitive: obj_scle_vnf_req = super(ScaleVnfRequest, cls).obj_from_primitive( primitive, context) else: obj_scle_vnf_req = ScaleVnfRequest._from_dict(primitive) return obj_scle_vnf_req @classmethod def _from_dict(cls, data_dict): type = data_dict.get('type') aspect_id = data_dict.get('aspect_id') number_of_steps = data_dict.get('number_of_steps') additional_params = data_dict.get('additional_params') obj = cls(type=type, aspect_id=aspect_id, number_of_steps=number_of_steps, additional_params=additional_params) return obj
class InstantiateVnfRequest(base.TackerObject): # Version 1.0: Initial version VERSION = '1.0' fields = { 'flavour_id': fields.StringField(nullable=False), 'instantiation_level_id': fields.StringField(nullable=True, default=None), 'ext_managed_virtual_links': fields.ListOfObjectsField( 'ExtManagedVirtualLinkData', nullable=True, default=[]), 'vim_connection_info': fields.ListOfObjectsField( 'VimConnectionInfo', nullable=True, default=[]), 'ext_virtual_links': fields.ListOfObjectsField( 'ExtVirtualLinkData', nullable=True, default=[]), 'additional_params': fields.DictOfStringsField(nullable=True, default={}), } @classmethod def obj_from_primitive(cls, primitive, context): if 'tacker_object.name' in primitive: obj_instantiate_vnf_req = super( InstantiateVnfRequest, cls).obj_from_primitive( primitive, context) else: if 'ext_managed_virtual_links' in primitive.keys(): obj_data = [ExtManagedVirtualLinkData._from_dict( ext_manage) for ext_manage in primitive.get( 'ext_managed_virtual_links', [])] primitive.update({'ext_managed_virtual_links': obj_data}) if 'vim_connection_info' in primitive.keys(): obj_data = [objects.VimConnectionInfo._from_dict( vim_conn) for vim_conn in primitive.get( 'vim_connection_info', [])] primitive.update({'vim_connection_info': obj_data}) if 'ext_virtual_links' in primitive.keys(): obj_data = [ExtVirtualLinkData.obj_from_primitive( ext_vir_link, context) for ext_vir_link in primitive.get( 'ext_virtual_links', [])] primitive.update({'ext_virtual_links': obj_data}) obj_instantiate_vnf_req = InstantiateVnfRequest._from_dict( primitive) return obj_instantiate_vnf_req @classmethod def _from_dict(cls, data_dict): flavour_id = data_dict.get('flavour_id') instantiation_level_id = data_dict.get('instantiation_level_id') ext_managed_virtual_links = data_dict.get('ext_managed_virtual_links', []) vim_connection_info = data_dict.get('vim_connection_info', []) ext_virtual_links = data_dict.get('ext_virtual_links', []) additional_params = data_dict.get('additional_params', {}) return cls(flavour_id=flavour_id, instantiation_level_id=instantiation_level_id, ext_managed_virtual_links=ext_managed_virtual_links, vim_connection_info=vim_connection_info, ext_virtual_links=ext_virtual_links, additional_params=additional_params) @classmethod def from_vnf_instance(cls, vnf_instance): vnf_instantiated_info = vnf_instance.instantiated_vnf_info # Vim connection info vim_connection_info = _get_vim_connection_info(vnf_instance) # Flavour id flavour_id = vnf_instantiated_info.flavour_id # Instantiation level instantiation_level_id = vnf_instantiated_info.instantiation_level_id # Externally managed virtual links ext_managed_virtual_links = _get_ext_managed_virtual_links( vnf_instantiated_info) # External virtual links ext_virtual_links = _get_ext_virtual_link_data(vnf_instantiated_info) additional_params = vnf_instantiated_info.additional_params instantiate_vnf_request = cls(flavour_id=flavour_id, instantiation_level_id=instantiation_level_id, ext_managed_virtual_links=ext_managed_virtual_links, vim_connection_info=vim_connection_info, ext_virtual_links=ext_virtual_links, additional_params=additional_params) return instantiate_vnf_request
class VnfInstance(base.TackerObject, base.TackerPersistentObject, base.TackerObjectDictCompat): # Version 1.0: Initial version VERSION = '1.0' fields = { 'id': fields.UUIDField(nullable=False), 'vnf_instance_name': fields.StringField(nullable=True), 'vnf_instance_description': fields.StringField(nullable=True), 'instantiation_state': fields.VnfInstanceStateField( nullable=False, default=fields.VnfInstanceState.NOT_INSTANTIATED), 'task_state': fields.StringField(nullable=True, default=None), '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), 'vnfd_version': fields.StringField(nullable=False), 'vim_connection_info': fields.ListOfObjectsField('VimConnectionInfo', nullable=True, default=[]), 'tenant_id': fields.StringField(nullable=False), 'instantiated_vnf_info': fields.ObjectField('InstantiatedVnfInfo', nullable=True, default=None), 'vnf_pkg_id': fields.StringField(nullable=False), 'vnf_metadata': fields.DictOfStringsField(nullable=True, default={}) } ALL_ATTRIBUTES = { 'id': ('id', "string", 'VnfInstance'), 'vnfInstanceName': ('vnf_instance_name', 'string', 'VnfInstance'), 'vnfInstanceDescription': ('vnf_instance_description', 'string', 'VnfInstance'), 'instantiationState': ('instantiation_state', 'string', 'VnfInstance'), 'taskState': ('task_state', 'string', 'VnfInstance'), 'vnfdId': ('vnfd_id', 'string', 'VnfInstance'), 'vnfProvider': ('vnf_provider', 'string', 'VnfInstance'), 'vnfProductName': ('vnf_product_name', 'string', 'VnfInstance'), 'vnfSoftwareVersion': ('vnf_software_version', 'string', 'VnfInstance'), 'vnfdVersion': ('vnfd_version', 'string', 'VnfInstance'), 'tenantId': ('tenant_id', 'string', 'VnfInstance'), 'vnfPkgId': ('vnf_pkg_id', 'string', 'VnfInstance'), 'vimConnectionInfo/*': ('vim_connection_info', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstance" }), 'metadata/*': ('vnf_metadata', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstance" }), } ALL_ATTRIBUTES.update( vnf_instantiated_info.InstantiatedVnfInfo.ALL_ATTRIBUTES) FLATTEN_ATTRIBUTES = utils.flatten_dict(ALL_ATTRIBUTES.copy()) def __init__(self, context=None, **kwargs): super(VnfInstance, self).__init__(context, **kwargs) self.obj_set_defaults() @staticmethod def _from_db_object(context, vnf_instance, db_vnf_instance, expected_attrs=None): special_fields = ["instantiated_vnf_info", "vim_connection_info"] for key in vnf_instance.fields: if key in special_fields: continue setattr(vnf_instance, key, db_vnf_instance[key]) VnfInstance._load_instantiated_vnf_info_from_db_object( context, vnf_instance, db_vnf_instance) vim_connection_info = db_vnf_instance['vim_connection_info'] vim_connection_list = [ objects.VimConnectionInfo.obj_from_primitive(vim_info, context) for vim_info in vim_connection_info ] vnf_instance.vim_connection_info = vim_connection_list vnf_instance._context = context vnf_instance.obj_reset_changes() return vnf_instance @staticmethod def _load_instantiated_vnf_info_from_db_object(context, vnf_instance, db_vnf_instance): if db_vnf_instance['instantiated_vnf_info']: inst_vnf_info = \ objects.InstantiatedVnfInfo.obj_from_db_obj(context, db_vnf_instance['instantiated_vnf_info']) vnf_instance.instantiated_vnf_info = inst_vnf_info @base.remotable def create(self): if self.obj_attr_is_set('id'): raise exceptions.ObjectActionError(action='create', reason=_('already created')) updates = self.obj_get_changes() if 'id' not in updates: updates['id'] = uuidutils.generate_uuid() self.id = updates['id'] db_vnf_instance = _vnf_instance_create(self._context, updates) expected_attrs = ["instantiated_vnf_info"] self._from_db_object(self._context, self, db_vnf_instance, expected_attrs=expected_attrs) @base.remotable def save(self): context = self._context updates = {} changes = self.obj_what_changed() for field in self.fields: if (self.obj_attr_is_set(field) and isinstance(self.fields[field], fields.ObjectField)): try: getattr(self, '_save_%s' % field)(context) except AttributeError: LOG.exception('No save handler for %s', field) elif (self.obj_attr_is_set(field) and isinstance( self.fields[field], fields.ListOfObjectsField)): field_list = getattr(self, field) updates[field] = [obj.obj_to_primitive() for obj in field_list] elif field in changes: updates[field] = self[field] expected_attrs = ["instantiated_vnf_info"] db_vnf_instance = _vnf_instance_update(self._context, self.id, updates, columns_to_join=expected_attrs) self._from_db_object(self._context, self, db_vnf_instance) def _save_instantiated_vnf_info(self, context): if self.instantiated_vnf_info: with self.instantiated_vnf_info.obj_alternate_context(context): self.instantiated_vnf_info.save() @base.remotable def destroy(self, context): if not self.obj_attr_is_set('id'): raise exceptions.ObjectActionError(action='destroy', reason='no uuid') _destroy_vnf_instance(context, self.id) def to_dict(self): data = { 'id': self.id, 'vnf_instance_name': self.vnf_instance_name, 'vnf_instance_description': self.vnf_instance_description, 'instantiation_state': self.instantiation_state, 'vnfd_id': self.vnfd_id, 'vnf_provider': self.vnf_provider, 'vnf_product_name': self.vnf_product_name, 'vnf_software_version': self.vnf_software_version, 'vnf_pkg_id': self.vnf_pkg_id, 'vnfd_version': self.vnfd_version, 'vnf_metadata': self.vnf_metadata } if (self.instantiation_state == fields.VnfInstanceState.INSTANTIATED and self.instantiated_vnf_info): data.update({ 'instantiated_vnf_info': self.instantiated_vnf_info.to_dict() }) vim_connection_info_list = [] for vim_connection_info in self.vim_connection_info: vim_connection_info_list.append(vim_connection_info.to_dict()) data.update({'vim_connection_info': vim_connection_info_list}) return data @base.remotable_classmethod def get_by_id(cls, context, id): expected_attrs = ["instantiated_vnf_info"] db_vnf_instance = _vnf_instance_get_by_id( context, id, columns_to_join=expected_attrs) return cls._from_db_object(context, cls(), db_vnf_instance, expected_attrs=expected_attrs)
class VnfPackage(base.TackerObject, base.TackerPersistentObject): # Version 1.0: Initial version VERSION = '1.0' fields = { 'id': fields.UUIDField(nullable=False), 'onboarding_state': fields.StringField(nullable=False), 'operational_state': fields.StringField(nullable=False), 'usage_state': fields.StringField(nullable=False), 'user_data': fields.DictOfStringsField(), 'tenant_id': fields.StringField(nullable=False), 'algorithm': fields.StringField(nullable=True), 'hash': fields.StringField(nullable=True), 'location_glance_store': fields.StringField(nullable=True), 'vnf_deployment_flavours': fields.ObjectField( 'VnfDeploymentFlavoursList', nullable=True), 'vnfd': fields.ObjectField('VnfPackageVnfd', nullable=True), } @staticmethod def _from_db_object(context, vnf_package, db_vnf_package, expected_attrs=None): if expected_attrs is None: expected_attrs = [] vnf_package._context = context for key in vnf_package.fields: if key in VNF_PACKAGE_OPTIONAL_ATTRS: continue if key == 'user_data': db_key = 'metadetails' else: db_key = key setattr(vnf_package, key, db_vnf_package[db_key]) vnf_package._context = context vnf_package._extra_attributes_from_db_object( vnf_package, db_vnf_package, expected_attrs) vnf_package.obj_reset_changes() return vnf_package @staticmethod def _extra_attributes_from_db_object(vnf_package, db_vnf_package, expected_attrs=None): """Method to help with migration of extra attributes to objects.""" if expected_attrs is None: expected_attrs = [] if 'vnf_deployment_flavours' in expected_attrs: vnf_package._load_vnf_deployment_flavours( db_vnf_package.get('vnf_deployment_flavours')) if 'vnfd' in expected_attrs: vnf_package._load_vnfd(db_vnf_package.get('vnfd')) def _load_vnf_deployment_flavours(self, db_flavours=_NO_DATA_SENTINEL): if db_flavours is _NO_DATA_SENTINEL: vnf_package = self.get_by_id( self._context, self.id, expected_attrs=['vnf_deployment_flavours']) if 'vnf_deployment_flavours' in vnf_package: self.vnf_deployment_flavours = \ vnf_package.vnf_deployment_flavours self.vnf_deployment_flavours.obj_reset_changes(recursive=True) self.obj_reset_changes(['vnf_deployment_flavours']) else: self.vnf_deployment_flavours = \ objects.VnfDeploymentFlavoursList(objects=[]) elif db_flavours: self.vnf_deployment_flavours = base.obj_make_list( self._context, objects.VnfDeploymentFlavoursList( self._context), objects.VnfDeploymentFlavour, db_flavours) self.obj_reset_changes(['vnf_deployment_flavours']) def _load_vnfd(self, db_vnfd=_NO_DATA_SENTINEL): if db_vnfd is None: self.vnfd = None elif db_vnfd is _NO_DATA_SENTINEL: vnf_package = self.get_by_id(self._context, self.id, expected_attrs=['vnfd']) if 'vnfd' in vnf_package and vnf_package.vnfd is not None: self.vnfd = vnf_package.vnfd self.vnfd.obj_reset_changes(recursive=True) self.obj_reset_changes(['vnfd']) else: self.vnfd = None elif db_vnfd: self.vnfd = objects.VnfPackageVnfd.obj_from_db_obj( self._context, db_vnfd) self.obj_reset_changes(['vnfd']) def _load_generic(self, attrname): vnf_package = self.__class__.get_by_id(self._context, id=self.id, expected_attrs=None) if attrname not in vnf_package: raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('loading %s requires recursion') % attrname) for field in self.fields: if field in vnf_package and field not in self: setattr(self, field, getattr(vnf_package, field)) def obj_load_attr(self, attrname): if not self._context: raise exceptions.OrphanedObjectError( method='obj_load_attr', objtype=self.obj_name()) if 'id' not in self: raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('attribute %s not lazy-loadable') % attrname) LOG.debug("Lazy-loading '%(attr)s' on %(name)s id %(id)s", {'attr': attrname, 'name': self.obj_name(), 'id': self.id, }) self._obj_load_attr(attrname) def _obj_load_attr(self, attrname): """Internal method for loading attributes from vnf package.""" if attrname == 'vnf_deployment_flavours': self._load_vnf_deployment_flavours() elif attrname == 'vnfd': self._load_vnfd() elif attrname in self.fields and attrname != 'id': self._load_generic(attrname) else: # NOTE(nirajsingh): Raise error if non existing field is # requested. raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('attribute %s not lazy-loadable') % attrname) self.obj_reset_changes([attrname]) @base.remotable def create(self): if self.obj_attr_is_set('id'): raise exceptions.ObjectActionError(action='create', reason=_('already created')) updates = self.obj_get_changes() if 'id' not in updates: updates['id'] = uuidutils.generate_uuid() self.id = updates['id'] for key in ['vnf_deployment_flavours']: if key in updates.keys(): updates.pop(key) user_data = updates.pop('user_data', None) db_vnf_package = _vnf_package_create(self._context, updates, user_data=user_data) self._from_db_object(self._context, self, db_vnf_package) @base.remotable_classmethod def get_by_id(cls, context, id, expected_attrs=None): db_vnf_package = _vnf_package_get_by_id( context, id, columns_to_join=expected_attrs) return cls._from_db_object(context, cls(), db_vnf_package, expected_attrs=expected_attrs) @base.remotable def destroy(self, context): if not self.obj_attr_is_set('id'): raise exceptions.ObjectActionError(action='destroy', reason='no uuid') _destroy_vnf_package(context, self.id) @base.remotable def save(self): updates = self.tacker_obj_get_changes() for key in ['vnf_deployment_flavours']: if key in updates.keys(): updates.pop(key) db_vnf_package = _vnf_package_update(self._context, self.id, updates) self._from_db_object(self._context, self, db_vnf_package)
class VnfcResourceInfo(base.TackerObject, base.TackerPersistentObject): # Version 1.0: Initial version VERSION = '1.0' fields = { 'id': fields.StringField(nullable=False), 'vdu_id': fields.StringField(nullable=False), 'compute_resource': fields.ObjectField('ResourceHandle', nullable=False), 'storage_resource_ids': fields.ListOfStringsField(nullable=True, default=[]), 'vnfc_cp_info': fields.ListOfObjectsField('VnfcCpInfo', nullable=True, default=[]), 'metadata': fields.DictOfStringsField(nullable=True, default={}) } @classmethod def obj_from_primitive(cls, primitive, context): if 'tacker_object.name' in primitive: vnfc_resource_info = super(VnfcResourceInfo, cls).obj_from_primitive( primitive, context) else: if 'compute_resource' in primitive.keys(): obj_data = ResourceHandle._from_dict( primitive.get('compute_resource')) primitive.update({'compute_resource': obj_data}) if 'vnfc_cp_info' in primitive.keys(): obj_data = [ VnfcCpInfo.obj_from_primitive(vnfc_cp_info, context) for vnfc_cp_info in primitive.get('vnfc_cp_info', []) ] primitive.update({'vnfc_cp_info': obj_data}) vnfc_resource_info = VnfcResourceInfo._from_dict(primitive) return vnfc_resource_info @classmethod def _from_dict(cls, data_dict): id = data_dict.get('id') vdu_id = data_dict.get('vdu_id') compute_resource = data_dict.get('compute_resource') storage_resource_ids = data_dict.get('storage_resource_ids', []) vnfc_cp_info = data_dict.get('vnfc_cp_info', []) metadata = data_dict.get('metadata', {}) obj = cls(id=id, vdu_id=vdu_id, compute_resource=compute_resource, storage_resource_ids=storage_resource_ids, vnfc_cp_info=vnfc_cp_info, metadata=metadata) return obj def to_dict(self): data = { 'id': self.id, 'vdu_id': self.vdu_id, 'compute_resource': self.compute_resource.to_dict(), 'storage_resource_ids': self.storage_resource_ids } if self.vnfc_cp_info: vnfc_cp_info_list = [] for vnfc_cp_info in self.vnfc_cp_info: vnfc_cp_info_list.append(vnfc_cp_info.to_dict()) data.update({'vnfc_cp_info': vnfc_cp_info_list}) return data
class InstantiatedVnfInfo(base.TackerObject, base.TackerObjectDictCompat, base.TackerPersistentObject): # Version 1.0: Initial version VERSION = '1.0' fields = { 'flavour_id': fields.StringField(nullable=False), 'vnf_instance_id': fields.UUIDField(nullable=False), 'scale_status': fields.ListOfObjectsField('ScaleInfo', nullable=True, default=[]), 'ext_cp_info': fields.ListOfObjectsField('VnfExtCpInfo', nullable=False), 'ext_virtual_link_info': fields.ListOfObjectsField('ExtVirtualLinkInfo', nullable=True, default=[]), 'ext_managed_virtual_link_info': fields.ListOfObjectsField('ExtManagedVirtualLinkInfo', nullable=True, default=[]), 'vnfc_resource_info': fields.ListOfObjectsField('VnfcResourceInfo', nullable=True, default=[]), 'vnf_virtual_link_resource_info': fields.ListOfObjectsField('VnfVirtualLinkResourceInfo', nullable=True, default=[]), 'virtual_storage_resource_info': fields.ListOfObjectsField('VirtualStorageResourceInfo', nullable=True, default=[]), 'vnfc_info': fields.ListOfObjectsField('VnfcInfo', nullable=True, default=[]), 'vnf_state': fields.VnfOperationalStateTypeField( nullable=False, default=fields.VnfOperationalStateType.STOPPED), 'instance_id': fields.StringField(nullable=True, default=None), 'instantiation_level_id': fields.StringField(nullable=True, default=None), 'additional_params': fields.DictOfStringsField(nullable=True, default={}) } ALL_ATTRIBUTES = { 'instantiatedInfo': { 'flavourId': ('id', 'string', 'VnfInstantiatedInfo'), 'vnfInstanceId': ('vnf_instance_id', 'string', 'VnfInstantiatedInfo'), 'vnfState': ('vnf_state', 'string', 'VnfInstantiatedInfo'), 'instanceId': ('instance_id', 'string', 'VnfInstantiatedInfo'), 'instantiationLevelId': ('instantiation_level_id', 'string', 'VnfInstantiatedInfo'), 'extCpInfo/*': ('ext_cp_info', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstantiatedInfo" }), 'extVirtualLinkInfo/*': ('ext_virtual_link_info', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstantiatedInfo" }), 'extManagedVirtualLinkInfo/*': ('ext_managed_virtual_link_info', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstantiatedInfo" }), 'vnfcResourceInfo/*': ('vnfc_resource_info', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstantiatedInfo" }), 'vnfVirtualLinkResourceInfo/*': ('vnf_virtual_link_resource_info', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstantiatedInfo" }), 'virtualStorageResourceInfo/*': ('virtual_storage_resource_info', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstantiatedInfo" }), 'additionalParams/*': ('additional_params', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstantiatedInfo" }), 'vnfcInfo/*': ('vnfc_info', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfInstantiatedInfo" }), } } FLATTEN_ATTRIBUTES = utils.flatten_dict(ALL_ATTRIBUTES.copy()) @staticmethod def _from_db_object(context, inst_vnf_info, db_inst_vnf_info): special_fields = [ 'scale_status', 'ext_cp_info', 'ext_virtual_link_info', 'ext_managed_virtual_link_info', 'vnfc_resource_info', 'vnf_virtual_link_resource_info', 'virtual_storage_resource_info', 'vnfc_info' ] for key in inst_vnf_info.fields: if key in special_fields: continue setattr(inst_vnf_info, key, db_inst_vnf_info.get(key)) scale_status = db_inst_vnf_info['scale_status'] scale_status_list = [ ScaleInfo.obj_from_primitive(scale, context) for scale in scale_status ] inst_vnf_info.scale_status = scale_status_list ext_cp_info = db_inst_vnf_info['ext_cp_info'] ext_cp_info_list = [ VnfExtCpInfo.obj_from_primitive(ext_cp, context) for ext_cp in ext_cp_info ] inst_vnf_info.ext_cp_info = ext_cp_info_list vnfc_resource_info = db_inst_vnf_info['vnfc_resource_info'] vnfc_resource_info_list = [ VnfcResourceInfo.obj_from_primitive(vnfc_resource, context) for vnfc_resource in vnfc_resource_info ] inst_vnf_info.vnfc_resource_info = vnfc_resource_info_list storage_res_info = db_inst_vnf_info['virtual_storage_resource_info'] storage_res_info_list = [ VirtualStorageResourceInfo.obj_from_primitive( storage_resource, context) for storage_resource in storage_res_info ] inst_vnf_info.virtual_storage_resource_info = storage_res_info_list ext_virtual_link_info = db_inst_vnf_info['ext_virtual_link_info'] ext_vl_info_list = [ ExtVirtualLinkInfo.obj_from_primitive(ext_vl_info, context) for ext_vl_info in ext_virtual_link_info ] inst_vnf_info.ext_virtual_link_info = ext_vl_info_list ext_mng_vl_info = db_inst_vnf_info['ext_managed_virtual_link_info'] ext_managed_vl_info_list = [ ExtManagedVirtualLinkInfo.obj_from_primitive( ext_managed_vl_info, context) for ext_managed_vl_info in ext_mng_vl_info ] inst_vnf_info.ext_managed_virtual_link_info = ext_managed_vl_info_list vnf_vl_resource_info = db_inst_vnf_info[ 'vnf_virtual_link_resource_info'] vnf_vl_info_list = [ VnfVirtualLinkResourceInfo.obj_from_primitive( vnf_vl_info, context) for vnf_vl_info in vnf_vl_resource_info ] inst_vnf_info.vnf_virtual_link_resource_info = vnf_vl_info_list vnfc_info = db_inst_vnf_info['vnfc_info'] vnfc_info_list = [ VnfcInfo.obj_from_primitive(vnfc, context) for vnfc in vnfc_info ] inst_vnf_info.vnfc_info = vnfc_info_list inst_vnf_info._context = context inst_vnf_info.obj_reset_changes() return inst_vnf_info @base.remotable def save(self): updates = {} changes = self.obj_what_changed() for field in self.fields: if (self.obj_attr_is_set(field) and isinstance( self.fields[field], fields.ListOfObjectsField)): field_list = getattr(self, field) updates[field] = [obj.obj_to_primitive() for obj in field_list] elif field in changes: updates[field] = self[field] vnf_info = _instantiate_vnf_info_update(self._context, self.vnf_instance_id, updates) self._from_db_object(self._context, self, vnf_info) self.obj_reset_changes() @classmethod def obj_from_primitive(cls, primitive, context): if 'tacker_object.name' in primitive: instantiate_vnf_info = super(InstantiatedVnfInfo, cls).obj_from_primitive( primitive, context) else: if 'scale_status' in primitive.keys(): obj_data = [ ScaleInfo.obj_from_primitive(scale, context) for scale in primitive.get('scale_status', []) ] primitive.update({'scale_status': obj_data}) if 'ext_cp_info' in primitive.keys(): obj_data = [ VnfExtCpInfo.obj_from_primitive(vnf_ext_cp, context) for vnf_ext_cp in primitive.get('ext_cp_info', []) ] primitive.update({'ext_cp_info': obj_data}) if 'ext_virtual_link_info' in primitive.keys(): obj_data = [ ExtVirtualLinkInfo.obj_from_primitive( ext_virtual_link, context) for ext_virtual_link in primitive.get( 'ext_virtual_link_info', []) ] primitive.update({'ext_virtual_link_info': obj_data}) if 'ext_managed_virtual_link_info' in primitive.keys(): obj_data = [ ExtManagedVirtualLinkInfo.obj_from_primitive( ext_managed_v_link, context) for ext_managed_v_link in primitive.get( 'ext_managed_virtual_link_info', []) ] primitive.update({'ext_managed_virtual_link_info': obj_data}) if 'vnfc_resource_info' in primitive.keys(): obj_data = [ VnfcResourceInfo.obj_from_primitive( vnf_resource_info, context) for vnf_resource_info in primitive.get( 'vnfc_resource_info', []) ] primitive.update({'vnfc_resource_info': obj_data}) if 'vnf_virtual_link_resource_info' in primitive.keys(): obj_data = [ VnfVirtualLinkResourceInfo.obj_from_primitive( vnf_v_link_resource, context) for vnf_v_link_resource in primitive.get( 'vnf_virtual_link_resource_info', []) ] primitive.update({'vnf_virtual_link_resource_info': obj_data}) if 'virtual_storage_resource_info' in primitive.keys(): obj_data = [ VirtualStorageResourceInfo.obj_from_primitive( virtual_storage_info, context) for virtual_storage_info in primitive.get( 'virtual_storage_resource_info', []) ] primitive.update({'virtual_storage_resource_info': obj_data}) if 'vnfc_info' in primitive.keys(): obj_data = [ VnfcInfo.obj_from_primitive(vnfc_info, context) for vnfc_info in primitive.get('vnfc_info', []) ] primitive.update({'vnfc_info': obj_data}) instantiate_vnf_info = \ InstantiatedVnfInfo._from_dict(primitive) return instantiate_vnf_info @classmethod def obj_from_db_obj(cls, context, db_obj): return cls._from_db_object(context, cls(), db_obj) @classmethod def _from_dict(cls, data_dict): flavour_id = data_dict.get('flavour_id') scale_status = data_dict.get('scale_status', []) ext_cp_info = data_dict.get('ext_cp_info', []) ext_virtual_link_info = data_dict.get('ext_virtual_link_info', []) ext_managed_virtual_link_info = data_dict.get( 'ext_managed_virtual_link_info', []) vnfc_resource_info = data_dict.get('vnfc_resource_info', []) vnf_virtual_link_resource_info = data_dict.get( 'vnf_virtual_link_resource_info', []) virtual_storage_resource_info = data_dict.get( 'virtual_storage_resource_info', []) vnf_state = data_dict.get('vnf_state') instantiation_level_id = data_dict.get('instantiation_level_id') additional_params = data_dict.get('additional_params', {}) vnfc_info = data_dict.get('vnfc_info', []) obj = cls( flavour_id=flavour_id, scale_status=scale_status, ext_cp_info=ext_cp_info, ext_virtual_link_info=ext_virtual_link_info, ext_managed_virtual_link_info=ext_managed_virtual_link_info, vnfc_resource_info=vnfc_resource_info, vnf_virtual_link_resource_info=vnf_virtual_link_resource_info, virtual_storage_resource_info=virtual_storage_resource_info, vnfc_info=vnfc_info, vnf_state=vnf_state, instantiation_level_id=instantiation_level_id, additional_params=additional_params) return obj def to_dict(self): data = {'flavour_id': self.flavour_id, 'vnf_state': self.vnf_state} if self.scale_status: scale_status_list = [] for scale_status in self.scale_status: scale_status_list.append(scale_status.to_dict()) data.update({'scale_status': scale_status_list}) ext_cp_info_list = [] for ext_cp_info in self.ext_cp_info: ext_cp_info_list.append(ext_cp_info.to_dict()) data.update({'ext_cp_info': ext_cp_info_list}) if self.ext_virtual_link_info: exp_virt_link_info_list = [] for exp_virt_link_info in self.ext_virtual_link_info: exp_virt_link_info_list.append(exp_virt_link_info.to_dict()) data.update({'ext_virtual_link_info': exp_virt_link_info_list}) if self.ext_managed_virtual_link_info: ext_managed_virt_info_list = [] for exp_managed_virt_link_info in \ self.ext_managed_virtual_link_info: info = exp_managed_virt_link_info.to_dict() ext_managed_virt_info_list.append(info) data.update( {'ext_managed_virtual_link_info': ext_managed_virt_info_list}) if self.vnfc_resource_info: vnfc_resource_info_list = [] for vnfc_resource_info in self.vnfc_resource_info: vnfc_resource_info_list.append(vnfc_resource_info.to_dict()) data.update({'vnfc_resource_info': vnfc_resource_info_list}) if self.vnf_virtual_link_resource_info: virt_link_info = [] for vnf_virtual_link_resource_info in \ self.vnf_virtual_link_resource_info: info = vnf_virtual_link_resource_info.to_dict() virt_link_info.append(info) data.update({'vnf_virtual_link_resource_info': virt_link_info}) if self.virtual_storage_resource_info: virtual_storage_resource_info_list = [] for virtual_storage_resource_info in \ self.virtual_storage_resource_info: info = virtual_storage_resource_info.to_dict() virtual_storage_resource_info_list.append(info) data.update({ 'virtual_storage_resource_info': virtual_storage_resource_info_list }) if self.vnfc_info: vnfc_info = [] for vnfc in self.vnfc_info: info = vnfc.to_dict() vnfc_info.append(info) data.update({'vnfc_info': vnfc_info}) data.update({'additional_params': self.additional_params}) return data def reinitialize(self): # Reinitialize vnf to non instantiated state. self.scale_status = [] self.ext_cp_info = [] self.ext_virtual_link_info = [] self.ext_managed_virtual_link_info = [] self.vnfc_resource_info = [] self.vnf_virtual_link_resource_info = [] self.virtual_storage_resource_info = [] self.instance_id = None self.vnf_state = fields.VnfOperationalStateType.STOPPED self.vnfc_info = [] @base.remotable def destroy(self, context): if not self.obj_attr_is_set('vnf_instance_id'): raise exceptions.ObjectActionError(action='destroy', reason='no uuid') _destroy_instantiated_vnf_info(context, self.vnf_instance_id)
class VnfPackage(base.TackerObject, base.TackerPersistentObject, base.TackerObjectDictCompat): # Key corresponds to the name of the parameter as defined # in type VnfPkgInfo of SOL003 document and value will contain tuple # of following values:- # 1. Parameter that is mapped to version object # 2. Data type of the field as per the data types supported by # attribute-based filtering # 3. DB model that's mapped to the version object. # 4. Valid values for a given data type if any. This value is set # especially for 'enum' data type. ALL_ATTRIBUTES = { 'id': ('id', "string", 'VnfPackage'), 'onboardingState': ('onboarding_state', "enum", 'VnfPackage', fields.PackageOnboardingStateTypeField().valid_values), 'operationalState': ('operational_state', 'enum', 'VnfPackage', fields.PackageOperationalStateTypeField().valid_values), 'usageState': ('usage_state', 'enum', 'VnfPackage', fields.PackageUsageStateTypeField().valid_values), 'vnfProvider': ('vnfd.vnf_provider', 'string', 'VnfPackageVnfd'), 'vnfProductName': ('vnfd.vnf_product_name', 'string', 'VnfPackageVnfd'), 'vnfdId': ('vnfd.vnfd_id', 'string', 'VnfPackageVnfd'), 'vnfSoftwareVersion': ('vnfd.vnf_software_version', 'string', 'VnfPackageVnfd'), 'vnfdVersion': ('vnfd.vnfd_version', 'string', 'VnfPackageVnfd'), 'userDefinedData/*': ('user_data', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfPackageUserData" }), "checksum": { 'algorithm': ('algorithm', 'string', 'VnfPackage'), 'hash': ('hash', 'string', 'VnfPackage'), } } ALL_ATTRIBUTES.update(vnf_software_image.VnfSoftwareImage.ALL_ATTRIBUTES) FLATTEN_ATTRIBUTES = utils.flatten_dict(ALL_ATTRIBUTES.copy()) simple_attributes = [ 'id', 'onboardingState', 'operationalState', 'usageState' ] simple_instantiated_attributes = [ 'vnfProvider', 'vnfProductName', 'vnfdId', 'vnfSoftwareVersion', 'vnfdVersion' ] COMPLEX_ATTRIBUTES = ["checksum", "userDefinedData"] COMPLEX_ATTRIBUTES.extend( vnf_software_image.VnfSoftwareImage.COMPLEX_ATTRIBUTES) # Version 1.1: Added 'size' to persist size of VnfPackage. VERSION = '1.1' fields = { 'id': fields.UUIDField(nullable=False), 'onboarding_state': fields.PackageOnboardingStateTypeField(nullable=False), 'operational_state': fields.PackageOperationalStateTypeField(nullable=False), 'usage_state': fields.PackageUsageStateTypeField(nullable=False), 'user_data': fields.DictOfStringsField(), 'tenant_id': fields.StringField(nullable=False), 'algorithm': fields.StringField(nullable=True), 'hash': fields.StringField(nullable=True), 'location_glance_store': fields.StringField(nullable=True), 'vnf_deployment_flavours': fields.ObjectField('VnfDeploymentFlavoursList', nullable=True), 'vnfd': fields.ObjectField('VnfPackageVnfd', nullable=True), 'size': fields.IntegerField(nullable=False, default=0), } def __init__(self, context=None, **kwargs): super(VnfPackage, self).__init__(context, **kwargs) self.obj_set_defaults() def obj_make_compatible(self, primitive, target_version): super(VnfPackage, self).obj_make_compatible(primitive, target_version) target_version = versionutils.convert_version_to_tuple(target_version) if target_version < (1, 1) and 'size' in primitive: del primitive['size'] @staticmethod def _from_db_object(context, vnf_package, db_vnf_package, expected_attrs=None): expected_attrs = expected_attrs or [] vnf_package._context = context for key in vnf_package.fields: if key in VNF_PACKAGE_OPTIONAL_ATTRS: continue if key == 'user_data': db_key = 'metadetails' else: db_key = key setattr(vnf_package, key, db_vnf_package[db_key]) vnf_package._context = context vnf_package._extra_attributes_from_db_object(vnf_package, db_vnf_package, expected_attrs) vnf_package.obj_reset_changes() return vnf_package @staticmethod def _extra_attributes_from_db_object(vnf_package, db_vnf_package, expected_attrs=None): """Method to help with migration of extra attributes to objects.""" if expected_attrs is None: expected_attrs = [] if 'vnf_deployment_flavours' in expected_attrs: vnf_package._load_vnf_deployment_flavours( db_vnf_package.get('vnf_deployment_flavours')) if 'vnfd' in expected_attrs: vnf_package._load_vnfd(db_vnf_package.get('vnfd')) def _load_vnf_deployment_flavours(self, db_flavours=_NO_DATA_SENTINEL): if db_flavours is _NO_DATA_SENTINEL: vnf_package = self.get_by_id( self._context, self.id, expected_attrs=['vnf_deployment_flavours']) if 'vnf_deployment_flavours' in vnf_package: self.vnf_deployment_flavours = \ vnf_package.vnf_deployment_flavours self.vnf_deployment_flavours.obj_reset_changes(recursive=True) self.obj_reset_changes(['vnf_deployment_flavours']) else: self.vnf_deployment_flavours = \ objects.VnfDeploymentFlavoursList(objects=[]) elif db_flavours: self.vnf_deployment_flavours = base.obj_make_list( self._context, objects.VnfDeploymentFlavoursList(self._context), objects.VnfDeploymentFlavour, db_flavours) self.obj_reset_changes(['vnf_deployment_flavours']) def _load_vnfd(self, db_vnfd=_NO_DATA_SENTINEL): if db_vnfd is None: self.vnfd = None elif db_vnfd is _NO_DATA_SENTINEL: vnf_package = self.get_by_id(self._context, self.id, expected_attrs=['vnfd']) if 'vnfd' in vnf_package and vnf_package.vnfd is not None: self.vnfd = vnf_package.vnfd self.vnfd.obj_reset_changes(recursive=True) self.obj_reset_changes(['vnfd']) else: self.vnfd = None elif db_vnfd: self.vnfd = objects.VnfPackageVnfd.obj_from_db_obj( self._context, db_vnfd) self.obj_reset_changes(['vnfd']) def _load_generic(self, attrname): vnf_package = self.__class__.get_by_id(self._context, id=self.id, expected_attrs=None) if attrname not in vnf_package: raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('loading %s requires recursion') % attrname) for field in self.fields: if field in vnf_package and field not in self: setattr(self, field, getattr(vnf_package, field)) def obj_load_attr(self, attrname): if not self._context: raise exceptions.OrphanedObjectError(method='obj_load_attr', objtype=self.obj_name()) if 'id' not in self: raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('attribute %s not lazy-loadable') % attrname) LOG.debug("Lazy-loading '%(attr)s' on %(name)s id %(id)s", { 'attr': attrname, 'name': self.obj_name(), 'id': self.id, }) self._obj_load_attr(attrname) def _obj_load_attr(self, attrname): """Internal method for loading attributes from vnf package.""" if attrname == 'vnf_deployment_flavours': self._load_vnf_deployment_flavours() elif attrname == 'vnfd': self._load_vnfd() elif attrname in self.fields and attrname != 'id': self._load_generic(attrname) else: # NOTE(nirajsingh): Raise error if non existing field is # requested. raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('attribute %s not lazy-loadable') % attrname) self.obj_reset_changes([attrname]) @base.remotable def create(self): if self.obj_attr_is_set('id'): raise exceptions.ObjectActionError(action='create', reason=_('already created')) updates = self.obj_get_changes() if 'id' not in updates: updates['id'] = uuidutils.generate_uuid() self.id = updates['id'] for key in ['vnf_deployment_flavours']: if key in updates: updates.pop(key) user_data = updates.pop('user_data', None) db_vnf_package = _vnf_package_create(self._context, updates, user_data=user_data) self._from_db_object(self._context, self, db_vnf_package) @base.remotable_classmethod def get_by_id(cls, context, id, expected_attrs=None): db_vnf_package = _vnf_package_get_by_id(context, id, columns_to_join=expected_attrs) return cls._from_db_object(context, cls(), db_vnf_package, expected_attrs=expected_attrs) @base.remotable def destroy(self, context): if not self.obj_attr_is_set('id'): raise exceptions.ObjectActionError(action='destroy', reason='no uuid') _destroy_vnf_package(context, self.id) @base.remotable def save(self): updates = self.tacker_obj_get_changes() for key in ['vnf_deployment_flavours']: if key in updates: updates.pop(key) db_vnf_package = _vnf_package_update(self._context, self.id, updates) self._from_db_object(self._context, self, db_vnf_package) @base.remotable def is_package_in_use(self, context): if self.onboarding_state == \ fields.PackageOnboardingStateType.ONBOARDED: # check if vnf package is used by any vnf instances. query = context.session.query( func.count(models.VnfInstance.id)).\ filter_by( instantiation_state=fields.VnfInstanceState.INSTANTIATED).\ filter_by(tenant_id=self.tenant_id).\ filter_by(vnfd_id=self.vnfd.vnfd_id).\ filter_by(deleted=False) result = query.scalar() return True if result > 0 else False else: return False def _get_vnfd(self, include_fields=None): response = dict() to_fields = set( self.simple_instantiated_attributes).intersection(include_fields) for field in to_fields: response[field] = utils.deepgetattr( self, self.FLATTEN_ATTRIBUTES[field][0]) return response def _get_checksum(self, include_fields=None): response = dict() to_fields = set([ key for key in self.FLATTEN_ATTRIBUTES.keys() if key.startswith('checksum') ]) to_fields = to_fields.intersection(include_fields) for field in to_fields: display_field = field.split("/")[-1] response[display_field] = getattr( self, self.FLATTEN_ATTRIBUTES[field][0]) return {'checksum': response} if response else None def _get_user_defined_data(self, include_fields=None): # Need special handling for field containing key-value pair. # If user requests userDefined/key1 and if userDefineData contains # key1=value1, key2-value2, it should return only keys that are # requested in include_fields. If user requests only userDefinedData, # then in that case,it should return all key/value pairs. In case, # if any of the requested key is not present, then it should # siliently ignore it. key = 'userDefinedData' if key in include_fields or 'userDefinedData/*' in include_fields: return {key: self.user_data} else: # Check if user has requested specified keys from # userDefinedData. data_resp = dict() key_list = [] special_key = 'userDefinedData/' for field in include_fields: if field.startswith(special_key): key_list.append(field[len(special_key):]) for key_req in key_list: if key_req in self.user_data: data_resp[key_req] = self.user_data[key_req] if data_resp: return {key: data_resp} def _basic_vnf_package_info(self, include_fields=None): response = dict() to_fields = set(self.simple_attributes).intersection(include_fields) for field in to_fields: response[field] = getattr(self, self.FLATTEN_ATTRIBUTES[field][0]) return response def to_dict(self, include_fields=None): if not include_fields: include_fields = set(self.FLATTEN_ATTRIBUTES.keys()) vnf_package_response = self._basic_vnf_package_info( include_fields=include_fields) user_defined_data = self._get_user_defined_data( include_fields=include_fields) if user_defined_data: vnf_package_response.update(user_defined_data) if (self.onboarding_state == fields.PackageOnboardingStateType.ONBOARDED): software_images = self.vnf_deployment_flavours.to_dict( include_fields=include_fields) if software_images: vnf_package_response.update( {'softwareImages': software_images}) vnf_package_response.update( self._get_vnfd(include_fields=include_fields)) checksum = self._get_checksum(include_fields=include_fields) if checksum: vnf_package_response.update(checksum) return vnf_package_response
class VnfSoftwareImage(base.TackerObject, base.TackerPersistentObject): # Version 1.0: Initial version VERSION = '1.0' fields = { 'id': fields.UUIDField(nullable=False), 'software_image_id': fields.StringField(nullable=False), 'flavour_uuid': fields.UUIDField(nullable=False), 'name': fields.StringField(nullable=True), 'provider': fields.StringField(nullable=True), 'version': fields.StringField(nullable=True), 'algorithm': fields.StringField(nullable=True), 'hash': fields.StringField(nullable=True), 'container_format': fields.StringField(nullable=True), 'disk_format': fields.StringField(nullable=True), 'min_disk': fields.IntegerField(), 'min_ram': fields.IntegerField(default=0), 'size': fields.IntegerField(), 'image_path': fields.StringField(), 'metadata': fields.DictOfStringsField(nullable=True) } @staticmethod def _from_db_object(context, vnf_sw_image, db_sw_image, expected_attrs=None): vnf_sw_image._context = context for key in vnf_sw_image.fields: if key in VNF_SOFTWARE_IMAGE_OPTIONAL_ATTRS: continue else: db_key = key setattr(vnf_sw_image, key, db_sw_image[db_key]) vnf_sw_image._extra_attributes_from_db_object(vnf_sw_image, db_sw_image, expected_attrs) vnf_sw_image.obj_reset_changes() return vnf_sw_image @staticmethod def _extra_attributes_from_db_object(vnf_sw_image, db_sw_image, expected_attrs=None): """Method to help with migration of extra attributes to objects. """ if expected_attrs is None: expected_attrs = [] if 'metadata' in expected_attrs: setattr(vnf_sw_image, 'metadata', db_sw_image['metadetails']) def obj_load_attr(self, attrname): if not self._context: raise exceptions.OrphanedObjectError(method='obj_load_attr', objtype=self.obj_name()) if 'id' not in self: raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('attribute %s not lazy-loadable') % attrname) LOG.debug("Lazy-loading '%(attr)s' on %(name)s id %(id)s", { 'attr': attrname, 'name': self.obj_name(), 'id': self.id, }) self._obj_load_attr(attrname) def _obj_load_attr(self, attrname): """Internal method for loading attributes from vnf flavour.""" if attrname in self.fields and attrname != 'id': self._load_generic(attrname) else: # NOTE(nirajsingh): Raise error if non existing field is # requested. raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('attribute %s not lazy-loadable') % attrname) self.obj_reset_changes([attrname]) def _load_generic(self, attrname): software_image = self.__class__.get_by_id(self._context, id=self.id, expected_attrs=attrname) if attrname not in software_image: raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('loading %s requires recursion') % attrname) for field in self.fields: if field in software_image and field not in self: setattr(self, field, getattr(software_image, field)) @base.remotable def create(self): if self.obj_attr_is_set('id'): raise exceptions.ObjectActionError(action='create', reason=_('already created')) updates = self.obj_get_changes() if 'id' not in updates: updates['id'] = uuidutils.generate_uuid() self.id = updates['id'] metadata = updates.pop('metadata', None) db_sw_image = _vnf_sw_image_create(self._context, updates, metadata=metadata) self._from_db_object(self._context, self, db_sw_image) @base.remotable_classmethod def get_by_id(cls, context, id, expected_attrs=None): db_sw_image = _vnf_sw_image_get_by_id(context, id) return cls._from_db_object(context, cls(), db_sw_image, expected_attrs=expected_attrs)
class VnfSoftwareImage(base.TackerObject, base.TackerPersistentObject): ALL_ATTRIBUTES = { "softwareImages": { 'id': ('software_image_id', 'string', 'VnfSoftwareImage'), 'imagePath': ('image_path', 'string', 'VnfSoftwareImage'), 'diskFormat': ('disk_format', 'string', 'VnfSoftwareImage'), 'userMetadata/*': ('metadata', 'key_value_pair', { "key_column": "key", "value_column": "value", "model": "VnfSoftwareImageMetadata" }), 'size': ('size', 'number', 'VnfSoftwareImage'), 'createdAt': ('created_at', 'datetime', 'VnfSoftwareImage'), 'name': ('name', 'string', 'VnfSoftwareImage'), 'minDisk': ('min_disk', 'number', 'VnfSoftwareImage'), 'version': ('version', 'string', 'VnfSoftwareImage'), 'provider': ('provider', 'string', 'VnfSoftwareImage'), 'minRam': ('min_ram', 'number', 'VnfSoftwareImage'), 'containerFormat': ('container_format', 'string', 'VnfSoftwareImage'), "checksum": { 'hash': ('hash', 'string', 'VnfSoftwareImage'), 'algorithm': ('algorithm', 'string', 'VnfSoftwareImage') } } } FLATTEN_ATTRIBUTES = utils.flatten_dict(ALL_ATTRIBUTES.copy()) SIMPLE_ATTRIBUTES = [ 'id', 'imagePath', 'diskFormat', 'size', 'createdAt', 'name', 'minDisk', 'version', 'provider', 'minRam', 'containerFormat' ] COMPLEX_ATTRIBUTES = [ 'softwareImages', 'softwareImages/userMetadata', 'softwareImages/checksum' ] # Version 1.0: Initial version VERSION = '1.0' fields = { 'id': fields.UUIDField(nullable=False), 'software_image_id': fields.StringField(nullable=False), 'flavour_uuid': fields.UUIDField(nullable=False), 'name': fields.StringField(nullable=True), 'provider': fields.StringField(nullable=True), 'version': fields.StringField(nullable=True), 'algorithm': fields.StringField(nullable=True), 'hash': fields.StringField(nullable=True), 'container_format': fields.StringField(nullable=True), 'disk_format': fields.StringField(nullable=True), 'min_disk': fields.IntegerField(), 'min_ram': fields.IntegerField(default=0), 'size': fields.IntegerField(), 'image_path': fields.StringField(), 'metadata': fields.DictOfStringsField(nullable=True) } @staticmethod def _from_db_object(context, vnf_sw_image, db_sw_image, expected_attrs=None): vnf_sw_image._context = context for key in vnf_sw_image.fields: if key in VNF_SOFTWARE_IMAGE_OPTIONAL_ATTRS: continue else: db_key = key setattr(vnf_sw_image, key, db_sw_image[db_key]) vnf_sw_image._extra_attributes_from_db_object(vnf_sw_image, db_sw_image, expected_attrs) vnf_sw_image.obj_reset_changes() return vnf_sw_image @staticmethod def _extra_attributes_from_db_object(vnf_sw_image, db_sw_image, expected_attrs=None): """Method to help with migration of extra attributes to objects. """ if expected_attrs is None: expected_attrs = [] if 'metadata' in expected_attrs: setattr(vnf_sw_image, 'metadata', db_sw_image['metadetails']) def obj_load_attr(self, attrname): if not self._context: raise exceptions.OrphanedObjectError(method='obj_load_attr', objtype=self.obj_name()) if 'id' not in self: raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('attribute %s not lazy-loadable') % attrname) LOG.debug("Lazy-loading '%(attr)s' on %(name)s id %(id)s", { 'attr': attrname, 'name': self.obj_name(), 'id': self.id, }) self._obj_load_attr(attrname) def _obj_load_attr(self, attrname): """Internal method for loading attributes from vnf flavour.""" if attrname in self.fields and attrname != 'id': self._load_generic(attrname) else: # NOTE(nirajsingh): Raise error if non existing field is # requested. raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('attribute %s not lazy-loadable') % attrname) self.obj_reset_changes([attrname]) def _load_generic(self, attrname): software_image = self.__class__.get_by_id(self._context, id=self.id, expected_attrs=attrname) if attrname not in software_image: raise exceptions.ObjectActionError( action='obj_load_attr', reason=_('loading %s requires recursion') % attrname) for field in self.fields: if field in software_image and field not in self: setattr(self, field, getattr(software_image, field)) @base.remotable def create(self): if self.obj_attr_is_set('id'): raise exceptions.ObjectActionError(action='create', reason=_('already created')) updates = self.obj_get_changes() if 'id' not in updates: updates['id'] = uuidutils.generate_uuid() self.id = updates['id'] metadata = updates.pop('metadata', None) db_sw_image = _vnf_sw_image_create(self._context, updates, metadata=metadata) self._from_db_object(self._context, self, db_sw_image) @base.remotable_classmethod def get_by_id(cls, context, id, expected_attrs=None): db_sw_image = _vnf_sw_image_get_by_id(context, id) return cls._from_db_object(context, cls(), db_sw_image, expected_attrs=expected_attrs) def _get_user_metadata(self, include_fields=None): # Need special handling for field containing key-value pair. # If user requests softwareImages/userMetadata/key1 and if # softwareImages/userMetadata contains key1=value1, key2=value2, # it should return only keys that are requested in include_fields. # If user requests only softwareImages/userMetadata, then in that # case, it should return all key/value pairs. If any of the requested # key is not present, then it will siliently ignore it. key = 'softwareImages/userMetadata' if key in include_fields or '%s/*' % key in \ include_fields: return self.metadata else: # Check if user has requested specified keys from # softwareImages/userMetadata. key_list = [] special_key = '%s/' % key for field in include_fields: if field.startswith(special_key): key_list.append(field[len(special_key):]) data_resp = dict() for key_req in key_list: if key_req in self.metadata: data_resp[key_req] = self.metadata[key_req] if len(key_list) > 0: return data_resp def to_dict(self, include_fields=None): response = dict() fields = [ 'softwareImages/%s' % attribute for attribute in self.SIMPLE_ATTRIBUTES ] to_fields = set(fields).intersection(include_fields) for field in to_fields: display_field = field.split("/")[-1] response[display_field] = getattr( self, self.FLATTEN_ATTRIBUTES[field][0]) # add checksum to_fields = set([ key for key in self.FLATTEN_ATTRIBUTES.keys() if key.startswith('softwareImages/checksum') ]) checksum = dict() to_fields = to_fields.intersection(include_fields) for field in to_fields: display_field = field.split("/")[-1] checksum[display_field] = getattr( self, self.FLATTEN_ATTRIBUTES[field][0]) if checksum: response.update({"checksum": checksum}) user_metadata = self._get_user_metadata(include_fields) if user_metadata is not None: response.update({"userMetadata": user_metadata}) return response
class LccnSubscriptionRequest(base.TackerObject, base.TackerPersistentObject): # Version 1.0: Initial version VERSION = '1.0' fields = { 'id': fields.UUIDField(nullable=False), 'callback_uri': fields.StringField(nullable=False), 'subscription_authentication': fields.DictOfStringsField(nullable=True), 'filter': fields.StringField(nullable=True) } @base.remotable def create(self, filter): updates = self.obj_clone() db_vnf_lcm_subscriptions = _vnf_lcm_subscriptions_create( self._context, updates, filter) LOG.debug('test_log: db_vnf_lcm_subscriptions %s' % db_vnf_lcm_subscriptions) return db_vnf_lcm_subscriptions @base.remotable_classmethod def vnf_lcm_subscriptions_show(cls, context, subscriptionId): try: vnf_lcm_subscriptions = _vnf_lcm_subscriptions_show( context, subscriptionId) except Exception as e: raise e return vnf_lcm_subscriptions @base.remotable_classmethod def vnf_lcm_subscriptions_list(cls, context): # get vnf_lcm_subscriptions data try: vnf_lcm_subscriptions = _vnf_lcm_subscriptions_all(context) except Exception as e: raise e return vnf_lcm_subscriptions @base.remotable_classmethod def vnf_lcm_subscriptions_get(cls, context, notification_type, operation_type=None): return _vnf_lcm_subscriptions_get(context, notification_type, operation_type) @base.remotable_classmethod def destroy(cls, context, subscriptionId): try: get_subscriptionid = _get_by_subscriptionid( context, subscriptionId) except Exception as e: raise e if not get_subscriptionid: return 404 try: _destroy_vnf_lcm_subscription(context, subscriptionId) except Exception as e: raise e return 204