Merge "Fix processing pool statuses for LBs with multiple listeners"
This commit is contained in:
commit
05c933a19c
|
@ -195,16 +195,16 @@ class UpdateHealthDb(object):
|
||||||
|
|
||||||
# Process pools bound to listeners
|
# Process pools bound to listeners
|
||||||
for db_pool in db_listener.pools:
|
for db_pool in db_listener.pools:
|
||||||
lb_status, processed_pools = self._process_pool_status(
|
lb_status = self._process_pool_status(
|
||||||
session, db_pool, pools, lb_status)
|
session, db_pool, pools, lb_status, processed_pools)
|
||||||
|
|
||||||
# Process pools bound to the load balancer
|
# Process pools bound to the load balancer
|
||||||
for db_pool in db_lb.pools:
|
for db_pool in db_lb.pools:
|
||||||
# Don't re-process pools shared with listeners
|
# Don't re-process pools shared with listeners
|
||||||
if db_pool.id in processed_pools:
|
if db_pool.id in processed_pools:
|
||||||
continue
|
continue
|
||||||
lb_status, processed_pools = self._process_pool_status(
|
lb_status = self._process_pool_status(
|
||||||
session, db_pool, pools, lb_status)
|
session, db_pool, [], lb_status, processed_pools)
|
||||||
|
|
||||||
# Update the load balancer status last
|
# Update the load balancer status last
|
||||||
try:
|
try:
|
||||||
|
@ -216,12 +216,11 @@ class UpdateHealthDb(object):
|
||||||
except sqlalchemy.orm.exc.NoResultFound:
|
except sqlalchemy.orm.exc.NoResultFound:
|
||||||
LOG.error("Load balancer %s is not in DB", db_lb.id)
|
LOG.error("Load balancer %s is not in DB", db_lb.id)
|
||||||
|
|
||||||
def _process_pool_status(self, session, db_pool, pools, lb_status):
|
def _process_pool_status(self, session, db_pool, pools, lb_status,
|
||||||
|
processed_pools):
|
||||||
pool_status = None
|
pool_status = None
|
||||||
pool_id = db_pool.id
|
pool_id = db_pool.id
|
||||||
|
|
||||||
processed_pools = []
|
|
||||||
|
|
||||||
if pool_id not in pools:
|
if pool_id not in pools:
|
||||||
pool_status = constants.OFFLINE
|
pool_status = constants.OFFLINE
|
||||||
else:
|
else:
|
||||||
|
@ -301,7 +300,7 @@ class UpdateHealthDb(object):
|
||||||
except sqlalchemy.orm.exc.NoResultFound:
|
except sqlalchemy.orm.exc.NoResultFound:
|
||||||
LOG.error("Pool %s is not in DB", pool_id)
|
LOG.error("Pool %s is not in DB", pool_id)
|
||||||
|
|
||||||
return lb_status, processed_pools
|
return lb_status
|
||||||
|
|
||||||
|
|
||||||
class UpdateStatsDb(stats.StatsMixin):
|
class UpdateStatsDb(stats.StatsMixin):
|
||||||
|
|
|
@ -238,25 +238,18 @@ class TestUpdateHealthDb(base.TestCase):
|
||||||
self.hm.update_health(health)
|
self.hm.update_health(health)
|
||||||
self.assertTrue(not self.amphora_health_repo.replace.called)
|
self.assertTrue(not self.amphora_health_repo.replace.called)
|
||||||
|
|
||||||
def test_update_lb_pool_health_online(self):
|
def test_update_lb_pool_health_offline(self):
|
||||||
|
|
||||||
health = {
|
health = {
|
||||||
"id": self.FAKE_UUID_1,
|
"id": self.FAKE_UUID_1,
|
||||||
"listeners": {
|
"listeners": {
|
||||||
"listener-id-1": {"status": constants.OPEN, "pools": {
|
"listener-id-1": {"status": constants.OPEN, "pools": {}}
|
||||||
"pool-id-1": {"status": constants.UP,
|
|
||||||
"members": {"member-id-1": constants.UP}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
"recv_time": time.time()
|
"recv_time": time.time()
|
||||||
}
|
}
|
||||||
|
|
||||||
mock_lb, mock_listener1, mock_pool1, mock_member1 = (
|
mock_lb, mock_listener1, mock_pool1, mock_member1 = (
|
||||||
self._make_mock_lb_tree())
|
self._make_mock_lb_tree())
|
||||||
# I'm not sure why we were testing this, but we were -- leaving it
|
|
||||||
mock_listener1.pools = []
|
|
||||||
|
|
||||||
self.amphora_repo.get_all_lbs_on_amphora.return_value = [mock_lb]
|
self.amphora_repo.get_all_lbs_on_amphora.return_value = [mock_lb]
|
||||||
self.hm.update_health(health)
|
self.hm.update_health(health)
|
||||||
|
@ -269,19 +262,61 @@ class TestUpdateHealthDb(base.TestCase):
|
||||||
self.listener_repo.update.assert_any_call(
|
self.listener_repo.update.assert_any_call(
|
||||||
self.session_mock, listener_id,
|
self.session_mock, listener_id,
|
||||||
operating_status=constants.ONLINE)
|
operating_status=constants.ONLINE)
|
||||||
|
self.pool_repo.update.assert_any_call(
|
||||||
|
self.session_mock, mock_pool1.id,
|
||||||
|
operating_status=constants.OFFLINE
|
||||||
|
)
|
||||||
|
|
||||||
for pool_id, pool in six.iteritems(listener.get('pools', {})):
|
def test_update_lb_multiple_listeners_one_error_pool(self):
|
||||||
|
health = {
|
||||||
|
"id": self.FAKE_UUID_1,
|
||||||
|
"listeners": {
|
||||||
|
"listener-id-1": {"status": constants.OPEN, "pools": {
|
||||||
|
"pool-id-1": {"status": constants.DOWN,
|
||||||
|
"members": {"member-id-1": constants.ERROR}}
|
||||||
|
}},
|
||||||
|
"listener-id-2": {"status": constants.OPEN, "pools": {
|
||||||
|
"pool-id-2": {"status": constants.UP,
|
||||||
|
"members": {"member-id-2": constants.UP}}
|
||||||
|
}}
|
||||||
|
},
|
||||||
|
"recv_time": time.time()
|
||||||
|
}
|
||||||
|
|
||||||
# We should not double process a shared pool
|
mock_lb, mock_listener1, mock_pool1, mock_member1 = (
|
||||||
self.hm.pool_repo.update.assert_called_once_with(
|
self._make_mock_lb_tree())
|
||||||
self.session_mock, pool_id,
|
|
||||||
operating_status=constants.ONLINE)
|
|
||||||
|
|
||||||
for member_id, member in six.iteritems(
|
mock_member2 = mock.Mock()
|
||||||
pool.get('members', {})):
|
mock_member2.id = 'member-id-2'
|
||||||
self.member_repo.update.assert_any_call(
|
mock_pool2 = mock.Mock()
|
||||||
self.session_mock, member_id,
|
mock_pool2.id = "pool-id-2"
|
||||||
operating_status=constants.ONLINE)
|
mock_pool2.members = [mock_member2]
|
||||||
|
mock_listener2 = mock.Mock()
|
||||||
|
mock_listener2.id = 'listener-id-2'
|
||||||
|
mock_listener2.pools = [mock_pool2]
|
||||||
|
|
||||||
|
mock_lb.listeners.append(mock_listener2)
|
||||||
|
mock_lb.pools.append(mock_pool2)
|
||||||
|
|
||||||
|
self.amphora_repo.get_all_lbs_on_amphora.return_value = [mock_lb]
|
||||||
|
self.hm.update_health(health)
|
||||||
|
self.assertTrue(self.amphora_health_repo.replace.called)
|
||||||
|
|
||||||
|
# test listener, member
|
||||||
|
for listener_id, listener in six.iteritems(
|
||||||
|
health.get('listeners')):
|
||||||
|
self.listener_repo.update.assert_any_call(
|
||||||
|
self.session_mock, listener_id,
|
||||||
|
operating_status=constants.ONLINE)
|
||||||
|
|
||||||
|
# Call count should be exactly 2, as each pool should be processed once
|
||||||
|
self.assertEqual(2, self.pool_repo.update.call_count)
|
||||||
|
self.pool_repo.update.assert_has_calls([
|
||||||
|
mock.call(self.session_mock, mock_pool1.id,
|
||||||
|
operating_status=constants.ERROR),
|
||||||
|
mock.call(self.session_mock, mock_pool2.id,
|
||||||
|
operating_status=constants.ONLINE)
|
||||||
|
])
|
||||||
|
|
||||||
def test_update_lb_and_list_pool_health_online(self):
|
def test_update_lb_and_list_pool_health_online(self):
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue