diff --git a/charmhelpers/contrib/openstack/ip.py b/charmhelpers/contrib/openstack/ip.py index b8c94c56..2afad369 100644 --- a/charmhelpers/contrib/openstack/ip.py +++ b/charmhelpers/contrib/openstack/ip.py @@ -25,6 +25,7 @@ from charmhelpers.contrib.network.ip import ( is_ipv6, get_ipv6_addr, resolve_network_cidr, + get_iface_for_address ) from charmhelpers.contrib.hahelpers.cluster import is_clustered @@ -145,6 +146,30 @@ def local_address(unit_get_fallback='public-address'): return unit_get(unit_get_fallback) +def get_invalid_vips(): + """Check if any of the provided vips are invalid. + A vip is invalid if it doesn't belong to the subnet in any interface. + If all vips are valid, this returns an empty list. + + :returns: A list of strings, where each string is an invalid vip address. + :rtype: list + """ + + clustered = is_clustered() + vips = config('vip') + if vips: + vips = vips.split() + invalid_vips = [] + + if clustered and vips: + for vip in vips: + iface_for_vip = get_iface_for_address(vip) + if iface_for_vip is None: + invalid_vips.append(vip) + + return invalid_vips + + def resolve_address(endpoint_type=PUBLIC, override=True): """Return unit address depending on net config. diff --git a/hooks/keystone_utils.py b/hooks/keystone_utils.py index 69ee2771..56b50d5b 100644 --- a/hooks/keystone_utils.py +++ b/hooks/keystone_utils.py @@ -43,6 +43,7 @@ from charmhelpers.contrib.network.ip import ( ) from charmhelpers.contrib.openstack.ip import ( + get_invalid_vips, resolve_address, PUBLIC, INTERNAL, @@ -2516,6 +2517,12 @@ def check_extra_for_assess_status(configs): return ('blocked', 'hacluster missing configuration: ' 'vip, vip_iface, vip_cidr') + + # Check if any of the vips are invalid + invalid_vips = get_invalid_vips() + if invalid_vips: + return('blocked', f'Invalid vips: {invalid_vips}') + # verify that the config item, if set, is actually usable and valid conf = config('password-security-compliance') if (conf and (keystone_context.KeystoneContext