diff --git a/README-bagpipe.rst b/README-bagpipe.rst index 6d64b10e..7100103b 100644 --- a/README-bagpipe.rst +++ b/README-bagpipe.rst @@ -17,10 +17,6 @@ In devstack : [service_providers] service_provider=BGPVPN:BaGPipe:networking_bgpvpn.neutron.services.service_drivers.bagpipe.bagpipe.BaGPipeBGPVPNDriver:default - * add ``bgpvpn_notify`` to ``Q_ML2_PLUGIN_MECHANISM_DRIVERS`` - - * (this mech_driver does not implement the setup of L2 networks; it is used only to notify the ``bagpipe`` driver for the BGPVPN plugin of L2 ports coming and going on compute nodes) - * on a control node, if you want to run the Fake Route-Reflector there:: enable_plugin bagpipe-bgp https://github.com/Orange-OpenSource/bagpipe-bgp.git diff --git a/networking_bgpvpn/neutron/db/bgpvpn_db.py b/networking_bgpvpn/neutron/db/bgpvpn_db.py index b42d30b3..39cf8cc4 100644 --- a/networking_bgpvpn/neutron/db/bgpvpn_db.py +++ b/networking_bgpvpn/neutron/db/bgpvpn_db.py @@ -53,12 +53,6 @@ class BGPVPNConnectionMissingRouteTarget(q_exc.BadRequest): " route_targets, import_targets or export_targets attribute") -class BGPVPNNetworkInUse(q_exc.NetworkInUse): - message = _("Unable to complete operation on network %(network_id)s. " - "There are one or more BGP VPN connections associated" - " to the network.") - - class BGPVPNPluginDb(common_db_mixin.CommonDbMixin): """BGP VPN service plugin database class using SQLAlchemy models.""" diff --git a/networking_bgpvpn/neutron/services/service_drivers/bagpipe/bagpipe.py b/networking_bgpvpn/neutron/services/service_drivers/bagpipe/bagpipe.py index 94823f26..5151404b 100644 --- a/networking_bgpvpn/neutron/services/service_drivers/bagpipe/bagpipe.py +++ b/networking_bgpvpn/neutron/services/service_drivers/bagpipe/bagpipe.py @@ -16,11 +16,16 @@ from sqlalchemy.orm import exc from sqlalchemy import sql +from neutron import context as n_context +from neutron import manager + +from neutron.callbacks import events +from neutron.callbacks import registry +from neutron.callbacks import resources from neutron.common import constants as const from neutron.db import models_v2 from oslo_log import log as logging -from networking_bgpvpn.neutron.db import bgpvpn_db from networking_bgpvpn.neutron.services import service_drivers from networking_bagpipe_l2.agent.bgpvpn import rpc_client @@ -74,6 +79,12 @@ class BaGPipeBGPVPNDriver(service_drivers.BGPVPNDriverDB): self.agent_rpc = rpc_client.BGPVPNAgentNotifyApi() + registry.subscribe(self.registry_port_updated, resources.PORT, + events.AFTER_UPDATE) + + registry.subscribe(self.registry_port_deleted, resources.PORT, + events.AFTER_DELETE) + @property def service_type(self): return BAGPIPE_BGPVPN @@ -146,8 +157,7 @@ class BaGPipeBGPVPNDriver(service_drivers.BGPVPNDriverDB): return bgpvpn_rts - def _retrieve_bgpvpn_network_info_for_port(self, context, port_id, - network_id): + def _retrieve_bgpvpn_network_info_for_port(self, context, port): """Retrieve BGP VPN network informations for a specific port { @@ -161,6 +171,9 @@ class BaGPipeBGPVPNDriver(service_drivers.BGPVPNDriverDB): } } """ + port_id = port['id'] + network_id = port['network_id'] + bgpvpn_network_info = {} # Check if port is connected on a BGP VPN network @@ -297,17 +310,34 @@ class BaGPipeBGPVPNDriver(service_drivers.BGPVPNDriverDB): self._format_bgpvpn_connection(bgpvpn_connection) ) + def _get_port_host(self, port_id): + # the port dict, as provided by the registry callback + # has no binding:host_id information, it seems the reason is + # because the context is not admin + # let's switch to an admin context and retrieve full port info + _core_plugin = manager.NeutronManager.get_plugin() + full_port = _core_plugin.get_port(n_context.get_admin_context(), + port_id) + + if 'binding:host_id' not in full_port: + raise Exception("cannot determine host_id for port %s, " + "aborting BGPVPN update", port_id) + + return full_port.get('binding:host_id') + def notify_port_updated(self, context, port): port_bgpvpn_info = {'id': port['id'], 'network_id': port['network_id']} - agent_host = port['binding:host_id'] + + if port['device_owner'] == 'network:dhcp': + LOG.info("Owner of port %s is network:dhcp, ignoring") + + agent_host = self._get_port_host(port['id']) if port['status'] == const.PORT_STATUS_ACTIVE: bgpvpn_network_info = ( - self._retrieve_bgpvpn_network_info_for_port( - context, - port['id'], - port['network_id'])) + self._retrieve_bgpvpn_network_info_for_port(context, port) + ) if bgpvpn_network_info: port_bgpvpn_info.update(bgpvpn_network_info) @@ -319,28 +349,28 @@ class BaGPipeBGPVPNDriver(service_drivers.BGPVPNDriverDB): self.agent_rpc.detach_port_from_bgpvpn_network(context, port_bgpvpn_info, agent_host) + else: + LOG.debug("no action since new port status is %", port['status']) def remove_port_from_bgpvpn_agent(self, context, port): port_bgpvpn_info = {'id': port['id'], 'network_id': port['network_id']} - agent_host = port['binding:host_id'] + + if port['device_owner'] == 'network:dhcp': + LOG.info("Owner of port %s is network:dhcp, ignoring") + + agent_host = self._get_port_host(port['id']) self.agent_rpc.detach_port_from_bgpvpn_network(context, port_bgpvpn_info, agent_host) - def prevent_bgpvpn_network_deletion(self, context, network_id): - '''Method called by the mech_driver at delete_network_precommit time + def registry_port_updated(self, resource, event, trigger, **kwargs): + context = kwargs.get('context') + port_dict = kwargs.get('port') + self.notify_port_updated(context, port_dict) - Used to prevent deletion of a network referred to by a BGPVPN - connection. - ''' - LOG.debug('Prevent BGP VPN network deletion') - # Note(ethuleau): can we use DB directly instead of the service - # provider to get that list? - if (self.service_plugin.get_bgpvpn_connections( - context, - filters={'network_id': [network_id]})): - raise bgpvpn_db.BGPVPNNetworkInUse(network_id=network_id) - else: - LOG.debug('Network %(network_id)s can be deleted') + def registry_port_deleted(self, resource, event, trigger, **kwargs): + context = kwargs.get('context') + port_dict = kwargs.get('port') + self.remove_port_from_bgpvpn_agent(context, port_dict) diff --git a/networking_bgpvpn/neutron/services/service_drivers/bagpipe/ml2_mech_driver.py b/networking_bgpvpn/neutron/services/service_drivers/bagpipe/ml2_mech_driver.py deleted file mode 100644 index bc6ec2b9..00000000 --- a/networking_bgpvpn/neutron/services/service_drivers/bagpipe/ml2_mech_driver.py +++ /dev/null @@ -1,64 +0,0 @@ -# Copyright (c) 2015 Orange. -# All Rights Reserved. -# -# Licensed under the Apache License, Version 2.0 (the "License"); you may -# not use this file except in compliance with the License. You may obtain -# a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT -# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the -# License for the specific language governing permissions and limitations -# under the License. - -from oslo_log import log - -from neutron import context as n_context -from neutron import manager - -from networking_bgpvpn.neutron.services.common import constants -from neutron.plugins.ml2 import driver_api as api - -LOG = log.getLogger(__name__) - - -class ML2BGPVPNMechanismDriver(api.MechanismDriver): - """This driver notifies the BGPVPNPlugin driver of port events. - - It allows to notify BGP VPN plugin service drivers that need to be aware - of ports coming and going. - """ - - def initialize(self): - self.db_context = n_context.get_admin_context() - - def delete_network_precommit(self, context): - network = context.current - - bgpvpnplugin = manager.NeutronManager.get_service_plugins().get( - constants.BGPVPN) - - if bgpvpnplugin: - bgpvpnplugin.driver.prevent_bgpvpn_network_deletion( - self.db_context, network['id']) - - def update_port_postcommit(self, context): - port = context.current - - bgpvpnplugin = manager.NeutronManager.get_service_plugins().get( - constants.BGPVPN) - - if bgpvpnplugin: - bgpvpnplugin.driver.notify_port_updated(self.db_context, port) - - def delete_port_postcommit(self, context): - port = context.current - - bgpvpnplugin = manager.NeutronManager.get_service_plugins().get( - constants.BGPVPN) - - if bgpvpnplugin: - bgpvpnplugin.driver.remove_port_from_bgpvpn_agent(self.db_context, - port) diff --git a/setup.cfg b/setup.cfg index ab594fc0..873d4fff 100644 --- a/setup.cfg +++ b/setup.cfg @@ -35,8 +35,6 @@ console_scripts= neutron-bagpipe-openvswitch-agent = networking_bgpvpn.neutron.services.service_drivers.bagpipe.ovs_agent.ovs_bagpipe_neutron_agent:main neutronclient.extension= bgpvpn_connection = networking_bgpvpn.neutronclient.neutron.v2_0.bgpvpn.bgpvpn_connection -neutron.ml2.mechanism_drivers = - bgpvpn_notify = networking_bgpvpn.neutron.services.service_drivers.bagpipe.ml2_mech_driver:ML2BGPVPNMechanismDriver [build_sphinx] source-dir = doc/source

AltStyle によって変換されたページ (->オリジナル) /