Merge "Check gateways if non-default node groups are used"
This commit is contained in:
commit
ee1492c306
|
@ -498,6 +498,54 @@ class NetworkCheck(object):
|
|||
"errors": ["gateway"]})
|
||||
self.expose_error_messages()
|
||||
|
||||
def _get_net_range_for_ip(self, ip, net):
|
||||
"""Returns the first network's IP range that contains given IP."""
|
||||
if net.get('ip_ranges'):
|
||||
for r in net['ip_ranges']:
|
||||
ipr = netaddr.IPRange(r[0], r[1])
|
||||
if ip in ipr:
|
||||
return ipr
|
||||
|
||||
def neutron_check_gateways(self):
|
||||
"""Check that gateways are set if non-default node groups are used."""
|
||||
if objects.NodeGroupCollection.get_by_cluster_id(
|
||||
self.cluster.id).count() < 2:
|
||||
return
|
||||
for net in self.networks:
|
||||
if net['meta']['notation'] in (
|
||||
consts.NETWORK_NOTATION.cidr,
|
||||
consts.NETWORK_NOTATION.ip_ranges):
|
||||
cidr = netaddr.IPNetwork(net['cidr'])
|
||||
if net['gateway'] is not None:
|
||||
gw = netaddr.IPAddress(net['gateway'])
|
||||
# broadcast and net address intersection is checked by
|
||||
# check_network_addresses_not_match_subnet_and_broadcast
|
||||
if gw in cidr:
|
||||
ip_range = self._get_net_range_for_ip(gw, net)
|
||||
if ip_range is not None:
|
||||
self.err_msgs.append(
|
||||
u"Gateway address belongs to the network's "
|
||||
u"IP range [{0}].".format(ip_range)
|
||||
)
|
||||
self.result.append(
|
||||
{"ids": [net['id']], "errors": ["gateway"]}
|
||||
)
|
||||
else:
|
||||
self.err_msgs.append(
|
||||
u"Gateway address does not belong to the network."
|
||||
)
|
||||
self.result.append(
|
||||
{"ids": [net['id']], "errors": ["gateway"]}
|
||||
)
|
||||
else:
|
||||
self.err_msgs.append(
|
||||
u"Gateway is not set for network."
|
||||
)
|
||||
self.result.append(
|
||||
{"ids": [net['id']], "errors": ["gateway"]}
|
||||
)
|
||||
self.expose_error_messages()
|
||||
|
||||
def check_network_classes_exclude_loopback(self):
|
||||
"""Check if address space is in real world addresses space
|
||||
|
||||
|
@ -623,6 +671,7 @@ class NetworkCheck(object):
|
|||
self.neutron_check_network_address_spaces_intersection()
|
||||
self.neutron_check_segmentation_ids()
|
||||
self.neutron_check_l3_addresses_not_match_subnet_and_broadcast()
|
||||
self.neutron_check_gateways()
|
||||
else:
|
||||
self.check_public_floating_ranges_intersection()
|
||||
self.check_network_address_spaces_intersection()
|
||||
|
|
|
@ -1179,10 +1179,14 @@ class TestNeutronOrchestratorSerializer61(OrchestratorSerializerTestBase):
|
|||
if net['name'] in nets_w_gw.keys():
|
||||
if net['group_id'] == group_id:
|
||||
net['cidr'] = nets_w_gw[net['name']]
|
||||
net['ip_ranges'] = [[
|
||||
str(IPAddress(IPNetwork(net['cidr']).first + 2)),
|
||||
str(IPAddress(IPNetwork(net['cidr']).first + 253)),
|
||||
]]
|
||||
# IP ranges for networks in default nodegroup must
|
||||
# be updated as well to exclude gateway address.
|
||||
# Use first 126 addresses to avoid clashing
|
||||
# with floating range.
|
||||
net['ip_ranges'] = [[
|
||||
str(IPAddress(IPNetwork(net['cidr']).first + 2)),
|
||||
str(IPAddress(IPNetwork(net['cidr']).first + 127)),
|
||||
]]
|
||||
net['gateway'] = str(
|
||||
IPAddress(IPNetwork(net['cidr']).first + 1))
|
||||
resp = self.env.neutron_networks_put(cluster.id, nets)
|
||||
|
|
|
@ -488,3 +488,64 @@ class TestNetworkCheck(BaseIntegrationTest):
|
|||
checker.check_interface_mapping()
|
||||
mock_untagged.assert_called_with()
|
||||
mock_bond.assert_called_with()
|
||||
|
||||
@patch.object(helpers, 'db')
|
||||
@patch('objects.NodeGroupCollection.get_by_cluster_id')
|
||||
def test_neutron_check_gateways_valid(self, get_by_cluster_id_mock,
|
||||
mocked_db):
|
||||
checker = NetworkCheck(self.task, {})
|
||||
checker.networks = [{'id': 1,
|
||||
'cidr': '192.168.0.0/24',
|
||||
'gateway': '192.168.0.1',
|
||||
'meta': {'notation': consts.NETWORK_NOTATION.cidr}
|
||||
}]
|
||||
nodegroup_mock = MagicMock(**{'count.return_value': 2})
|
||||
get_by_cluster_id_mock.return_value = nodegroup_mock
|
||||
self.assertNotRaises(errors.NetworkCheckError,
|
||||
checker.neutron_check_gateways)
|
||||
|
||||
@patch.object(helpers, 'db')
|
||||
@patch('objects.NodeGroupCollection.get_by_cluster_id')
|
||||
def test_neutron_check_gateways_gw_none(self, get_by_cluster_id_mock,
|
||||
mocked_db):
|
||||
checker = NetworkCheck(self.task, {})
|
||||
checker.networks = [{'id': 1,
|
||||
'cidr': '192.168.0.0/24',
|
||||
'gateway': None,
|
||||
'meta': {'notation': consts.NETWORK_NOTATION.cidr}
|
||||
}]
|
||||
nodegroup_mock = MagicMock(**{'count.return_value': 2})
|
||||
get_by_cluster_id_mock.return_value = nodegroup_mock
|
||||
self.assertRaises(errors.NetworkCheckError,
|
||||
checker.neutron_check_gateways)
|
||||
|
||||
@patch.object(helpers, 'db')
|
||||
@patch('objects.NodeGroupCollection.get_by_cluster_id')
|
||||
def test_neutron_check_gateways_gw_outside(self, get_by_cluster_id_mock,
|
||||
mocked_db):
|
||||
checker = NetworkCheck(self.task, {})
|
||||
checker.networks = [{'id': 1,
|
||||
'cidr': '192.168.0.0/24',
|
||||
'gateway': '192.168.1.1',
|
||||
'meta': {'notation': consts.NETWORK_NOTATION.cidr}
|
||||
}]
|
||||
nodegroup_mock = MagicMock(**{'count.return_value': 2})
|
||||
get_by_cluster_id_mock.return_value = nodegroup_mock
|
||||
self.assertRaises(errors.NetworkCheckError,
|
||||
checker.neutron_check_gateways)
|
||||
|
||||
@patch.object(helpers, 'db')
|
||||
@patch('objects.NodeGroupCollection.get_by_cluster_id')
|
||||
def test_neutron_check_gateways_gw_in_range(self, get_by_cluster_id_mock,
|
||||
mocked_db):
|
||||
checker = NetworkCheck(self.task, {})
|
||||
checker.networks = [{'id': 1,
|
||||
'cidr': '192.168.0.0/24',
|
||||
'gateway': '192.168.0.75',
|
||||
'ip_ranges': [('192.168.0.50', '192.168.0.100')],
|
||||
'meta': {'notation': consts.NETWORK_NOTATION.cidr}
|
||||
}]
|
||||
nodegroup_mock = MagicMock(**{'count.return_value': 2})
|
||||
get_by_cluster_id_mock.return_value = nodegroup_mock
|
||||
self.assertRaises(errors.NetworkCheckError,
|
||||
checker.neutron_check_gateways)
|
||||
|
|
Loading…
Reference in New Issue