# vim: tabstop=4 shiftwidth=4 softtabstop=4 # Copyright 2013 Embrane, Inc. # 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. # # @author: Ivar Lazzaro, Embrane, Inc. import functools from heleosapi import exceptions as h_exc from neutron.openstack.common import log as logging from neutron.plugins.embrane.common import constants as p_con LOG = logging.getLogger(__name__) handlers = dict() def handler(event, handler): def wrap(f): if event not in handler.keys(): new_func_list = [f] handler[event] = new_func_list else: handler[event].append(f) @functools.wraps(f) def wrapped_f(*args, **kwargs): return f(*args, **kwargs) return wrapped_f return wrap @handler(p_con.Events.CREATE_ROUTER, handlers) def _create_dva_and_assign_address(api, tenant_id, neutron_router, flavor, utif_info=None, ip_allocation_info=None): """Creates a new router, and assign the gateway interface if any.""" dva = api.create_router(tenant_id=tenant_id, router_id=neutron_router["id"], name=neutron_router["name"], flavor=flavor, up=neutron_router["admin_state_up"]) try: if utif_info: api.grow_interface(utif_info, neutron_router["admin_state_up"], tenant_id, neutron_router["id"]) if ip_allocation_info: dva = api.allocate_address(neutron_router["id"], neutron_router["admin_state_up"], ip_allocation_info) except h_exc.PreliminaryOperationsFailed as ex: raise h_exc.BrokenInterface(err_msg=ex.message) state = api.extract_dva_state(dva) return state @handler(p_con.Events.UPDATE_ROUTER, handlers) def _update_dva_and_assign_address(api, tenant_id, neutron_router, utif_info=None, ip_allocation_info=None, routes_info=[]): name = neutron_router["name"] up = neutron_router["admin_state_up"] r_id = neutron_router["id"] if ip_allocation_info or routes_info: up = True dva = api.update_dva(tenant_id=tenant_id, router_id=r_id, name=name, up=up, utif_info=utif_info) if ip_allocation_info: api.allocate_address(r_id, up, ip_allocation_info) if routes_info: api.delete_extra_routes(r_id, up) api.set_extra_routes(r_id, neutron_router["admin_state_up"], routes_info) return api.extract_dva_state(dva) @handler(p_con.Events.DELETE_ROUTER, handlers) def _delete_dva(api, tenant_id, neutron_router): try: api.delete_dva(tenant_id, neutron_router["id"]) except h_exc.DvaNotFound: LOG.warning(_("The router %s had no physical representation," "likely already deleted"), neutron_router["id"]) return p_con.Status.DELETED @handler(p_con.Events.GROW_ROUTER_IF, handlers) def _grow_dva_iface_and_assign_address(api, tenant_id, neutron_router, utif_info=None, ip_allocation_info=None): try: dva = api.grow_interface(utif_info, neutron_router["admin_state_up"], tenant_id, neutron_router["id"]) if ip_allocation_info: dva = api.allocate_address(neutron_router["id"], neutron_router["admin_state_up"], ip_allocation_info) except h_exc.PreliminaryOperationsFailed as ex: raise h_exc.BrokenInterface(err_msg=ex.message) state = api.extract_dva_state(dva) return state @handler(p_con.Events.SHRINK_ROUTER_IF, handlers) def _shrink_dva_iface(api, tenant_id, neutron_router, port_id): try: dva = api.shrink_interface(tenant_id, neutron_router["id"], neutron_router["admin_state_up"], port_id) except h_exc.InterfaceNotFound: LOG.warning(_("Interface %s not found in the heleos back-end," "likely already deleted"), port_id) return (p_con.Status.ACTIVE if neutron_router["admin_state_up"] else p_con.Status.READY) except h_exc.PreliminaryOperationsFailed as ex: raise h_exc.BrokenInterface(err_msg=ex.message) state = api.extract_dva_state(dva) return state @handler(p_con.Events.SET_NAT_RULE, handlers) def _create_nat_rule(api, tenant_id, neutron_router, nat_info=None): dva = api.create_nat_entry(neutron_router["id"], neutron_router["admin_state_up"], nat_info) state = api.extract_dva_state(dva) return state @handler(p_con.Events.RESET_NAT_RULE, handlers) def _delete_nat_rule(api, tenant_id, neutron_router, floating_ip_id): dva = api.remove_nat_entry(neutron_router["id"], neutron_router["admin_state_up"], floating_ip_id) state = api.extract_dva_state(dva) return state