Merge "Divide dhcp and l3 agent scheduling into separate extensions"
This commit is contained in:
commit
f8310ed645
@ -61,7 +61,7 @@ class DhcpAgentNotifyAPI(proxy.RpcProxy):
|
||||
"""Notify all the agents that are hosting the network."""
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
if (method != 'network_delete_end' and utils.is_extension_supported(
|
||||
plugin, constants.AGENT_SCHEDULER_EXT_ALIAS)):
|
||||
plugin, constants.DHCP_AGENT_SCHEDULER_EXT_ALIAS)):
|
||||
if method == 'port_create_end':
|
||||
# we don't schedule when we create network
|
||||
# because we want to give admin a chance to
|
||||
|
@ -67,7 +67,7 @@ class L3AgentNotifyAPI(proxy.RpcProxy):
|
||||
"""Notify all the agents that are hosting the routers."""
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
if utils.is_extension_supported(
|
||||
plugin, constants.AGENT_SCHEDULER_EXT_ALIAS):
|
||||
plugin, constants.L3_AGENT_SCHEDULER_EXT_ALIAS):
|
||||
adminContext = (context.is_admin and
|
||||
context or context.elevated())
|
||||
plugin.schedule_routers(adminContext, routers)
|
||||
|
@ -71,4 +71,5 @@ PAGINATION_INFINITE = 'infinite'
|
||||
SORT_DIRECTION_ASC = 'asc'
|
||||
SORT_DIRECTION_DESC = 'desc'
|
||||
|
||||
AGENT_SCHEDULER_EXT_ALIAS = 'agent_scheduler'
|
||||
L3_AGENT_SCHEDULER_EXT_ALIAS = 'l3_agent_scheduler'
|
||||
DHCP_AGENT_SCHEDULER_EXT_ALIAS = 'dhcp_agent_scheduler'
|
||||
|
@ -24,7 +24,8 @@ from neutron.common import constants
|
||||
from neutron.db import agents_db
|
||||
from neutron.db import model_base
|
||||
from neutron.db import models_v2
|
||||
from neutron.extensions import agentscheduler
|
||||
from neutron.extensions import dhcpagentscheduler
|
||||
from neutron.extensions import l3agentscheduler
|
||||
from neutron.openstack.common import log as logging
|
||||
|
||||
|
||||
@ -55,14 +56,11 @@ class RouterL3AgentBinding(model_base.BASEV2, models_v2.HasId):
|
||||
ondelete='CASCADE'))
|
||||
|
||||
|
||||
class AgentSchedulerDbMixin(agentscheduler.AgentSchedulerPluginBase,
|
||||
agents_db.AgentDbMixin):
|
||||
"""Mixin class to add agent scheduler extension to db_plugin_base_v2."""
|
||||
class AgentSchedulerDbMixin(agents_db.AgentDbMixin):
|
||||
"""Common class for agent scheduler mixins."""
|
||||
|
||||
dhcp_agent_notifier = None
|
||||
l3_agent_notifier = None
|
||||
network_scheduler = None
|
||||
router_scheduler = None
|
||||
|
||||
@staticmethod
|
||||
def is_eligible_agent(active, agent):
|
||||
@ -77,101 +75,31 @@ class AgentSchedulerDbMixin(agentscheduler.AgentSchedulerPluginBase,
|
||||
return not agents_db.AgentDbMixin.is_agent_down(
|
||||
agent['heartbeat_timestamp'])
|
||||
|
||||
def get_dhcp_agents_hosting_networks(
|
||||
self, context, network_ids, active=None):
|
||||
if not network_ids:
|
||||
return []
|
||||
query = context.session.query(NetworkDhcpAgentBinding)
|
||||
query = query.options(joinedload('dhcp_agent'))
|
||||
if len(network_ids) == 1:
|
||||
query = query.filter(
|
||||
NetworkDhcpAgentBinding.network_id == network_ids[0])
|
||||
elif network_ids:
|
||||
query = query.filter(
|
||||
NetworkDhcpAgentBinding.network_id in network_ids)
|
||||
if active is not None:
|
||||
query = (query.filter(agents_db.Agent.admin_state_up == active))
|
||||
def update_agent(self, context, id, agent):
|
||||
original_agent = self.get_agent(context, id)
|
||||
result = super(AgentSchedulerDbMixin, self).update_agent(
|
||||
context, id, agent)
|
||||
agent_data = agent['agent']
|
||||
if ('admin_state_up' in agent_data and
|
||||
original_agent['admin_state_up'] != agent_data['admin_state_up']):
|
||||
if (original_agent['agent_type'] == constants.AGENT_TYPE_DHCP and
|
||||
self.dhcp_agent_notifier):
|
||||
self.dhcp_agent_notifier.agent_updated(
|
||||
context, agent_data['admin_state_up'],
|
||||
original_agent['host'])
|
||||
elif (original_agent['agent_type'] == constants.AGENT_TYPE_L3 and
|
||||
self.l3_agent_notifier):
|
||||
self.l3_agent_notifier.agent_updated(
|
||||
context, agent_data['admin_state_up'],
|
||||
original_agent['host'])
|
||||
return result
|
||||
|
||||
return [binding.dhcp_agent
|
||||
for binding in query
|
||||
if AgentSchedulerDbMixin.is_eligible_agent(active,
|
||||
binding.dhcp_agent)]
|
||||
|
||||
def add_network_to_dhcp_agent(self, context, id, network_id):
|
||||
self._get_network(context, network_id)
|
||||
with context.session.begin(subtransactions=True):
|
||||
agent_db = self._get_agent(context, id)
|
||||
if (agent_db['agent_type'] != constants.AGENT_TYPE_DHCP or
|
||||
not agent_db['admin_state_up']):
|
||||
raise agentscheduler.InvalidDHCPAgent(id=id)
|
||||
dhcp_agents = self.get_dhcp_agents_hosting_networks(
|
||||
context, [network_id])
|
||||
for dhcp_agent in dhcp_agents:
|
||||
if id == dhcp_agent.id:
|
||||
raise agentscheduler.NetworkHostedByDHCPAgent(
|
||||
network_id=network_id, agent_id=id)
|
||||
binding = NetworkDhcpAgentBinding()
|
||||
binding.dhcp_agent_id = id
|
||||
binding.network_id = network_id
|
||||
context.session.add(binding)
|
||||
if self.dhcp_agent_notifier:
|
||||
self.dhcp_agent_notifier.network_added_to_agent(
|
||||
context, network_id, agent_db.host)
|
||||
class L3AgentSchedulerDbMixin(l3agentscheduler.L3AgentSchedulerPluginBase,
|
||||
AgentSchedulerDbMixin):
|
||||
"""Mixin class to add l3 agent scheduler extension to db_plugin_base_v2."""
|
||||
|
||||
def remove_network_from_dhcp_agent(self, context, id, network_id):
|
||||
agent = self._get_agent(context, id)
|
||||
with context.session.begin(subtransactions=True):
|
||||
try:
|
||||
query = context.session.query(NetworkDhcpAgentBinding)
|
||||
binding = query.filter(
|
||||
NetworkDhcpAgentBinding.network_id == network_id,
|
||||
NetworkDhcpAgentBinding.dhcp_agent_id == id).one()
|
||||
except exc.NoResultFound:
|
||||
raise agentscheduler.NetworkNotHostedByDhcpAgent(
|
||||
network_id=network_id, agent_id=id)
|
||||
context.session.delete(binding)
|
||||
if self.dhcp_agent_notifier:
|
||||
self.dhcp_agent_notifier.network_removed_from_agent(
|
||||
context, network_id, agent.host)
|
||||
|
||||
def list_networks_on_dhcp_agent(self, context, id):
|
||||
query = context.session.query(NetworkDhcpAgentBinding.network_id)
|
||||
query = query.filter(NetworkDhcpAgentBinding.dhcp_agent_id == id)
|
||||
|
||||
net_ids = [item[0] for item in query]
|
||||
if net_ids:
|
||||
return {'networks':
|
||||
self.get_networks(context, filters={'id': net_ids})}
|
||||
else:
|
||||
return {'networks': []}
|
||||
|
||||
def list_active_networks_on_active_dhcp_agent(self, context, host):
|
||||
agent = self._get_agent_by_type_and_host(
|
||||
context, constants.AGENT_TYPE_DHCP, host)
|
||||
if not agent.admin_state_up:
|
||||
return []
|
||||
query = context.session.query(NetworkDhcpAgentBinding.network_id)
|
||||
query = query.filter(NetworkDhcpAgentBinding.dhcp_agent_id == agent.id)
|
||||
|
||||
net_ids = [item[0] for item in query]
|
||||
if net_ids:
|
||||
return self.get_networks(
|
||||
context,
|
||||
filters={'id': net_ids, 'admin_state_up': [True]}
|
||||
)
|
||||
else:
|
||||
return []
|
||||
|
||||
def list_dhcp_agents_hosting_network(self, context, network_id):
|
||||
dhcp_agents = self.get_dhcp_agents_hosting_networks(
|
||||
context, [network_id])
|
||||
agent_ids = [dhcp_agent.id for dhcp_agent in dhcp_agents]
|
||||
if agent_ids:
|
||||
return {
|
||||
'agents':
|
||||
self.get_agents(context, filters={'id': agent_ids})}
|
||||
else:
|
||||
return {'agents': []}
|
||||
router_scheduler = None
|
||||
|
||||
def add_router_to_l3_agent(self, context, id, router_id):
|
||||
"""Add a l3 agent to host a router."""
|
||||
@ -181,14 +109,14 @@ class AgentSchedulerDbMixin(agentscheduler.AgentSchedulerPluginBase,
|
||||
if (agent_db['agent_type'] != constants.AGENT_TYPE_L3 or
|
||||
not agent_db['admin_state_up'] or
|
||||
not self.get_l3_agent_candidates(router, [agent_db])):
|
||||
raise agentscheduler.InvalidL3Agent(id=id)
|
||||
raise l3agentscheduler.InvalidL3Agent(id=id)
|
||||
query = context.session.query(RouterL3AgentBinding)
|
||||
try:
|
||||
binding = query.filter(
|
||||
RouterL3AgentBinding.l3_agent_id == agent_db.id,
|
||||
RouterL3AgentBinding.router_id == router_id).one()
|
||||
if binding:
|
||||
raise agentscheduler.RouterHostedByL3Agent(
|
||||
raise l3agentscheduler.RouterHostedByL3Agent(
|
||||
router_id=router_id, agent_id=id)
|
||||
except exc.NoResultFound:
|
||||
pass
|
||||
@ -197,7 +125,7 @@ class AgentSchedulerDbMixin(agentscheduler.AgentSchedulerPluginBase,
|
||||
agent_db.host,
|
||||
router_id)
|
||||
if not result:
|
||||
raise agentscheduler.RouterSchedulingFailed(
|
||||
raise l3agentscheduler.RouterSchedulingFailed(
|
||||
router_id=router_id, agent_id=id)
|
||||
|
||||
if self.l3_agent_notifier:
|
||||
@ -220,7 +148,7 @@ class AgentSchedulerDbMixin(agentscheduler.AgentSchedulerPluginBase,
|
||||
try:
|
||||
binding = query.one()
|
||||
except exc.NoResultFound:
|
||||
raise agentscheduler.RouterNotHostedByL3Agent(
|
||||
raise l3agentscheduler.RouterNotHostedByL3Agent(
|
||||
router_id=router_id, agent_id=id)
|
||||
context.session.delete(binding)
|
||||
if self.l3_agent_notifier:
|
||||
@ -305,18 +233,6 @@ class AgentSchedulerDbMixin(agentscheduler.AgentSchedulerPluginBase,
|
||||
else:
|
||||
return {'agents': []}
|
||||
|
||||
def schedule_network(self, context, created_network):
|
||||
if self.network_scheduler:
|
||||
chosen_agent = self.network_scheduler.schedule(
|
||||
self, context, created_network)
|
||||
if not chosen_agent:
|
||||
LOG.warn(_('Fail scheduling network %s'), created_network)
|
||||
return chosen_agent
|
||||
|
||||
def auto_schedule_networks(self, context, host):
|
||||
if self.network_scheduler:
|
||||
self.network_scheduler.auto_schedule_networks(self, context, host)
|
||||
|
||||
def get_l3_agents(self, context, active=None, filters=None):
|
||||
query = context.session.query(agents_db.Agent)
|
||||
query = query.filter(
|
||||
@ -372,21 +288,118 @@ class AgentSchedulerDbMixin(agentscheduler.AgentSchedulerPluginBase,
|
||||
for router in routers:
|
||||
self.schedule_router(context, router)
|
||||
|
||||
def update_agent(self, context, id, agent):
|
||||
original_agent = self.get_agent(context, id)
|
||||
result = super(AgentSchedulerDbMixin, self).update_agent(
|
||||
context, id, agent)
|
||||
agent_data = agent['agent']
|
||||
if ('admin_state_up' in agent_data and
|
||||
original_agent['admin_state_up'] != agent_data['admin_state_up']):
|
||||
if (original_agent['agent_type'] == constants.AGENT_TYPE_DHCP and
|
||||
self.dhcp_agent_notifier):
|
||||
self.dhcp_agent_notifier.agent_updated(
|
||||
context, agent_data['admin_state_up'],
|
||||
original_agent['host'])
|
||||
elif (original_agent['agent_type'] == constants.AGENT_TYPE_L3 and
|
||||
self.l3_agent_notifier):
|
||||
self.l3_agent_notifier.agent_updated(
|
||||
context, agent_data['admin_state_up'],
|
||||
original_agent['host'])
|
||||
return result
|
||||
|
||||
class DhcpAgentSchedulerDbMixin(dhcpagentscheduler
|
||||
.DhcpAgentSchedulerPluginBase,
|
||||
AgentSchedulerDbMixin):
|
||||
"""Mixin class to add DHCP agent scheduler extension to db_plugin_base_v2.
|
||||
"""
|
||||
|
||||
network_scheduler = None
|
||||
|
||||
def get_dhcp_agents_hosting_networks(
|
||||
self, context, network_ids, active=None):
|
||||
if not network_ids:
|
||||
return []
|
||||
query = context.session.query(NetworkDhcpAgentBinding)
|
||||
query = query.options(joinedload('dhcp_agent'))
|
||||
if len(network_ids) == 1:
|
||||
query = query.filter(
|
||||
NetworkDhcpAgentBinding.network_id == network_ids[0])
|
||||
elif network_ids:
|
||||
query = query.filter(
|
||||
NetworkDhcpAgentBinding.network_id in network_ids)
|
||||
if active is not None:
|
||||
query = (query.filter(agents_db.Agent.admin_state_up == active))
|
||||
|
||||
return [binding.dhcp_agent
|
||||
for binding in query
|
||||
if AgentSchedulerDbMixin.is_eligible_agent(active,
|
||||
binding.dhcp_agent)]
|
||||
|
||||
def add_network_to_dhcp_agent(self, context, id, network_id):
|
||||
self._get_network(context, network_id)
|
||||
with context.session.begin(subtransactions=True):
|
||||
agent_db = self._get_agent(context, id)
|
||||
if (agent_db['agent_type'] != constants.AGENT_TYPE_DHCP or
|
||||
not agent_db['admin_state_up']):
|
||||
raise dhcpagentscheduler.InvalidDHCPAgent(id=id)
|
||||
dhcp_agents = self.get_dhcp_agents_hosting_networks(
|
||||
context, [network_id])
|
||||
for dhcp_agent in dhcp_agents:
|
||||
if id == dhcp_agent.id:
|
||||
raise dhcpagentscheduler.NetworkHostedByDHCPAgent(
|
||||
network_id=network_id, agent_id=id)
|
||||
binding = NetworkDhcpAgentBinding()
|
||||
binding.dhcp_agent_id = id
|
||||
binding.network_id = network_id
|
||||
context.session.add(binding)
|
||||
if self.dhcp_agent_notifier:
|
||||
self.dhcp_agent_notifier.network_added_to_agent(
|
||||
context, network_id, agent_db.host)
|
||||
|
||||
def remove_network_from_dhcp_agent(self, context, id, network_id):
|
||||
agent = self._get_agent(context, id)
|
||||
with context.session.begin(subtransactions=True):
|
||||
try:
|
||||
query = context.session.query(NetworkDhcpAgentBinding)
|
||||
binding = query.filter(
|
||||
NetworkDhcpAgentBinding.network_id == network_id,
|
||||
NetworkDhcpAgentBinding.dhcp_agent_id == id).one()
|
||||
except exc.NoResultFound:
|
||||
raise dhcpagentscheduler.NetworkNotHostedByDhcpAgent(
|
||||
network_id=network_id, agent_id=id)
|
||||
context.session.delete(binding)
|
||||
if self.dhcp_agent_notifier:
|
||||
self.dhcp_agent_notifier.network_removed_from_agent(
|
||||
context, network_id, agent.host)
|
||||
|
||||
def list_networks_on_dhcp_agent(self, context, id):
|
||||
query = context.session.query(NetworkDhcpAgentBinding.network_id)
|
||||
query = query.filter(NetworkDhcpAgentBinding.dhcp_agent_id == id)
|
||||
|
||||
net_ids = [item[0] for item in query]
|
||||
if net_ids:
|
||||
return {'networks':
|
||||
self.get_networks(context, filters={'id': net_ids})}
|
||||
else:
|
||||
return {'networks': []}
|
||||
|
||||
def list_active_networks_on_active_dhcp_agent(self, context, host):
|
||||
agent = self._get_agent_by_type_and_host(
|
||||
context, constants.AGENT_TYPE_DHCP, host)
|
||||
if not agent.admin_state_up:
|
||||
return []
|
||||
query = context.session.query(NetworkDhcpAgentBinding.network_id)
|
||||
query = query.filter(NetworkDhcpAgentBinding.dhcp_agent_id == agent.id)
|
||||
|
||||
net_ids = [item[0] for item in query]
|
||||
if net_ids:
|
||||
return self.get_networks(
|
||||
context,
|
||||
filters={'id': net_ids, 'admin_state_up': [True]}
|
||||
)
|
||||
else:
|
||||
return []
|
||||
|
||||
def list_dhcp_agents_hosting_network(self, context, network_id):
|
||||
dhcp_agents = self.get_dhcp_agents_hosting_networks(
|
||||
context, [network_id])
|
||||
agent_ids = [dhcp_agent.id for dhcp_agent in dhcp_agents]
|
||||
if agent_ids:
|
||||
return {
|
||||
'agents': self.get_agents(context, filters={'id': agent_ids})}
|
||||
else:
|
||||
return {'agents': []}
|
||||
|
||||
def schedule_network(self, context, created_network):
|
||||
if self.network_scheduler:
|
||||
chosen_agent = self.network_scheduler.schedule(
|
||||
self, context, created_network)
|
||||
if not chosen_agent:
|
||||
LOG.warn(_('Fail scheduling network %s'), created_network)
|
||||
return chosen_agent
|
||||
|
||||
def auto_schedule_networks(self, context, host):
|
||||
if self.network_scheduler:
|
||||
self.network_scheduler.auto_schedule_networks(self, context, host)
|
||||
|
@ -35,7 +35,7 @@ class DhcpRpcCallbackMixin(object):
|
||||
LOG.debug(_('Network list requested from %s'), host)
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
if utils.is_extension_supported(
|
||||
plugin, constants.AGENT_SCHEDULER_EXT_ALIAS):
|
||||
plugin, constants.DHCP_AGENT_SCHEDULER_EXT_ALIAS):
|
||||
if cfg.CONF.network_auto_schedule:
|
||||
plugin.auto_schedule_networks(context, host)
|
||||
nets = plugin.list_active_networks_on_active_dhcp_agent(
|
||||
|
@ -42,7 +42,7 @@ class L3RpcCallbackMixin(object):
|
||||
context = neutron_context.get_admin_context()
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
if utils.is_extension_supported(
|
||||
plugin, constants.AGENT_SCHEDULER_EXT_ALIAS):
|
||||
plugin, constants.L3_AGENT_SCHEDULER_EXT_ALIAS):
|
||||
if cfg.CONF.router_auto_schedule:
|
||||
plugin.auto_schedule_routers(context, host, router_id)
|
||||
routers = plugin.list_active_sync_routers_on_active_l3_agent(
|
||||
|
154
neutron/extensions/dhcpagentscheduler.py
Normal file
154
neutron/extensions/dhcpagentscheduler.py
Normal file
@ -0,0 +1,154 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright (c) 2013 OpenStack Foundation.
|
||||
# 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 abc import abstractmethod
|
||||
|
||||
from neutron.api import extensions
|
||||
from neutron.api.v2 import base
|
||||
from neutron.api.v2 import resource
|
||||
from neutron.common import constants
|
||||
from neutron.common import exceptions
|
||||
from neutron.extensions import agent
|
||||
from neutron import manager
|
||||
from neutron import policy
|
||||
from neutron import wsgi
|
||||
|
||||
DHCP_NET = 'dhcp-network'
|
||||
DHCP_NETS = DHCP_NET + 's'
|
||||
DHCP_AGENT = 'dhcp-agent'
|
||||
DHCP_AGENTS = DHCP_AGENT + 's'
|
||||
|
||||
|
||||
class NetworkSchedulerController(wsgi.Controller):
|
||||
def index(self, request, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
policy.enforce(request.context,
|
||||
"get_%s" % DHCP_NETS,
|
||||
{})
|
||||
return plugin.list_networks_on_dhcp_agent(
|
||||
request.context, kwargs['agent_id'])
|
||||
|
||||
def create(self, request, body, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
policy.enforce(request.context,
|
||||
"create_%s" % DHCP_NET,
|
||||
{})
|
||||
return plugin.add_network_to_dhcp_agent(
|
||||
request.context, kwargs['agent_id'], body['network_id'])
|
||||
|
||||
def delete(self, request, id, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
policy.enforce(request.context,
|
||||
"delete_%s" % DHCP_NET,
|
||||
{})
|
||||
return plugin.remove_network_from_dhcp_agent(
|
||||
request.context, kwargs['agent_id'], id)
|
||||
|
||||
|
||||
class DhcpAgentsHostingNetworkController(wsgi.Controller):
|
||||
def index(self, request, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
policy.enforce(request.context,
|
||||
"get_%s" % DHCP_AGENTS,
|
||||
{})
|
||||
return plugin.list_dhcp_agents_hosting_network(
|
||||
request.context, kwargs['network_id'])
|
||||
|
||||
|
||||
class Dhcpagentscheduler(extensions.ExtensionDescriptor):
|
||||
"""Extension class supporting dhcp agent scheduler.
|
||||
"""
|
||||
|
||||
@classmethod
|
||||
def get_name(cls):
|
||||
return "DHCP Agent Scheduler"
|
||||
|
||||
@classmethod
|
||||
def get_alias(cls):
|
||||
return constants.DHCP_AGENT_SCHEDULER_EXT_ALIAS
|
||||
|
||||
@classmethod
|
||||
def get_description(cls):
|
||||
return "Schedule networks among dhcp agents"
|
||||
|
||||
@classmethod
|
||||
def get_namespace(cls):
|
||||
return "http://docs.openstack.org/ext/dhcp_agent_scheduler/api/v1.0"
|
||||
|
||||
@classmethod
|
||||
def get_updated(cls):
|
||||
return "2013-02-07T10:00:00-00:00"
|
||||
|
||||
@classmethod
|
||||
def get_resources(cls):
|
||||
"""Returns Ext Resources."""
|
||||
exts = []
|
||||
parent = dict(member_name="agent",
|
||||
collection_name="agents")
|
||||
controller = resource.Resource(NetworkSchedulerController(),
|
||||
base.FAULT_MAP)
|
||||
exts.append(extensions.ResourceExtension(
|
||||
DHCP_NETS, controller, parent))
|
||||
|
||||
parent = dict(member_name="network",
|
||||
collection_name="networks")
|
||||
|
||||
controller = resource.Resource(DhcpAgentsHostingNetworkController(),
|
||||
base.FAULT_MAP)
|
||||
exts.append(extensions.ResourceExtension(
|
||||
DHCP_AGENTS, controller, parent))
|
||||
return exts
|
||||
|
||||
def get_extended_resources(self, version):
|
||||
return {}
|
||||
|
||||
|
||||
class InvalidDHCPAgent(agent.AgentNotFound):
|
||||
message = _("Agent %(id)s is not a valid DHCP Agent or has been disabled")
|
||||
|
||||
|
||||
class NetworkHostedByDHCPAgent(exceptions.Conflict):
|
||||
message = _("The network %(network_id)s has been already hosted"
|
||||
" by the DHCP Agent %(agent_id)s.")
|
||||
|
||||
|
||||
class NetworkNotHostedByDhcpAgent(exceptions.Conflict):
|
||||
message = _("The network %(network_id)s is not hosted"
|
||||
" by the DHCP agent %(agent_id)s.")
|
||||
|
||||
|
||||
class DhcpAgentSchedulerPluginBase(object):
|
||||
"""REST API to operate the DHCP agent scheduler.
|
||||
|
||||
All of method must be in an admin context.
|
||||
"""
|
||||
|
||||
@abstractmethod
|
||||
def add_network_to_dhcp_agent(self, context, id, network_id):
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def remove_network_from_dhcp_agent(self, context, id, network_id):
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def list_networks_on_dhcp_agent(self, context, id):
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def list_dhcp_agents_hosting_network(self, context, network_id):
|
||||
pass
|
@ -27,42 +27,12 @@ from neutron import manager
|
||||
from neutron import policy
|
||||
from neutron import wsgi
|
||||
|
||||
DHCP_NET = 'dhcp-network'
|
||||
DHCP_NETS = DHCP_NET + 's'
|
||||
DHCP_AGENT = 'dhcp-agent'
|
||||
DHCP_AGENTS = DHCP_AGENT + 's'
|
||||
L3_ROUTER = 'l3-router'
|
||||
L3_ROUTERS = L3_ROUTER + 's'
|
||||
L3_AGENT = 'l3-agent'
|
||||
L3_AGENTS = L3_AGENT + 's'
|
||||
|
||||
|
||||
class NetworkSchedulerController(wsgi.Controller):
|
||||
def index(self, request, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
policy.enforce(request.context,
|
||||
"get_%s" % DHCP_NETS,
|
||||
{})
|
||||
return plugin.list_networks_on_dhcp_agent(
|
||||
request.context, kwargs['agent_id'])
|
||||
|
||||
def create(self, request, body, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
policy.enforce(request.context,
|
||||
"create_%s" % DHCP_NET,
|
||||
{})
|
||||
return plugin.add_network_to_dhcp_agent(
|
||||
request.context, kwargs['agent_id'], body['network_id'])
|
||||
|
||||
def delete(self, request, id, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
policy.enforce(request.context,
|
||||
"delete_%s" % DHCP_NET,
|
||||
{})
|
||||
return plugin.remove_network_from_dhcp_agent(
|
||||
request.context, kwargs['agent_id'], id)
|
||||
|
||||
|
||||
class RouterSchedulerController(wsgi.Controller):
|
||||
def index(self, request, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
@ -91,16 +61,6 @@ class RouterSchedulerController(wsgi.Controller):
|
||||
request.context, kwargs['agent_id'], id)
|
||||
|
||||
|
||||
class DhcpAgentsHostingNetworkController(wsgi.Controller):
|
||||
def index(self, request, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
policy.enforce(request.context,
|
||||
"get_%s" % DHCP_AGENTS,
|
||||
{})
|
||||
return plugin.list_dhcp_agents_hosting_network(
|
||||
request.context, kwargs['network_id'])
|
||||
|
||||
|
||||
class L3AgentsHostingRouterController(wsgi.Controller):
|
||||
def index(self, request, **kwargs):
|
||||
plugin = manager.NeutronManager.get_plugin()
|
||||
@ -111,29 +71,29 @@ class L3AgentsHostingRouterController(wsgi.Controller):
|
||||
request.context, kwargs['router_id'])
|
||||
|
||||
|
||||
class Agentscheduler(extensions.ExtensionDescriptor):
|
||||
"""Extension class supporting agent scheduler.
|
||||
class L3agentscheduler(extensions.ExtensionDescriptor):
|
||||
"""Extension class supporting l3 agent scheduler.
|
||||
"""
|
||||
|
||||
@classmethod
|
||||
def get_name(cls):
|
||||
return "Agent Schedulers"
|
||||
return "L3 Agent Scheduler"
|
||||
|
||||
@classmethod
|
||||
def get_alias(cls):
|
||||
return constants.AGENT_SCHEDULER_EXT_ALIAS
|
||||
return constants.L3_AGENT_SCHEDULER_EXT_ALIAS
|
||||
|
||||
@classmethod
|
||||
def get_description(cls):
|
||||
return "Schedule resources among agents"
|
||||
return "Schedule routers among l3 agents"
|
||||
|
||||
@classmethod
|
||||
def get_namespace(cls):
|
||||
return "http://docs.openstack.org/ext/agent_scheduler/api/v1.0"
|
||||
return "http://docs.openstack.org/ext/l3_agent_scheduler/api/v1.0"
|
||||
|
||||
@classmethod
|
||||
def get_updated(cls):
|
||||
return "2013-02-03T10:00:00-00:00"
|
||||
return "2013-02-07T10:00:00-00:00"
|
||||
|
||||
@classmethod
|
||||
def get_resources(cls):
|
||||
@ -141,24 +101,12 @@ class Agentscheduler(extensions.ExtensionDescriptor):
|
||||
exts = []
|
||||
parent = dict(member_name="agent",
|
||||
collection_name="agents")
|
||||
controller = resource.Resource(NetworkSchedulerController(),
|
||||
base.FAULT_MAP)
|
||||
exts.append(extensions.ResourceExtension(
|
||||
DHCP_NETS, controller, parent))
|
||||
|
||||
controller = resource.Resource(RouterSchedulerController(),
|
||||
base.FAULT_MAP)
|
||||
exts.append(extensions.ResourceExtension(
|
||||
L3_ROUTERS, controller, parent))
|
||||
|
||||
parent = dict(member_name="network",
|
||||
collection_name="networks")
|
||||
|
||||
controller = resource.Resource(DhcpAgentsHostingNetworkController(),
|
||||
base.FAULT_MAP)
|
||||
exts.append(extensions.ResourceExtension(
|
||||
DHCP_AGENTS, controller, parent))
|
||||
|
||||
parent = dict(member_name="router",
|
||||
collection_name="routers")
|
||||
|
||||
@ -172,20 +120,6 @@ class Agentscheduler(extensions.ExtensionDescriptor):
|
||||
return {}
|
||||
|
||||
|
||||
class InvalidDHCPAgent(agent.AgentNotFound):
|
||||
message = _("Agent %(id)s is not a valid DHCP Agent or has been disabled")
|
||||
|
||||
|
||||
class NetworkHostedByDHCPAgent(exceptions.Conflict):
|
||||
message = _("The network %(network_id)s has been already hosted"
|
||||
" by the DHCP Agent %(agent_id)s.")
|
||||
|
||||
|
||||
class NetworkNotHostedByDhcpAgent(exceptions.Conflict):
|
||||
message = _("The network %(network_id)s is not hosted"
|
||||
" by the DHCP agent %(agent_id)s.")
|
||||
|
||||
|
||||
class InvalidL3Agent(agent.AgentNotFound):
|
||||
message = _("Agent %(id)s is not a L3 Agent or has been disabled")
|
||||
|
||||
@ -205,28 +139,12 @@ class RouterNotHostedByL3Agent(exceptions.Conflict):
|
||||
" by L3 agent %(agent_id)s.")
|
||||
|
||||
|
||||
class AgentSchedulerPluginBase(object):
|
||||
"""REST API to operate the agent scheduler.
|
||||
class L3AgentSchedulerPluginBase(object):
|
||||
"""REST API to operate the l3 agent scheduler.
|
||||
|
||||
All of method must be in an admin context.
|
||||
"""
|
||||
|
||||
@abstractmethod
|
||||
def add_network_to_dhcp_agent(self, context, id, network_id):
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def remove_network_from_dhcp_agent(self, context, id, network_id):
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def list_networks_on_dhcp_agent(self, context, id):
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def list_dhcp_agents_hosting_network(self, context, network_id):
|
||||
pass
|
||||
|
||||
@abstractmethod
|
||||
def add_router_to_l3_agent(self, context, id, router_id):
|
||||
pass
|
@ -197,7 +197,8 @@ class AgentNotifierApi(proxy.RpcProxy,
|
||||
class BrocadePluginV2(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
extraroute_db.ExtraRoute_db_mixin,
|
||||
sg_db_rpc.SecurityGroupServerRpcMixin,
|
||||
agentschedulers_db.AgentSchedulerDbMixin):
|
||||
agentschedulers_db.L3AgentSchedulerDbMixin,
|
||||
agentschedulers_db.DhcpAgentSchedulerDbMixin):
|
||||
"""BrocadePluginV2 is a Neutron plugin.
|
||||
|
||||
Provides L2 Virtual Network functionality using VDX. Upper
|
||||
@ -213,7 +214,8 @@ class BrocadePluginV2(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
|
||||
self.supported_extension_aliases = ["binding", "security-group",
|
||||
"router", "extraroute",
|
||||
"agent", "agent_scheduler"]
|
||||
"agent", "l3_agent_scheduler",
|
||||
"dhcp_agent_scheduler"]
|
||||
|
||||
self.physical_interface = (cfg.CONF.PHYSICAL_INTERFACE.
|
||||
physical_interface)
|
||||
|
@ -188,7 +188,8 @@ class LinuxBridgePluginV2(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
extraroute_db.ExtraRoute_db_mixin,
|
||||
l3_gwmode_db.L3_NAT_db_mixin,
|
||||
sg_db_rpc.SecurityGroupServerRpcMixin,
|
||||
agentschedulers_db.AgentSchedulerDbMixin,
|
||||
agentschedulers_db.L3AgentSchedulerDbMixin,
|
||||
agentschedulers_db.DhcpAgentSchedulerDbMixin,
|
||||
portbindings_db.PortBindingMixin):
|
||||
"""Implement the Neutron abstractions using Linux bridging.
|
||||
|
||||
@ -215,7 +216,9 @@ class LinuxBridgePluginV2(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
|
||||
_supported_extension_aliases = ["provider", "router", "ext-gw-mode",
|
||||
"binding", "quotas", "security-group",
|
||||
"agent", "extraroute", "agent_scheduler"]
|
||||
"agent", "extraroute",
|
||||
"l3_agent_scheduler",
|
||||
"dhcp_agent_scheduler"]
|
||||
|
||||
@property
|
||||
def supported_extension_aliases(self):
|
||||
|
@ -49,7 +49,8 @@ TYPE_MULTI_SEGMENT = 'multi-segment'
|
||||
class Ml2Plugin(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
extraroute_db.ExtraRoute_db_mixin,
|
||||
sg_db_rpc.SecurityGroupServerRpcMixin,
|
||||
agentschedulers_db.AgentSchedulerDbMixin,
|
||||
agentschedulers_db.L3AgentSchedulerDbMixin,
|
||||
agentschedulers_db.DhcpAgentSchedulerDbMixin,
|
||||
portbindings_db.PortBindingMixin):
|
||||
"""Implement the Neutron L2 abstractions using modules.
|
||||
|
||||
@ -70,7 +71,8 @@ class Ml2Plugin(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
# List of supported extensions
|
||||
_supported_extension_aliases = ["provider", "router", "extraroute",
|
||||
"binding", "quotas", "security-group",
|
||||
"agent", "agent_scheduler"]
|
||||
"agent", "l3_agent_scheduler",
|
||||
"dhcp_agent_scheduler"]
|
||||
|
||||
@property
|
||||
def supported_extension_aliases(self):
|
||||
|
@ -64,7 +64,8 @@ class NECPluginV2(nec_plugin_base.NECPluginV2Base,
|
||||
extraroute_db.ExtraRoute_db_mixin,
|
||||
l3_gwmode_db.L3_NAT_db_mixin,
|
||||
sg_db_rpc.SecurityGroupServerRpcMixin,
|
||||
agentschedulers_db.AgentSchedulerDbMixin):
|
||||
agentschedulers_db.L3AgentSchedulerDbMixin,
|
||||
agentschedulers_db.DhcpAgentSchedulerDbMixin):
|
||||
"""NECPluginV2 controls an OpenFlow Controller.
|
||||
|
||||
The Neutron NECPluginV2 maps L2 logical networks to L2 virtualized networks
|
||||
@ -79,7 +80,9 @@ class NECPluginV2(nec_plugin_base.NECPluginV2Base,
|
||||
"""
|
||||
_supported_extension_aliases = ["router", "ext-gw-mode", "quotas",
|
||||
"binding", "security-group",
|
||||
"extraroute", "agent", "agent_scheduler"]
|
||||
"extraroute", "agent",
|
||||
"l3_agent_scheduler",
|
||||
"dhcp_agent_scheduler"]
|
||||
|
||||
@property
|
||||
def supported_extension_aliases(self):
|
||||
|
@ -132,7 +132,7 @@ class NvpPluginV2(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
qos_db.NVPQoSDbMixin,
|
||||
nvp_sec.NVPSecurityGroups,
|
||||
nvp_meta.NvpMetadataAccess,
|
||||
agentschedulers_db.AgentSchedulerDbMixin):
|
||||
agentschedulers_db.DhcpAgentSchedulerDbMixin):
|
||||
"""L2 Virtual network plugin.
|
||||
|
||||
NvpPluginV2 is a Neutron plugin that provides L2 Virtual Network
|
||||
|
@ -218,7 +218,8 @@ class OVSNeutronPluginV2(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
extraroute_db.ExtraRoute_db_mixin,
|
||||
l3_gwmode_db.L3_NAT_db_mixin,
|
||||
sg_db_rpc.SecurityGroupServerRpcMixin,
|
||||
agentschedulers_db.AgentSchedulerDbMixin,
|
||||
agentschedulers_db.L3AgentSchedulerDbMixin,
|
||||
agentschedulers_db.DhcpAgentSchedulerDbMixin,
|
||||
portbindings_db.PortBindingMixin):
|
||||
|
||||
"""Implement the Neutron abstractions using Open vSwitch.
|
||||
@ -247,7 +248,9 @@ class OVSNeutronPluginV2(db_base_plugin_v2.NeutronDbPluginV2,
|
||||
|
||||
_supported_extension_aliases = ["provider", "router", "ext-gw-mode",
|
||||
"binding", "quotas", "security-group",
|
||||
"agent", "extraroute", "agent_scheduler"]
|
||||
"agent", "extraroute",
|
||||
"l3_agent_scheduler",
|
||||
"dhcp_agent_scheduler"]
|
||||
|
||||
@property
|
||||
def supported_extension_aliases(self):
|
||||
|
@ -29,7 +29,8 @@ from neutron.db import agents_db
|
||||
from neutron.db import dhcp_rpc_base
|
||||
from neutron.db import l3_rpc_base
|
||||
from neutron.extensions import agent
|
||||
from neutron.extensions import agentscheduler
|
||||
from neutron.extensions import dhcpagentscheduler
|
||||
from neutron.extensions import l3agentscheduler
|
||||
from neutron import manager
|
||||
from neutron.openstack.common import timeutils
|
||||
from neutron.openstack.common import uuidutils
|
||||
@ -89,7 +90,7 @@ class AgentSchedulerTestMixIn(object):
|
||||
expected_code=exc.HTTPOk.code,
|
||||
admin_context=True):
|
||||
path = "/agents/%s/%s.%s" % (agent_id,
|
||||
agentscheduler.L3_ROUTERS,
|
||||
l3agentscheduler.L3_ROUTERS,
|
||||
self.fmt)
|
||||
return self._request_list(path, expected_code=expected_code,
|
||||
admin_context=admin_context)
|
||||
@ -98,7 +99,7 @@ class AgentSchedulerTestMixIn(object):
|
||||
expected_code=exc.HTTPOk.code,
|
||||
admin_context=True):
|
||||
path = "/agents/%s/%s.%s" % (agent_id,
|
||||
agentscheduler.DHCP_NETS,
|
||||
dhcpagentscheduler.DHCP_NETS,
|
||||
self.fmt)
|
||||
return self._request_list(path, expected_code=expected_code,
|
||||
admin_context=admin_context)
|
||||
@ -107,7 +108,7 @@ class AgentSchedulerTestMixIn(object):
|
||||
expected_code=exc.HTTPOk.code,
|
||||
admin_context=True):
|
||||
path = "/routers/%s/%s.%s" % (router_id,
|
||||
agentscheduler.L3_AGENTS,
|
||||
l3agentscheduler.L3_AGENTS,
|
||||
self.fmt)
|
||||
return self._request_list(path, expected_code=expected_code,
|
||||
admin_context=admin_context)
|
||||
@ -116,7 +117,7 @@ class AgentSchedulerTestMixIn(object):
|
||||
expected_code=exc.HTTPOk.code,
|
||||
admin_context=True):
|
||||
path = "/networks/%s/%s.%s" % (network_id,
|
||||
agentscheduler.DHCP_AGENTS,
|
||||
dhcpagentscheduler.DHCP_AGENTS,
|
||||
self.fmt)
|
||||
return self._request_list(path, expected_code=expected_code,
|
||||
admin_context=admin_context)
|
||||
@ -125,7 +126,7 @@ class AgentSchedulerTestMixIn(object):
|
||||
expected_code=exc.HTTPCreated.code,
|
||||
admin_context=True):
|
||||
path = "/agents/%s/%s.%s" % (id,
|
||||
agentscheduler.L3_ROUTERS,
|
||||
l3agentscheduler.L3_ROUTERS,
|
||||
self.fmt)
|
||||
req = self._path_create_request(path,
|
||||
{'router_id': router_id},
|
||||
@ -137,7 +138,7 @@ class AgentSchedulerTestMixIn(object):
|
||||
expected_code=exc.HTTPCreated.code,
|
||||
admin_context=True):
|
||||
path = "/agents/%s/%s.%s" % (id,
|
||||
agentscheduler.DHCP_NETS,
|
||||
dhcpagentscheduler.DHCP_NETS,
|
||||
self.fmt)
|
||||
req = self._path_create_request(path,
|
||||
{'network_id': network_id},
|
||||
@ -149,7 +150,7 @@ class AgentSchedulerTestMixIn(object):
|
||||
expected_code=exc.HTTPNoContent.code,
|
||||
admin_context=True):
|
||||
path = "/agents/%s/%s/%s.%s" % (id,
|
||||
agentscheduler.DHCP_NETS,
|
||||
dhcpagentscheduler.DHCP_NETS,
|
||||
network_id,
|
||||
self.fmt)
|
||||
req = self._path_delete_request(path,
|
||||
@ -161,7 +162,7 @@ class AgentSchedulerTestMixIn(object):
|
||||
expected_code=exc.HTTPNoContent.code,
|
||||
admin_context=True):
|
||||
path = "/agents/%s/%s/%s.%s" % (id,
|
||||
agentscheduler.L3_ROUTERS,
|
||||
l3agentscheduler.L3_ROUTERS,
|
||||
router_id,
|
||||
self.fmt)
|
||||
req = self._path_delete_request(path, admin_context=admin_context)
|
||||
|
Loading…
Reference in New Issue
Block a user