diff --git a/neutron/db/l3_hamode_db.py b/neutron/db/l3_hamode_db.py index 8553d00c598..96647d8b1c9 100644 --- a/neutron/db/l3_hamode_db.py +++ b/neutron/db/l3_hamode_db.py @@ -262,13 +262,13 @@ class L3_HA_NAT_db_mixin(l3_dvr_db.L3_NAT_with_dvr_db_mixin): """ min_agents = cfg.CONF.min_l3_agents_per_router - num_agents = len(self.get_l3_agents(context, + num_agents = len(self.get_l3_agents(context, active=True, filters={'agent_modes': [constants.L3_AGENT_MODE_LEGACY, constants.L3_AGENT_MODE_DVR_SNAT]})) max_agents = cfg.CONF.max_l3_agents_per_router if max_agents: if max_agents > num_agents: - LOG.info(_LI("Number of available agents lower than " + LOG.info(_LI("Number of active agents lower than " "max_l3_agents_per_router. L3 agents " "available: %s"), num_agents) else: diff --git a/neutron/tests/unit/db/test_l3_hamode_db.py b/neutron/tests/unit/db/test_l3_hamode_db.py index e13991aa0e0..bd8f9e9cd44 100644 --- a/neutron/tests/unit/db/test_l3_hamode_db.py +++ b/neutron/tests/unit/db/test_l3_hamode_db.py @@ -12,8 +12,10 @@ # License for the specific language governing permissions and limitations # under the License. +import datetime import mock from oslo_config import cfg +from oslo_utils import timeutils from neutron.api.v2 import attributes from neutron.common import constants @@ -52,22 +54,28 @@ class L3HATestFramework(testlib_api.SqlTestCase): cfg.CONF.set_override('allow_overlapping_ips', True) self.plugin = FakeL3PluginWithAgents() - self._register_agents() + self.agent1 = self._register_agent('legacy', 'l3host') + self.agent2 = self._register_agent('dvr_snat', 'l3host_2') - def _register_agents(self): + def _register_agent(self, agent_mode, host): agent_status = { 'agent_type': constants.AGENT_TYPE_L3, 'binary': 'neutron-l3-agent', - 'host': 'l3host', + 'host': host, 'topic': 'N/A', - 'configurations': {'agent_mode': 'legacy'} + 'configurations': {'agent_mode': agent_mode} } self.plugin.create_or_update_agent(self.admin_ctx, agent_status) - agent_status['host'] = 'l3host_2' - agent_status['configurations'] = {'agent_mode': 'dvr_snat'} - self.plugin.create_or_update_agent(self.admin_ctx, agent_status) - self.agent1, self.agent2 = self.plugin.get_agents(self.admin_ctx) + return self.plugin.get_agents( + self.admin_ctx, filters={'host': [host]})[0] + + def _bring_down_agent(self, agent_id): + update = { + 'agent': { + 'heartbeat_timestamp': + timeutils.utcnow() - datetime.timedelta(hours=1)}} + self.plugin.update_agent(self.admin_ctx, agent_id, update) def _create_router(self, ha=True, tenant_id='tenant1', distributed=None, ctx=None): @@ -478,6 +486,14 @@ class L3HATestCase(L3HATestFramework): self.admin_ctx) self.assertEqual(2, num_ha_candidates) + def test_get_number_of_agents_for_scheduling_not_enough_agents(self): + cfg.CONF.set_override('min_l3_agents_per_router', 3) + agent_to_bring_down = self._register_agent('legacy', 'l3host_3') + self._bring_down_agent(agent_to_bring_down['id']) + self.assertRaises(l3_ext_ha_mode.HANotEnoughAvailableAgents, + self.plugin.get_number_of_agents_for_scheduling, + self.admin_ctx) + class L3HAModeDbTestCase(L3HATestFramework): diff --git a/neutron/tests/unit/scheduler/test_l3_agent_scheduler.py b/neutron/tests/unit/scheduler/test_l3_agent_scheduler.py index 09e3f708021..f7ee3d766fe 100644 --- a/neutron/tests/unit/scheduler/test_l3_agent_scheduler.py +++ b/neutron/tests/unit/scheduler/test_l3_agent_scheduler.py @@ -1641,10 +1641,10 @@ class L3HAChanceSchedulerTestCase(L3HATestCaseMixin): admin_state_up=True) self.assertEqual(2, len(agents)) + r2 = self._create_ha_router() self._set_l3_agent_admin_state(self.adminContext, self.agent_id2, False) - r2 = self._create_ha_router() self.plugin.schedule_router(self.adminContext, r2['id']) agents = self.plugin.get_l3_agents_hosting_routers( self.adminContext, [r2['id']],