Fix bulk port binding
Bulk ports were not binding correctly when they were created. This is
due to a few inconsistencies between the create_port code and the
create_port_bulk code, mostly a result of the use of the Port object in
the bulk code.
Change-Id: I3bcd3cec12b1b6f6a568cda4bfeb569f636efb98
Closes-Bug: #1835209
(cherry picked from commit d0c172afa6
)
This commit is contained in:
parent
1229be91d9
commit
aa60d6e837
|
@ -215,7 +215,7 @@ class DbBasePluginCommon(common_db_mixin.CommonDbMixin):
|
|||
"admin_state_up": port["admin_state_up"],
|
||||
"status": port["status"],
|
||||
"fixed_ips": [{'subnet_id': ip["subnet_id"],
|
||||
'ip_address': ip["ip_address"]}
|
||||
'ip_address': str(ip["ip_address"])}
|
||||
for ip in port["fixed_ips"]],
|
||||
"device_id": port["device_id"],
|
||||
"device_owner": port["device_owner"]}
|
||||
|
|
|
@ -1418,8 +1418,10 @@ class L3_NAT_dbonly_mixin(l3.RouterPluginBase,
|
|||
floatingip_id=fip_id,
|
||||
floatingip_db=floatingip_db)
|
||||
|
||||
self._core_plugin.update_port(context.elevated(), external_port['id'],
|
||||
{'port': {'device_id': fip_id}})
|
||||
self._core_plugin.update_port(
|
||||
context.elevated(), external_port['id'],
|
||||
{'port': {'device_id': fip_id,
|
||||
'project_id': fip['tenant_id']}})
|
||||
registry.notify(resources.FLOATING_IP,
|
||||
events.AFTER_UPDATE,
|
||||
self._update_fip_assoc,
|
||||
|
|
|
@ -771,7 +771,8 @@ class SecurityGroupDbMixin(ext_sg.SecurityGroupPluginBase,
|
|||
tenant_id = kwargs['original_' + resource]['tenant_id']
|
||||
else:
|
||||
tenant_id = kwargs[resource]['tenant_id']
|
||||
self._ensure_default_security_group(context, tenant_id)
|
||||
if tenant_id:
|
||||
self._ensure_default_security_group(context, tenant_id)
|
||||
|
||||
def _ensure_default_security_group(self, context, tenant_id):
|
||||
"""Create a default security group if one doesn't exist.
|
||||
|
|
|
@ -1401,11 +1401,18 @@ class Ml2Plugin(db_base_plugin_v2.NeutronDbPluginV2,
|
|||
for port in port_list:
|
||||
# Set up the port request dict
|
||||
pdata = port.get('port')
|
||||
project_id = pdata.get('project_id') or pdata.get('tenant_id')
|
||||
security_group_ids = pdata.get('security_groups')
|
||||
if security_group_ids is const.ATTR_NOT_SPECIFIED:
|
||||
security_group_ids = None
|
||||
else:
|
||||
security_group_ids = set(security_group_ids)
|
||||
if pdata.get('device_owner'):
|
||||
self._enforce_device_owner_not_router_intf_or_device_id(
|
||||
context, pdata.get('device_owner'),
|
||||
pdata.get('device_id'), pdata.get('tenant_id'))
|
||||
bulk_port_data = dict(project_id=pdata.get('project_id'),
|
||||
pdata.get('device_id'), project_id)
|
||||
bulk_port_data = dict(
|
||||
project_id=project_id,
|
||||
name=pdata.get('name'),
|
||||
network_id=pdata.get('network_id'),
|
||||
admin_state_up=pdata.get('admin_state_up'),
|
||||
|
@ -1413,7 +1420,7 @@ class Ml2Plugin(db_base_plugin_v2.NeutronDbPluginV2,
|
|||
const.PORT_STATUS_ACTIVE),
|
||||
device_id=pdata.get('device_id'),
|
||||
device_owner=pdata.get('device_owner'),
|
||||
security_groups=pdata.get('security_groups'),
|
||||
security_group_ids=security_group_ids,
|
||||
description=pdata.get('description'))
|
||||
|
||||
# Ensure that the networks exist.
|
||||
|
@ -1434,6 +1441,7 @@ class Ml2Plugin(db_base_plugin_v2.NeutronDbPluginV2,
|
|||
mac=raw_mac_address)
|
||||
eui_mac_address = netaddr.EUI(raw_mac_address,
|
||||
dialect=eui48.mac_unix_expanded)
|
||||
port['port']['mac_address'] = str(eui_mac_address)
|
||||
|
||||
# Create the Port object
|
||||
db_port_obj = ports_obj.Port(context,
|
||||
|
@ -1441,27 +1449,42 @@ class Ml2Plugin(db_base_plugin_v2.NeutronDbPluginV2,
|
|||
id=uuidutils.generate_uuid(),
|
||||
**bulk_port_data)
|
||||
db_port_obj.create()
|
||||
port_dict = self._make_port_dict(db_port_obj,
|
||||
process_extensions=False)
|
||||
port_compat = {'port': port_dict}
|
||||
|
||||
# Call IPAM to allocate IP addresses
|
||||
try:
|
||||
# TODO(njohnston): IPAM allocation needs to be revamped to
|
||||
# be bulk-friendly.
|
||||
self.ipam.allocate_ips_for_port_and_store(
|
||||
context, db_port_obj, db_port_obj['id'])
|
||||
ips = self.ipam.allocate_ips_for_port_and_store(
|
||||
context, port, db_port_obj['id'])
|
||||
ipam_fixed_ips = []
|
||||
for ip in ips:
|
||||
fixed_ip = ports_obj.IPAllocation(
|
||||
port_id=db_port_obj['id'],
|
||||
subnet_id=ip['subnet_id'],
|
||||
network_id=network_id,
|
||||
ip_address=ip['ip_address'])
|
||||
ipam_fixed_ips.append(fixed_ip)
|
||||
|
||||
db_port_obj['fixed_ips'] = ipam_fixed_ips
|
||||
db_port_obj['ip_allocation'] = (ipalloc_apidef.
|
||||
IP_ALLOCATION_IMMEDIATE)
|
||||
except ipam_exc.DeferIpam:
|
||||
db_port_obj['ip_allocation'] = (ipalloc_apidef.
|
||||
IP_ALLOCATION_DEFERRED)
|
||||
|
||||
fixed_ips = pdata.get('fixed_ips')
|
||||
if validators.is_attr_set(fixed_ips) and not fixed_ips:
|
||||
# [] was passed explicitly as fixed_ips: unaddressed port.
|
||||
db_port_obj['ip_allocation'] = (ipalloc_apidef.
|
||||
IP_ALLOCATION_NONE)
|
||||
|
||||
# Make port dict
|
||||
port_dict = self._make_port_dict(db_port_obj,
|
||||
process_extensions=False)
|
||||
port_dict[portbindings.HOST_ID] = pdata.get(
|
||||
portbindings.HOST_ID)
|
||||
port_compat = {'port': port_dict}
|
||||
|
||||
# Activities immediately post-port-creation
|
||||
self.extension_manager.process_create_port(context, port_dict,
|
||||
db_port_obj)
|
||||
|
@ -1475,6 +1498,10 @@ class Ml2Plugin(db_base_plugin_v2.NeutronDbPluginV2,
|
|||
|
||||
# process port binding
|
||||
binding = db.add_port_binding(context, port_dict['id'])
|
||||
binding_host = pdata.get(
|
||||
portbindings.HOST_ID, const.ATTR_NOT_SPECIFIED)
|
||||
if binding_host != const.ATTR_NOT_SPECIFIED:
|
||||
binding["host"] = binding_host
|
||||
mech_context = driver_context.PortContext(self, context,
|
||||
port_dict, network,
|
||||
binding, None)
|
||||
|
|
|
@ -586,6 +586,9 @@ class NeutronDbPluginV2TestCase(testlib_api.WebTestCase):
|
|||
if neutron_context:
|
||||
# create a specific auth context for this request
|
||||
req.environ['neutron.context'] = neutron_context
|
||||
elif hasattr(self, 'tenant_id'):
|
||||
req.environ['neutron.context'] = context.Context('',
|
||||
self.tenant_id)
|
||||
return req.get_response(self._api_for_resource(resource))
|
||||
|
||||
def _show(self, resource, id,
|
||||
|
|
|
@ -54,6 +54,7 @@ class NetworkRbacTestcase(test_plugin.NeutronDbPluginV2TestCase):
|
|||
'admin_state_up': True,
|
||||
'device_id': 'device_id',
|
||||
'device_owner': 'device_owner',
|
||||
'project_id': target_tenant,
|
||||
'tenant_id': target_tenant}}
|
||||
|
||||
port = self.plugin.create_port(self.context, test_port)
|
||||
|
|
|
@ -69,6 +69,7 @@ class FakeL3PluginWithAgents(common_db_mixin.CommonDbMixin,
|
|||
|
||||
class TestL2PopulationRpcTestCase(test_plugin.Ml2PluginV2TestCase):
|
||||
_mechanism_drivers = ['openvswitch', 'fake_agent', 'l2population']
|
||||
tenant = 'tenant'
|
||||
|
||||
def setUp(self):
|
||||
super(TestL2PopulationRpcTestCase, self).setUp()
|
||||
|
@ -366,13 +367,15 @@ class TestL2PopulationRpcTestCase(test_plugin.Ml2PluginV2TestCase):
|
|||
enable_dhcp=False) as snet:
|
||||
with self.port(
|
||||
subnet=snet,
|
||||
project_id=self.tenant,
|
||||
device_owner=constants.DEVICE_OWNER_DVR_INTERFACE)\
|
||||
as port:
|
||||
port_id = port['port']['id']
|
||||
plugin.update_distributed_port_binding(self.adminContext,
|
||||
port_id, {'port': {portbindings.HOST_ID: HOST_4,
|
||||
'device_id': router['id']}})
|
||||
port = self._show('ports', port_id)
|
||||
port = self._show('ports', port_id,
|
||||
neutron_context=self.adminContext)
|
||||
self.assertEqual(portbindings.VIF_TYPE_DISTRIBUTED,
|
||||
port['port'][portbindings.VIF_TYPE])
|
||||
self.callbacks.update_device_up(
|
||||
|
|
Loading…
Reference in New Issue