def test_extract_fips_with_port(self, mock_fip, mock_net, mock_port): # NOTE: without router; with secgroup, router interface # Here, we will make net_0 and port_0 in cache and without any # dependencies, so only net_0, fip, fipAss, port_0 will be extracted # at last. # ---------------------------------------------------- # | net_1 | # | / | | # | subnet_0(ext-sb) / subnet_1 | # | | \ | | # | | \ | | # | net_0(ext-net)<---fip<----fipAss--->port_0 | # ---------------------------------------------------- fake_fip = copy.deepcopy(fake_fip_dict) fake_fip['floating_network_id'] = ext_net_id fake_fip['port_id'] = fake_port_dict['id'] mock_fip.return_value = fake_fip fake_port = copy.deepcopy(fake_port_dict) mock_port.return_value = fake_port fake_port_id = fake_port['id'] fake_port_name = fake_port['name'] fake_port_res = resource.Resource('port_0', 'OS::Neutron::Port', fake_port_id) fake_port_dep = resource.ResourceDependency(fake_port_id, fake_port_name, 'port_0', 'OS::Neutron::Port') fake_net = copy.deepcopy(fake_net_dict) fake_net['id'] = fake_fip['floating_network_id'] fake_net_id = fake_net['id'] mock_net.return_value = fake_net fake_net_res = resource.Resource('net_0', 'OS::Neutron::Net', fake_net_id) fake_net_dep = resource.ResourceDependency(fake_net_id, fake_net_dict['name'], 'net_0', 'OS::Neutron::Net') self.net_resource = networks.NetworkResource(self.context, collected_resources={ fake_port_id: fake_port_res, fake_net_id: fake_net_res }, collected_dependencies={ fake_port_id: fake_port_dep, fake_net_id: fake_net_dep }) result = self.net_resource.extract_floatingips([fake_fip['id']]) self.assertEqual(1, len(result)) self.assertEqual(4, len(self.net_resource.get_collected_resources())) deps = self.net_resource.get_collected_dependencies() net_dep = deps.pop(fake_net_id) fip_dep = deps.pop(fake_fip['id']) port_dep = deps.pop(fake_port_id) fip_ass_dep = deps.values()[0] self.assertIn(net_dep.name_in_template, fip_dep.dependencies) self.assertIn(fip_dep.name_in_template, fip_ass_dep.dependencies) self.assertIn(port_dep.name_in_template, fip_ass_dep.dependencies)
def test_extract_ports_with_ids(self, mock_port, mock_subnet): # NOTE: default, in the case, subnets will be extracted. fake_port = copy.deepcopy(fake_port_dict) mock_port.return_value = fake_port fake_subnet = copy.deepcopy(fake_subnet_dict) fake_subnet_id = fake_subnet['id'] fake_subnet_name = fake_subnet['name'] mock_subnet.return_value = fake_subnet fake_subnet_res = resource.Resource( fake_subnet_name, 'OS::Neutron::Subnet', fake_subnet_id, properties={'network_id': { 'get_resource': 'network_0' }}) fake_subnet_dep = resource.ResourceDependency(fake_subnet_id, fake_subnet_name, 'subnet_0', 'OS::Neutron::Subnet') self.net_resource = networks.NetworkResource( self.context, collected_resources={fake_subnet_id: fake_subnet_res}, collected_dependencies={fake_subnet_id: fake_subnet_dep}) result = self.net_resource.extract_ports([fake_port['id']]) self.assertTrue(1 == len(result)) self.assertTrue(2 == len(self.net_resource.get_collected_resources()))
def test_extract_subnets_from_cache(self, mock_subnet_list): fake_subnet = copy.deepcopy(fake_subnet_dict) fake_subnet_id = fake_subnet['id'] fake_subnet_name = fake_subnet['name'] mock_subnet_list.return_value = [fake_subnet] fake_subnet_res = resource.Resource(fake_subnet_name, 'OS::Neutron::Subnet', fake_subnet_id) fake_subnet_dep = resource.ResourceDependency(fake_subnet_id, fake_subnet_name, 'subnet_0', 'OS::Neutron::Subnet') self.net_resource = networks.NetworkResource( self.context, collected_resources={fake_subnet_id: fake_subnet_res}, collected_dependencies={fake_subnet_id: fake_subnet_dep}) result = self.net_resource.extract_subnets([]) self.assertTrue(1 == len(result)) self.assertEqual(fake_subnet_id, result[0].id) collected_res = self.net_resource.get_collected_resources() collected_deps = self.net_resource.get_collected_dependencies() self.assertTrue(1 == len(collected_res)) self.assertTrue(1 == len(collected_deps)) subnet_dep = collected_deps[fake_subnet_id] self.assertFalse(len(subnet_dep.dependencies))
def extract_resource(self, template, name, resource_type, resource_id, stack_name=None, parent_resources=None): if not template or not name or not resource_id: return LOG.debug('Extract resource of heat resource %s.', name) # If this heat resource has been extracted, ignore it. heat_resources = self._collected_resources.get(resource_id) if heat_resources: return heat_resources resource_name = name if stack_name and resource_id in parent_resources: resource_name = stack_name + '.' + resource_name heat_resources = resource.Resource(resource_name, resource_type, resource_id, properties={}) template_resources = template.get('resources') t_resource = template_resources.get(name) properties = t_resource.get('properties') heat_resources.properties = properties resource_dependencies = resource.ResourceDependency( resource_id, name, resource_name, resource_type) self._collected_resources[resource_id] = heat_resources self._collected_dependencies[resource_id] = resource_dependencies return heat_resources
def extract_keypairs(self, keypair_ids, parent_name=None, parent_resources=None): keypair_objs = [] keypairResources = [] if not keypair_ids: LOG.debug('Extract resources of all keypairs.') keypair_objs = self.nova_api.keypair_list(self.context) else: LOG.debug('Extract resources of keypairs: %s', keypair_ids) # remove duplicate keypairs keypair_ids = {}.fromkeys(keypair_ids).keys() for keypair_id in keypair_ids: try: keypair = self.nova_api.get_keypair(self.context, keypair_id) keypair_objs.append(keypair) except Exception as e: msg = "Keypair resource <%s> could not be found. %s" \ % (keypair_id, unicode(e)) LOG.error(msg) raise exception.ResourceNotFound(message=msg) for keypair in keypair_objs: resource_id = keypair.get('id', '') keypair_res = self._collected_resources.get(resource_id) if keypair_res: keypairResources.append(keypair_res) continue name = keypair.get('name', '') properties = {'name': name, 'public_key': keypair.get('public_key', '') } resource_type = "OS::Nova::KeyPair" resource_name = "keypair_%d" \ % self._get_resource_num(resource_type) if parent_name and resource_id in parent_resources: resource_name = parent_name + '.' + resource_name keypair_res = resource.Resource(resource_name, resource_type, resource_id, properties=properties) keypair_dep = resource.ResourceDependency(resource_id, resource_name, name, resource_type) self._collected_resources[resource_id] = keypair_res self._collected_dependencies[resource_id] = keypair_dep keypairResources.append(keypair_res) if keypair_ids and not keypairResources: msg = "KeyPair resource extracted failed, \ can't find the keypair with id of %s." % keypair_ids LOG.error(msg) raise exception.ResourceNotFound(message=msg) return keypairResources
def extract_loadbalanceHealthmonitor(self, healthmonitor_id): # check health monitor resource exist or not healthmonitor_col = self._collected_resources.get(healthmonitor_id) if healthmonitor_col: return healthmonitor_col try: healthmonitor = \ self.neutron_api.show_health_monitor(self.context, healthmonitor_id) except Exception as e: _msg = 'Create LB health monitor resource error: %s' % e LOG.error(_msg) raise exception.ResourceExtractFailed(reason=_msg) properties = {} healthmonitor_info = healthmonitor.get('health_monitor') properties['delay'] = healthmonitor_info.get('delay') properties['type'] = healthmonitor_info.get('type') properties['max_retries'] = healthmonitor_info.get('max_retries') properties['timeout'] = healthmonitor_info.get('timeout') healthmonitor_code = healthmonitor_info.get('expected_codes') healthmonitor_http = healthmonitor_info.get('http_method') healthmonitor_admin = healthmonitor_info.get('admin_state_up') healthmonitor_url = healthmonitor_info.get('url_path') if healthmonitor_code: properties['expected_codes'] = healthmonitor_code if healthmonitor_http: properties['http_method'] = healthmonitor_http if healthmonitor_admin: properties['admin_state_up'] = healthmonitor_admin if healthmonitor_url: properties['url_path'] = healthmonitor_url healthmonitor_type = "OS::Neutron::HealthMonitor" healthmonitor_name = 'loadbalanceHealthmonitor_%d' \ % self._get_resource_num(healthmonitor_type) healthmonitor_res = resource.Resource(healthmonitor_name, healthmonitor_type, healthmonitor_id, properties=properties) healthmonitor_dep = resource.ResourceDependency( healthmonitor_id, healthmonitor_name, '', healthmonitor_type) self._collected_resources[healthmonitor_id] = healthmonitor_res self._collected_dependencies[healthmonitor_id] = healthmonitor_dep return healthmonitor_res
def _extract_stack_resources(self, context, stack): stack_id = stack['id'] properties = {} timeout_mins = stack['timeout_mins'] if timeout_mins: properties['timeout'] = timeout_mins template = self.heat_api.get_template(context, stack_id) parameters = template.get('parameters') if parameters and parameters.get('OS::stack_id'): parameters.pop('OS::stack_id') if parameters and parameters.get('OS::project_id'): parameters.pop('OS::project_id') properties['parameters'] = parameters properties['disable_rollback'] = stack['disable_rollback'] properties['stack_name'] = stack['stack_name'] resource_type = "OS::Heat::Stack" resource_name = 'stack_%d' % self._get_resource_num(resource_type) stack_res = res.Resource(resource_name, resource_type, stack_id, properties=properties) stack_dep = res.ResourceDependency(stack_id, resource_name, stack['stack_name'], resource_type) sub_reses, dependencies_reses = self._extract_son_resources( context, stack_id, resource_name) for resource in sub_reses: stack_dep.add_dependency(resource.id, resource.name, resource.properties.get('name', ''), resource.type) template_skeleton = ''' heat_template_version: '2013-05-23' description: Generated template parameters: resources: ''' template = yaml.load(template_skeleton) template['resources'] = {} template['parameters'] = {} for r_resource in dependencies_reses: if r_resource in sub_reses: if r_resource.type not in handle_resource_types: r_name = r_resource.name.split('.', 1)[-1] r_resource.name = r_name template['resources'].update(r_resource.template_resource) template['parameters'].update(r_resource.template_parameter) for key, value in parameters.items(): if key not in template['parameters'].keys(): template['parameters'][key] = value stack_res.add_property('template', json.dumps(template)) self._collected_resources[stack_id] = stack_res self._collected_dependencies[stack_id] = stack_dep return sub_reses
def mock_build_res_topo(cls, context, resources): ori_res = {} ori_deps = {} for res in resources: res_type = res.get('type') res_id = res.get('id') name = '%s-%s' % (res_type, res_id) name_in_tmpl = uuidutils.generate_uuid() ori_res[name_in_tmpl] = resource.Resource(name_in_tmpl, res_type, res_id) ori_deps[name_in_tmpl] = resource.ResourceDependency( res_id, name_in_tmpl, name, res_type) return ori_res, ori_deps
def rebuild_dependencies(self, is_original=False): def get_dependencies(properties, deps): if isinstance(properties, dict) and len(properties) == 1: key = properties.keys()[0] value = properties[key] if key == "get_resource": if isinstance(value, six.string_types) \ and value in resources.keys(): deps.append(value) elif key == "get_attr": if isinstance(value, list) and len(value) >= 1 \ and isinstance(value[0], six.string_types) \ and value[0] in resources.keys(): deps.append(value[0]) else: get_dependencies(properties[key], deps) elif isinstance(properties, dict): for p in properties.values(): get_dependencies(p, deps) elif isinstance(properties, list): for p in properties: get_dependencies(p, deps) resources = \ self.original_resources if is_original else self.updated_resources dependencies = self.original_dependencies if \ is_original else self.updated_dependencies if not resources: return dependencies = {} for res in resources.values(): deps = [] get_dependencies(res.properties, deps) # remove duplicate dependencies deps = {}.fromkeys(deps).keys() new_dependencies = resource.ResourceDependency( res.id, res.name, res.properties.get('name', ''), res.type, dependencies=deps) dependencies[res.name] = new_dependencies if is_original: self.original_dependencies = dependencies else: self.updated_dependencies = dependencies
def mock_extract_secgroups(cls, secgroups_ids): secgroup_res = [] for secgroup_id in secgroups_ids: fake_secgroup = copy.deepcopy(fake_object.fake_secgroup_dict) fake_secgroup['id'] = secgroup_id name_in_tmpl = uuidutils.generate_uuid() sg_res = resource.Resource(name_in_tmpl, 'OS::Neutron::SecurityGroup', secgroup_id) sg_dep = resource.ResourceDependency(secgroup_id, fake_secgroup['name'], name_in_tmpl, 'OS::Neutron::SecurityGroup') cls._collected_resources[secgroup_id] = sg_res cls._collected_dependencies[secgroup_id] = sg_dep secgroup_res.append(sg_res) return secgroup_res
def extract_loadbalanceListener(self, listener_id, vip_id, vip_name): listener_col = self._collected_resources.get(listener_id) if listener_col: return listener_col # 1 query listener info try: listener = self.neutron_api.show_listener(self.context, listener_id, vip_id) except Exception as e: _msg = 'Create LB listener resource error: %s' % e LOG.error(_msg) raise exception.ResourceExtractFailed(reason=_msg) # 2 build listener resource and dependence listener_info = listener.get('listener') properties = {} dependencies = [] properties['protocol'] = listener_info.get('protocol') properties['protocol_port'] = listener_info.get('protocol_port') properties['vip_id'] = {'get_resource': vip_name} dependencies.append(vip_name) listener_type = "OS::Neutron::Listener" listener_name = 'loadbalanceListener_%d' % \ self._get_resource_num(listener_type) listener_res = resource.Resource(listener_name, listener_type, listener_id, properties=properties) # remove duplicate dependencies dependencies = {}.fromkeys(dependencies).keys() listener_dep = resource.ResourceDependency(listener_id, listener_name, '', listener_type, dependencies=dependencies) self._collected_resources[listener_id] = listener_res self._collected_dependencies[listener_id] = listener_dep return listener_res
def _generate_interface_resource(self, interface, subnet_res, router_res, parent_name=None, parent_resources=None): interface_id = interface.get('id', '') # check this interface resource is exist in system or not interface_res = self._collected_resources.get(interface_id) if interface_res: return properties = { 'router_id': { 'get_resource': router_res.name }, 'subnet_id': { 'get_resource': subnet_res.name } } resource_type = "OS::Neutron::RouterInterface" resource_name = '%s_interface_%s' % \ (router_res.name, uuidutils.generate_uuid()) if parent_name and interface_id in parent_resources: resource_name = parent_name + '.' + resource_name interface_res = resource.Resource(resource_name, resource_type, interface_id, properties=properties) interface_dep = resource.ResourceDependency(interface_id, resource_name, interface.get('name', ''), resource_type) dep_router_name = router_res.properties.get('name', '') interface_dep.add_dependency(router_res.id, router_res.name, dep_router_name, router_res.type) dep_sub_name = subnet_res.properties.get('name', '') interface_dep.add_dependency(subnet_res.id, subnet_res.name, dep_sub_name, subnet_res.type) self._collected_resources[interface_id] = interface_res self._collected_dependencies[interface_id] = interface_dep
def test_extract_ports_from_cache(self, mock_port_list): fake_port = copy.deepcopy(fake_port_dict) mock_port_list.return_value = [fake_port] fake_port_id = fake_port['id'] fake_port_name = fake_port['name'] fake_port_des = resource.Resource(fake_port_name, 'OS::Neutron::Port', fake_port_id) fake_port_dep = resource.ResourceDependency(fake_port_id, fake_port_name, 'port_0', 'OS::Neutron::Port') self.net_resource = networks.NetworkResource( self.context, collected_resources={fake_port_id: fake_port_des}, collected_dependencies={fake_port_id: fake_port_dep}) result = self.net_resource.extract_ports([]) self.assertTrue(1 == len(result)) self.assertTrue(1 == len(self.net_resource.get_collected_resources()))
def mock_extract_volumes(self, volume_ids=None): for volume_id in volume_ids: volume_resource = self._collected_resources.get(volume_id) if volume_resource: continue resource_type = "OS::Cinder::Volume" resource_name = "server_%d" % self._get_resource_num(resource_type) volume_resource = resource.Resource(resource_name, resource_type, volume_id, properties={}) name = 'volume_%s' % volume_id instance_dependency = resource.ResourceDependency( volume_id, name, resource_name, resource_type) self._collected_resources[volume_id] = volume_resource self._collected_dependencies[volume_id] = instance_dependency
def mock_extract_instances(self, instance_ids=None): for instance_id in instance_ids: instance_resources = self._collected_resources.get(instance_id) if instance_resources: continue resource_type = "OS::Nova::Server" resource_name = "server_%d" % self._get_resource_num(resource_type) instance_resources = resource.Resource(resource_name, resource_type, instance_id, properties={}) name = 'server_%s' % instance_id instance_dependencies = resource.ResourceDependency( instance_id, name, resource_name, resource_type) self._collected_resources[instance_id] = instance_resources self._collected_dependencies[instance_id] = instance_dependencies
def test_extract_fips_from_cache(self, mock_fip_list): fake_fip = copy.deepcopy(fake_fip_dict) mock_fip_list.return_value = [fake_fip] fake_fip_id = fake_fip['id'] fake_fip_name = '' fake_fip_res = resource.Resource(fake_fip_name, 'OS::Neutron::FloatingIP', fake_fip_id) fake_fip_dep = resource.ResourceDependency(fake_fip_id, 'floatingip_0', fake_fip_name, 'OS::Neutron::FloatingIP') self.fip_resource = float_ips.FloatIps( self.context, collected_resources={fake_fip_id: fake_fip_res}, collected_dependencies={fake_fip_id: fake_fip_dep}) result = self.fip_resource.extract_floatingips([]) self.assertTrue(1 == len(result)) self.assertTrue(1 == len(self.fip_resource.get_collected_resources()))
def test_extract_stacks_from_cache(self, mock_stack): fake_stack = copy.deepcopy(fake_stack_dict) mock_stack.return_value = fake_stack fake_stack_res = resource.Resource('stack_0', 'OS::Heat::Stack', fake_stack['id']) fake_stack_dep = resource.ResourceDependency(fake_stack['id'], fake_stack['stack_name'], 'stack_0', 'OS::Heat::Stack') self.stack_resource = stacks.StackResource( self.context, collected_resources={fake_stack['id']: fake_stack_res}, collected_dependencies={fake_stack['id']: fake_stack_dep}) result = self.stack_resource.extract_stacks([fake_stack['id']]) self.assertEqual(1, len(result)) self.assertEqual(fake_stack['id'], result[0].id)
def mock_extract_networks(self, network_ids=None): for net_id in network_ids: net_resource = self._collected_resources.get(net_id) if net_resource: continue resource_type = "OS::Neutron::Net" resource_name = "server_%d" % self._get_resource_num(resource_type) net_resource = resource.Resource(resource_name, resource_type, net_id, properties={}) name = 'volume_%s' % net_id net_dependency = resource.ResourceDependency(net_id, name, resource_name, resource_type) self._collected_resources[net_id] = net_resource self._collected_dependencies[net_id] = net_dependency
def test_extract_secgroups_from_cache(self, mock_secgroup_list): fake_secgroup = copy.deepcopy(fake_secgroup_dict) mock_secgroup_list.return_value = [fake_secgroup] fake_sg_id = fake_secgroup['id'] fake_sg_name = fake_secgroup['name'] fake_net_res = resource.Resource(fake_sg_name, 'OS::Neutron::SecurityGroup', fake_sg_id) fake_net_dep = resource.ResourceDependency( fake_sg_id, fake_sg_name, 'securitygroup_0', 'OS::Neutron::SecurityGroup') self.secgroup_resource = secgroup.SecGroup( self.context, collected_resources={fake_sg_id: fake_net_res}, collected_dependencies={fake_sg_id: fake_net_dep}) result = self.secgroup_resource.extract_secgroups([]) self.assertTrue(1 == len(result)) self.assertEqual(fake_sg_id, result[0].id)
def extract_qos(self, qos_id, parent_name=None, parent_resources=None): LOG.debug('Create qos resource start: %s', qos_id) properties = {} # 1 check qos resource is existing or not qos_res = self._collected_resources.get(qos_id, None) if qos_res: LOG.debug('Create qos resource exist: %s', qos_id) return qos_res # 2 query qos info try: qos_info = self.cinder_api.get_qos_specs(self.context, qos_id) except Exception as e: _msg = 'Create volume qos error: %s' % e LOG.error(_msg) raise exception.ResourceExtractFailed(reason=_msg) properties['specs'] = qos_info.get('specs') properties['name'] = qos_info.get('name') qos_type = "OS::Cinder::Qos" qos_name = 'CinderQos_%d' % self._get_resource_num(qos_type) if parent_name and qos_id in parent_resources: qos_name = parent_name + '.' + qos_name qos_res = resource.Resource(qos_name, qos_type, qos_id, properties=properties) qos_dep = resource.ResourceDependency(qos_id, qos_name, '', qos_type) self._collected_resources[qos_id] = qos_res self._collected_dependencies[qos_id] = qos_dep LOG.debug('Create qos resource end: %s', qos_id) return qos_res
def test_extract_routers_from_cache(self, mock_router_list): fake_router = copy.deepcopy(fake_route_dict) mock_router_list.return_value = [fake_router] fake_router_id = fake_router['id'] fake_router_name = fake_router['name'] fake_router_res = resource.Resource(fake_router_name, 'OS::Neutron::Router', fake_router_id) fake_router_dep = resource.ResourceDependency(fake_router_id, fake_router_name, 'router_0', 'OS::Neutron::Router') self.net_resource = networks.NetworkResource( self.context, collected_resources={fake_router_id: fake_router_res}, collected_dependencies={fake_router_id: fake_router_dep}) result = self.net_resource.extract_routers([]) self.assertTrue(1 == len(result)) self.assertEqual(fake_router_id, result[0].id) self.assertTrue(1 == len(self.net_resource.get_collected_resources())) self.assertFalse( len(self.net_resource.get_collected_dependencies() [fake_router_id].dependencies))
def test_extract_keypairs_from_cache(self, mock_res, mock_keypair_list): """The request keypair ia already in collected resources""" fake_keypair = { "id": "keypair_0", "name": "keypair_0", "type": "OS::Nova::KeyPair" } fake_keypair_res = resource.Resource(**fake_keypair) fake_keypair_dep = resource.ResourceDependency("keypair_0", "keypair_0", "keypair_0", "OS::Nova::KeyPair") self.instance_resource = instances.InstanceResource( self.context, collected_resources={'keypair_0': fake_keypair_res}, collected_dependencies={'keypair_0': fake_keypair_dep}) mock_keypair_list.return_value = [{ "id": "keypair_0", "name": "keyapir", "public_key": "public_key" }] keypair_res = self.instance_resource.extract_keypairs([]) self.assertEqual(1, len(keypair_res))
def test_extract_flavor_from_cache(self, mock_res, mock_flavor_list): """The request flavors ia already in collected resources""" fake_flavor = {"id": 6, "name": "flavor_0", "type": "OS::Nova::Flavor"} fake_flavor_res = resource.Resource(**fake_flavor) fake_flavor_dep = resource.ResourceDependency(6, 'flavor_0', "flavor_0", "OS::Nova::Flavor") self.instance_resource = instances.InstanceResource( self.context, collected_resources={6: fake_flavor_res}, collected_dependencies={6: fake_flavor_dep}) mock_flavor_list.return_value = [{ "id": 6, "name": '', "ram": 1024, "vcpus": 1, "disk": 5, "rxtx_factor": 1, "os-flavor-access:is_public": True, "OS-FLV-EXT-DATA:ephemeral": 0, }] flavor_res = self.instance_resource.extract_flavors([]) self.assertEqual(1, len(flavor_res))
def _generate_router_resource(self, router_id, other_net_ids, parent_name=None, parent_resources=None): # 1. get router info from neutron api # routers = None try: router = self.neutron_api.get_router(self.context, router_id) except Exception as e: msg = "Router resource extracted failed, \ can't find router with id: %s. %s" % \ (router_id, unicode(e)) LOG.error(msg) raise exception.ResourceNotFound(message=msg) if not router: msg = "Router resource <%s> could not be found." \ % router_id LOG.error(msg) raise exception.ResourceNotFound(message=msg) # 2. check this router resource is exist or not router_id = router.get('id') router_res = self._collected_resources.get(router_id) if router_res: return router_res.name # 3. generate new router resource properties = { 'name': router.get('name'), 'admin_state_up': router.get('admin_state_up') } dependencies = [] external_gateway_info = router.get('external_gateway_info') if external_gateway_info: network = external_gateway_info.get('network_id') if (network in other_net_ids): if network: net_res = self.extract_nets( [network], with_subnets=True, parent_name=parent_name, parent_resources=parent_resources) if net_res: enable_snat = external_gateway_info.get('enable_snat') properties['external_gateway_info'] = \ {'network': {'get_resource': net_res[0].name}, 'enable_snat': enable_snat} dep_res_name = net_res[0].properties.get('name', '') dependencies.append({ 'id': net_res[0].id, 'name': net_res[0].name, 'name_in_template': dep_res_name, 'type': net_res[0].type }) else: # if router relate public network not in clone list, # do not copy router return None else: # if router does not have public network, do not clone router return None resource_type = "OS::Neutron::Router" resource_name = 'router_%d' % self._get_resource_num(resource_type) if parent_name and router_id in parent_resources: resource_name = parent_name + '.' + resource_name router_res = resource.Resource(resource_name, resource_type, router_id, properties=properties) # remove duplicate dependencies # dependencies = {}.fromkeys(dependencies).keys() router_dep = resource.ResourceDependency(router_id, resource_name, router.get('name'), resource_type, dependencies=dependencies) self._collected_resources[router_id] = router_res self._collected_dependencies[router_id] = router_dep return router_res
def extract_routers(self, router_ids, parent_name=None, parent_resources=None): router_objs = [] routerResources = [] if not router_ids: LOG.info('Extract resources of routers.') router_objs = filter(self._tenant_filter, self.neutron_api.router_list(self.context)) else: LOG.debug('Extract resources of routers: %s', router_ids) # remove duplicate routers router_ids = {}.fromkeys(router_ids).keys() for router_id in router_ids: try: router = self.neutron_api.get_router( self.context, router_id) router_objs.append(router) except Exception as e: msg = "Router resource <%s> could not be found. %s" \ % (router_id, unicode(e)) LOG.error(msg) raise exception.ResourceNotFound(message=msg) # every router_obj is a dict for router in router_objs: router_id = router.get('id') router_res = self._collected_resources.get(router_id) if router_res: routerResources.append(router_res) continue properties = { 'name': router.get('name'), 'admin_state_up': router.get('admin_state_up') } dependencies = [] external_gateway_info = router.get('external_gateway_info') if external_gateway_info: network = external_gateway_info.get('network_id') if network: net_res = self.extract_nets( [network], with_subnets=True, parent_name=parent_name, parent_resources=parent_resources) if net_res: enable_snat = external_gateway_info.get('enable_snat') properties['external_gateway_info'] = \ {'network': {'get_resource': net_res[0].name}, 'enable_snat': enable_snat} dep_res_name = net_res[0].properties.get('name', '') dependencies.append({ 'id': net_res[0].id, 'name': net_res[0].name, 'name_in_template': dep_res_name, 'type': net_res[0].type }) resource_type = "OS::Neutron::Router" resource_name = 'router_%d' % self.\ _get_resource_num(resource_type) if parent_name and router_id in parent_resources: resource_name = parent_name + '.' + resource_name router_res = resource.Resource(resource_name, resource_type, router_id, properties=properties) # remove duplicate dependencies # dependencies = {}.fromkeys(dependencies).keys() router_dep = resource.ResourceDependency(router_id, resource_name, router.get('name'), resource_type, dependencies=dependencies) self._collected_resources[router_id] = router_res self._collected_dependencies[router_id] = router_dep routerResources.append(router_res) if router_ids and not routerResources: msg = "Router resource extracted failed, \ can't find the router with id of %s." % router_ids LOG.error(msg) raise exception.ResourceNotFound(message=msg) return routerResources
def _extract_router_interface(self, router_res, subnet_res, parent_name=None, parent_resources=None): LOG.debug("Extract resources of router interface by %s and %s.", router_res.name, subnet_res.name) # step 1: judge whether the interface exists interfaces = self.neutron_api.port_list( self.context, device_owner="network:router_interface", device_id=router_res.id) interface = None for infa in interfaces: if interface: break fixed_ips = infa.get("fixed_ips", []) for fip in fixed_ips: if fip.get("subnet_id", "") == subnet_res.id: interface = infa break if not interface: return # step 2: build interface properties = { 'router_id': { 'get_resource': router_res.name }, 'subnet_id': { 'get_resource': subnet_res.name } } interface_id = interface.get('id', '') resource_type = "OS::Neutron::RouterInterface" resource_name = '%s_interface_0' % router_res.name if parent_name and router_res.id in parent_resources: resource_name = parent_name + '.' + resource_name interface_res = resource.Resource(resource_name, resource_type, interface_id, properties=properties) interface_dep = resource.ResourceDependency(interface_id, resource_name, interface.get('name', ''), resource_type) dep_router_name = router_res.properties.get('name', '') interface_dep.add_dependency(router_res.id, router_res.name, dep_router_name, router_res.type) dep_sub_name = subnet_res.properties.get('name', '') interface_dep.add_dependency(subnet_res.id, subnet_res.name, dep_sub_name, subnet_res.type) self._collected_resources[interface_id] = interface_res self._collected_dependencies[interface_id] = interface_dep return interface_res
def _extract_associate(self, floatingip, router_res, port_id, floatip_name, parent_name=None, parent_resources=None, **kwargs): properties = {} dependencies = [] port_res = self._collected_resources.get(port_id) if not port_res: port_res = self.extract_ports([port_id], parent_name, parent_resources) if port_res: port_res = port_res[0] else: LOG.error('Resource network driver query port failed, ID: %s', port_id) return None properties['port_id'] = {'get_resource': port_res.name} properties['floatingip_id'] = {'get_resource': floatip_name} dep_res_name = port_res.properties.get('name', '') dependencies.append({ 'id': port_res.id, 'name': port_res.name, 'name_in_template': dep_res_name, 'type': port_res.type }) dependencies.append({ 'id': kwargs['id'], 'name': kwargs['name'], 'name_in_template': kwargs['name_in_template'], 'type': kwargs['type'] }) fixed_id_addr = floatingip.get('fixed_ip_address') if router_res and port_res and fixed_id_addr: fixed_ips = port_res.properties.get('fixed_ips') subnet_res_name = None if len(fixed_ips) == 1: subnet_res_name = \ fixed_ips[0].get('subnet_id', {}).get('get_resource') elif len(fixed_ips) >= 2: for f in fixed_ips: if f.get('ip_address', '') == fixed_id_addr: subnet_res_name = \ f.get('subnet_id', {}).get('get_resource') # If port has multiple fixed ips, # we have to specify the ip addr in floatingip ip_index = fixed_ips.index(f) properties['fixed_ip_address'] = { 'get_attr': [ port_res.name, 'fixed_ips', ip_index, 'ip_address' ] } break # build router interface if subnet_res_name: subnet_res = self._get_resource_by_name(subnet_res_name) if subnet_res: self._extract_router_interface(router_res[0], subnet_res, parent_name, parent_resources) resource_type = "OS::Neutron::FloatingIPAssociation" resource_name = 'FloatingIPAssiation_%d' % \ self._get_resource_num(resource_type) resource_id = uuidutils.generate_uuid() if parent_name and port_id in parent_resources: resource_name = parent_name + '.' + resource_name association_res = resource.Resource(resource_name, resource_type, resource_id, properties=properties) # remove duplicate dependencies # dependencies = {}.fromkeys(dependencies).keys() association_dep = resource.ResourceDependency( resource_id, resource_name, '', resource_type, dependencies=dependencies) self._collected_resources[resource_id] = association_res self._collected_dependencies[resource_id] = association_dep
def extract_floatingips(self, floatingip_ids, parent_name=None, parent_resources=None): floatingip_objs = [] floatingipResources = [] if not floatingip_ids: LOG.debug('Extract resources of floating ips.') floatingip_list = self.neutron_api.floatingip_list(self.context) floatingip_objs = filter(self._tenant_filter, floatingip_list) else: LOG.debug('Extract resources of floating ips: %s', floatingip_ids) # remove duplicate floatingips floatingip_ids = {}.fromkeys(floatingip_ids).keys() for floatingip_id in floatingip_ids: try: floatingip = self.neutron_api.get_floatingip( self.context, floatingip_id) floatingip_objs.append(floatingip) except Exception as e: msg = "FloatingIp resource <%s> could not be found. %s" \ % (floatingip_id, unicode(e)) LOG.error(msg) raise exception.ResourceNotFound(message=msg) for floatingip in floatingip_objs: floatingip_id = floatingip.get('id') floatingip_res = self._collected_resources.get(floatingip_id) if floatingip_res: floatingipResources.append(floatingip_res) continue properties = {} dependencies = [] floating_network_id = floatingip.get('floating_network_id') floating_ip_address = floatingip.get('floating_ip_address') if not floating_network_id or not floating_ip_address: msg = "FloatingIp information is abnormal. \ 'floating_network_id' or 'floating_ip_address' " \ "is None" LOG.error(msg) raise exception.ResourceAttributesException(message=msg) net_res = self.extract_nets([floating_network_id], with_subnets=True, parent_name=parent_name, parent_resources=parent_resources) properties['floating_network_id'] = \ {'get_resource': net_res[0].name} dep_res_name = net_res[0].properties.get('name', '') dependencies.append({ 'id': net_res[0].id, 'name': net_res[0].name, 'name_in_template': dep_res_name, 'type': net_res[0].type }) router_id = floatingip.get('router_id') router_res = None if router_id: router_res = self.extract_routers([router_id], parent_name, parent_resources) port_id = floatingip.get('port_id') resource_type = "OS::Neutron::FloatingIP" resource_name = 'floatingip_%d' % \ self._get_resource_num(resource_type) if parent_name and port_id in parent_resources: resource_name = parent_name + '.' + resource_name if port_id: kwargs = {} kwargs['id'] = port_id kwargs['type'] = resource_type kwargs['name_in_template'] = '' self._extract_associate(floatingip, router_res, port_id, resource_name, parent_name, parent_resources, **kwargs) floatingip_res = resource.Resource(resource_name, resource_type, floatingip_id, properties=properties) # remove duplicate dependencies # dependencies = {}.fromkeys(dependencies).keys() floatingip_dep = resource.ResourceDependency( floatingip_id, resource_name, '', resource_type, dependencies=dependencies) self._collected_resources[floatingip_id] = floatingip_res self._collected_dependencies[floatingip_id] = floatingip_dep floatingipResources.append(floatingip_res) if floatingip_ids and not floatingipResources: msg = "FloatingIp resource extracted failed, \ can't find the floatingip with id of %s." % floatingip_ids LOG.error(msg) raise exception.ResourceNotFound(message=msg) return floatingipResources
def extract_nets(self, net_ids, with_subnets=False, parent_name=None, parent_resources=None): net_objs = [] netResources = [] if not net_ids: LOG.info('Extract resources of all networks.') network_list = self.neutron_api.network_list(self.context) net_objs = filter(self._tenant_filter, network_list) else: LOG.info('Extract resources of networks: %s', net_ids) # remove duplicate nets net_ids = {}.fromkeys(net_ids).keys() for net_id in net_ids: try: net = self.neutron_api.get_network(self.context, net_id) net_objs.append(net) except Exception as e: msg = "Network resource <%s> could not be found. %s" \ % (net_id, unicode(e)) LOG.error(msg) raise exception.ResourceNotFound(message=msg) # every net_obj is a dict for net in net_objs: net_id = net.get('id') net_res = self._collected_resources.get(net_id) if net_res: netResources.append(net_res) continue properties = { 'name': net.get('name'), 'admin_state_up': net.get('admin_state_up'), 'shared': net.get('shared') } value_specs = {} if net.get('provider:physical_network') is not None: value_specs['provider:physical_network'] = \ net.get('provider:physical_network') if net.get('provider:network_type') is not None: value_specs['provider:network_type'] = \ net.get('provider:network_type') if net.get('provider:segmentation_id') is not None: value_specs['provider:segmentation_id'] = \ net.get('provider:segmentation_id') if net.get('router:external') is not None: value_specs['router:external'] = net.get('router:external') if value_specs: properties['value_specs'] = value_specs resource_type = "OS::Neutron::Net" resource_name = 'network_%d' % \ self._get_resource_num(resource_type) if parent_name and net_id in parent_resources: resource_name = parent_name + '.' + resource_name if with_subnets: kwargs = {} kwargs['id'] = net_id kwargs['type'] = resource_type kwargs['name_in_template'] = net.get('name') self.extract_subnets_of_network(resource_name, net.get('subnets'), parent_name, parent_resources, **kwargs) net_res = resource.Resource(resource_name, resource_type, net_id, properties=properties) net_dep = resource.ResourceDependency(net_id, resource_name, net.get('name'), resource_type) self._collected_resources[net_id] = net_res self._collected_dependencies[net_id] = net_dep netResources.append(net_res) if net_ids and not netResources: msg = "Network resource extracted failed, \ can't find the network with id of %s." % net_ids LOG.error(msg) raise exception.ResourceNotFound(message=msg) return netResources
def extract_ports(self, port_ids, parent_name=None, parent_resources=None): port_objs = [] portResources = [] if not port_ids: LOG.debug('Extract resources of all ports.') port_objs = filter(self._tenant_filter, self.neutron_api.port_list(self.context)) else: LOG.debug('Extract resources of ports: %s', port_ids) # remove duplicate ports port_ids = {}.fromkeys(port_ids).keys() for port_id in port_ids: try: port = self.neutron_api.get_port(self.context, port_id) port_objs.append(port) except Exception as e: msg = "Port resource <%s> could not be found. %s" \ % (port_id, unicode(e)) LOG.error(msg) raise exception.ResourceNotFound(message=msg) # every port_obj is a dict for port in port_objs: port_id = port.get('id') port_res = self._collected_resources.get(port_id) if port_res: portResources.append(port_res) continue properties = { 'name': port.get('name', ''), 'mac_address': port.get('mac_address', ''), 'admin_state_up': port.get('admin_state_up', True), } dependencies = [] if port.get('allowed_address_pairs'): properties['allowed_address_pairs'] = \ port.get('allowed_address_pairs') value_specs = {} if port.get('binding:profile') is not None: value_specs['binding:profile'] = port.get('binding:profile') # fsp 6.1 add(wanggang) if port.get('binding:vnic_type', None): properties['binding:vnic_type'] = \ port.get('binding:vnic_type') if port.get('qos_policy_id', None): properties['qos_policy'] = \ port.get('qos_policy_id') # properties['device_owner'] = port.get('device_owner', '') # properties['device_id'] = port.get('device_id', '') if value_specs: properties['value_specs'] = value_specs if port.get('security_groups'): secgroup_ids = port.get('security_groups') secgroup_res = self.extract_secgroups(secgroup_ids, parent_name, parent_resources) secgroup_properties = [] for sec in secgroup_res: secgroup_properties.append({'get_resource': sec.name}) dep_res_name = sec.properties.get('name', '') dependencies.append({ 'id': sec.id, 'name': sec.name, 'name_in_template': dep_res_name, 'type': sec.type }) properties['security_groups'] = secgroup_properties fixed_ips_properties = [] fixed_ips = port.get('fixed_ips', []) for opt in fixed_ips: subnet_id = opt.get('subnet_id') ip_address = opt.get('ip_address') if not subnet_id or not ip_address: msg = "Port information is abnormal. \ 'subnet_id' or 'ip_address' attribute is None" LOG.error(msg) raise exception.ResourceAttributesException(message=msg) subnet_res = self.extract_subnets([subnet_id], parent_name, parent_resources) if not subnet_res: LOG.error("Subnet %s could not be found.", subnet_id) raise exception.ResourceNotFound(resource_type='Subnet', resource_id=subnet_id) sub_name = subnet_res[0].name fixed_ips_properties.append({ 'subnet_id': { 'get_resource': sub_name }, 'ip_address': ip_address }) sub_properties = subnet_res[0].properties network_name = \ sub_properties.get('network_id').get('get_resource') properties['network_id'] = {"get_resource": network_name} net_res = None for r_k, r_s in self._collected_resources.items(): if r_s.name == network_name: net_res = r_s break if net_res: dep_net_name = net_res.properties.get('name', '') dependencies.append({ 'id': net_res.id, 'name': net_res.name, 'name_in_template': dep_net_name, 'type': net_res.type }) dep_sub_name = sub_properties.get('name', '') dependencies.append({ 'id': subnet_res[0].id, 'name': subnet_res[0].name, 'name_in_template': dep_sub_name, 'type': subnet_res[0].type }) properties['fixed_ips'] = fixed_ips_properties resource_type = "OS::Neutron::Port" resource_name = 'port_%d' % self._get_resource_num(resource_type) if parent_name and port_id in parent_resources: resource_name = parent_name + '.' + resource_name port_res = resource.Resource(resource_name, resource_type, port_id, properties=properties) # remove duplicate dependencies # dependencies = {}.fromkeys(dependencies).keys() port_dep = resource.ResourceDependency(port_id, resource_name, port.get('name'), resource_type, dependencies=dependencies) self._collected_resources[port_id] = port_res self._collected_dependencies[port_id] = port_dep portResources.append(port_res) if port_ids and not portResources: msg = "Port resource extracted failed, \ can't find the port with id of %s." % port_ids LOG.error(msg) raise exception.ResourceNotFound(message=msg) return portResources