diff --git a/octavia/common/jinja/haproxy/combined_listeners/jinja_cfg.py b/octavia/common/jinja/haproxy/combined_listeners/jinja_cfg.py index 6bcb6d90fc..a46da715c6 100644 --- a/octavia/common/jinja/haproxy/combined_listeners/jinja_cfg.py +++ b/octavia/common/jinja/haproxy/combined_listeners/jinja_cfg.py @@ -294,6 +294,8 @@ class JinjaTemplater(object): pools.append(self._transform_pool( pool, feature_compatibility, **kwargs)) ret_value['pools'] = pools + policy_gen = (policy for policy in listener.l7policies if + policy.provisioning_status != constants.PENDING_DELETE) if listener.default_pool: for pool in pools: if pool['id'] == listener.default_pool.id: @@ -302,7 +304,7 @@ class JinjaTemplater(object): l7policies = [self._transform_l7policy( x, feature_compatibility, tls_certs) - for x in listener.l7policies] + for x in policy_gen] ret_value['l7policies'] = l7policies return ret_value @@ -329,12 +331,16 @@ class JinjaTemplater(object): 'crl_path': '', 'tls_enabled': pool.tls_enabled } + members_gen = (mem for mem in pool.members if + mem.provisioning_status != constants.PENDING_DELETE) members = [self._transform_member(x, feature_compatibility) - for x in pool.members] + for x in members_gen] ret_value['members'] = members - if pool.health_monitor: + health_mon = pool.health_monitor + if (health_mon and + health_mon.provisioning_status != constants.PENDING_DELETE): ret_value['health_monitor'] = self._transform_health_monitor( - pool.health_monitor, feature_compatibility) + health_mon, feature_compatibility) if pool.session_persistence: ret_value[ 'session_persistence'] = self._transform_session_persistence( @@ -418,7 +424,9 @@ class JinjaTemplater(object): 'redirect_prefix': l7policy.redirect_prefix, 'enabled': l7policy.enabled } - if l7policy.redirect_pool: + if (l7policy.redirect_pool and + l7policy.redirect_pool.provisioning_status != + constants.PENDING_DELETE): kwargs = {} if tls_certs is not None and tls_certs.get( l7policy.redirect_pool.id): @@ -434,8 +442,10 @@ class JinjaTemplater(object): ret_value['redirect_http_code'] = l7policy.redirect_http_code else: ret_value['redirect_http_code'] = None + rule_gen = (rule for rule in l7policy.l7rules if rule.enabled and + rule.provisioning_status != constants.PENDING_DELETE) l7rules = [self._transform_l7rule(x, feature_compatibility) - for x in l7policy.l7rules if x.enabled] + for x in rule_gen] ret_value['l7rules'] = l7rules return ret_value diff --git a/octavia/common/jinja/haproxy/split_listeners/jinja_cfg.py b/octavia/common/jinja/haproxy/split_listeners/jinja_cfg.py index 29effdd027..2e57be7016 100644 --- a/octavia/common/jinja/haproxy/split_listeners/jinja_cfg.py +++ b/octavia/common/jinja/haproxy/split_listeners/jinja_cfg.py @@ -271,7 +271,9 @@ class JinjaTemplater(object): ret_value['client_crl_path'] = '%s' % ( os.path.join(self.base_crt_dir, listener.id, client_crl)) - if listener.default_pool: + if (listener.default_pool and + listener.default_pool.provisioning_status != + constants.PENDING_DELETE): kwargs = {} if pool_tls_certs and pool_tls_certs.get(listener.default_pool.id): kwargs = {'pool_tls_certs': pool_tls_certs.get( @@ -279,16 +281,20 @@ class JinjaTemplater(object): ret_value['default_pool'] = self._transform_pool( listener.default_pool, feature_compatibility, **kwargs) pools = [] - for x in listener.pools: + pool_gen = (pool for pool in listener.pools if + pool.provisioning_status != constants.PENDING_DELETE) + for x in pool_gen: kwargs = {} if pool_tls_certs and pool_tls_certs.get(x.id): kwargs = {'pool_tls_certs': pool_tls_certs.get(x.id)} pools.append(self._transform_pool( x, feature_compatibility, **kwargs)) ret_value['pools'] = pools + policy_gen = (policy for policy in listener.l7policies if + policy.provisioning_status != constants.PENDING_DELETE) l7policies = [self._transform_l7policy( x, feature_compatibility, pool_tls_certs) - for x in listener.l7policies] + for x in policy_gen] ret_value['l7policies'] = l7policies return ret_value @@ -314,12 +320,16 @@ class JinjaTemplater(object): 'crl_path': '', 'tls_enabled': pool.tls_enabled } + members_gen = (mem for mem in pool.members if + mem.provisioning_status != constants.PENDING_DELETE) members = [self._transform_member(x, feature_compatibility) - for x in pool.members] + for x in members_gen] ret_value['members'] = members - if pool.health_monitor: + health_mon = pool.health_monitor + if (health_mon and + health_mon.provisioning_status != constants.PENDING_DELETE): ret_value['health_monitor'] = self._transform_health_monitor( - pool.health_monitor, feature_compatibility) + health_mon, feature_compatibility) if pool.session_persistence: ret_value[ 'session_persistence'] = self._transform_session_persistence( @@ -403,7 +413,9 @@ class JinjaTemplater(object): 'redirect_prefix': l7policy.redirect_prefix, 'enabled': l7policy.enabled } - if l7policy.redirect_pool: + if (l7policy.redirect_pool and + l7policy.redirect_pool.provisioning_status != + constants.PENDING_DELETE): kwargs = {} if pool_tls_certs and pool_tls_certs.get( l7policy.redirect_pool.id): @@ -419,8 +431,10 @@ class JinjaTemplater(object): ret_value['redirect_http_code'] = l7policy.redirect_http_code else: ret_value['redirect_http_code'] = None + rule_gen = (rule for rule in l7policy.l7rules if rule.enabled and + rule.provisioning_status != constants.PENDING_DELETE) l7rules = [self._transform_l7rule(x, feature_compatibility) - for x in l7policy.l7rules if x.enabled] + for x in rule_gen] ret_value['l7rules'] = l7rules return ret_value diff --git a/octavia/common/jinja/lvs/jinja_cfg.py b/octavia/common/jinja/lvs/jinja_cfg.py index 6632404a30..c9dc14df9f 100644 --- a/octavia/common/jinja/lvs/jinja_cfg.py +++ b/octavia/common/jinja/lvs/jinja_cfg.py @@ -120,7 +120,9 @@ class LvsJinjaTemplater(object): } if listener.connection_limit and listener.connection_limit > -1: ret_value['connection_limit'] = listener.connection_limit - if listener.default_pool: + if (listener.default_pool and + listener.default_pool.provisioning_status != + constants.PENDING_DELETE): ret_value['default_pool'] = self._transform_pool( listener.default_pool) return ret_value @@ -140,9 +142,13 @@ class LvsJinjaTemplater(object): 'session_persistence': '', 'enabled': pool.enabled } - members = [self._transform_member(x) for x in pool.members] + members_gen = (mem for mem in pool.members if + mem.provisioning_status != constants.PENDING_DELETE) + members = [self._transform_member(x) for x in members_gen] ret_value['members'] = members - if pool.health_monitor: + if (pool.health_monitor and + pool.health_monitor.provisioning_status != + constants.PENDING_DELETE): ret_value['health_monitor'] = self._transform_health_monitor( pool.health_monitor) if pool.session_persistence: diff --git a/octavia/tests/unit/common/sample_configs/sample_configs_combined.py b/octavia/tests/unit/common/sample_configs/sample_configs_combined.py index 3694ccc349..6d111277ec 100644 --- a/octavia/tests/unit/common/sample_configs/sample_configs_combined.py +++ b/octavia/tests/unit/common/sample_configs/sample_configs_combined.py @@ -601,6 +601,7 @@ def sample_listener_tuple(proto=None, monitor=True, alloc_default_pool=True, pool_ca_cert=False, pool_crl=False, tls_enabled=False, hm_host_http_check=False, id='sample_listener_id_1', recursive_nest=False, + provisioning_status=constants.ACTIVE, sample_default_pool=1, pool_enabled=True): proto = 'HTTP' if proto is None else proto @@ -619,7 +620,7 @@ def sample_listener_tuple(proto=None, monitor=True, alloc_default_pool=True, 'timeout_member_connect, timeout_member_data, ' 'timeout_tcp_inspect, client_ca_tls_certificate_id, ' 'client_ca_tls_certificate, client_authentication, ' - 'client_crl_container_id') + 'client_crl_container_id, provisioning_status') if l7: pools = [ sample_pool_tuple( @@ -734,6 +735,7 @@ def sample_listener_tuple(proto=None, monitor=True, alloc_default_pool=True, constants.CLIENT_AUTH_MANDATORY if client_ca_cert else constants.CLIENT_AUTH_NONE), client_crl_container_id='cont_id_crl' if client_crl_cert else '', + provisioning_status=provisioning_status, ) if recursive_nest: listener.load_balancer.listeners.append(listener) @@ -828,17 +830,19 @@ def sample_pool_tuple(listener_id=None, proto=None, monitor=True, tls_certificate_id='pool_cont_1' if pool_cert else None, ca_tls_certificate_id='pool_ca_1' if pool_ca_cert else None, crl_container_id='pool_crl' if pool_crl else None, - tls_enabled=tls_enabled, provisioning_status=constants.ACTIVE) + tls_enabled=tls_enabled, + provisioning_status=provisioning_status) def sample_member_tuple(id, ip, enabled=True, operating_status='ACTIVE', + provisioning_status=constants.ACTIVE, monitor_ip_port=False, backup=False): in_member = collections.namedtuple('member', 'id, ip_address, protocol_port, ' 'weight, subnet_id, ' 'enabled, operating_status, ' 'monitor_address, monitor_port, ' - 'backup') + 'backup, provisioning_status') monitor_address = '192.168.1.1' if monitor_ip_port else None monitor_port = 9000 if monitor_ip_port else None return in_member( @@ -851,7 +855,7 @@ def sample_member_tuple(id, ip, enabled=True, operating_status='ACTIVE', operating_status=operating_status, monitor_address=monitor_address, monitor_port=monitor_port, - backup=backup) + backup=backup, provisioning_status=provisioning_status) def sample_session_persistence_tuple(persistence_type=None, @@ -870,12 +874,14 @@ def sample_session_persistence_tuple(persistence_type=None, def sample_health_monitor_tuple(proto='HTTP', sample_hm=1, - host_http_check=False): + host_http_check=False, + provisioning_status=constants.ACTIVE): proto = 'HTTP' if proto is 'TERMINATED_HTTPS' else proto monitor = collections.namedtuple( 'monitor', 'id, type, delay, timeout, fall_threshold, rise_threshold,' 'http_method, url_path, expected_codes, enabled, ' - 'check_script_path, http_version, domain_name') + 'check_script_path, http_version, domain_name, ' + 'provisioning_status') if sample_hm == 1: id = 'sample_monitor_id_1' @@ -893,7 +899,8 @@ def sample_health_monitor_tuple(proto='HTTP', sample_hm=1, 'http_method': 'GET', 'url_path': url_path, 'expected_codes': '418', - 'enabled': True + 'enabled': True, + 'provisioning_status': provisioning_status, } if host_http_check: kwargs.update({'http_version': 1.1, 'domain_name': 'testlab.com'}) @@ -912,12 +919,14 @@ def sample_l7policy_tuple(id, redirect_pool=None, redirect_url=None, redirect_prefix=None, enabled=True, redirect_http_code=302, - sample_policy=1): + sample_policy=1, + provisioning_status=constants.ACTIVE): in_l7policy = collections.namedtuple('l7policy', 'id, action, redirect_pool, ' 'redirect_url, redirect_prefix, ' 'l7rules, enabled,' - 'redirect_http_code') + 'redirect_http_code,' + 'provisioning_status') l7rules = [] if sample_policy == 1: action = constants.L7POLICY_ACTION_REDIRECT_TO_POOL @@ -965,7 +974,8 @@ def sample_l7policy_tuple(id, redirect_http_code=redirect_http_code if (action in [constants.L7POLICY_ACTION_REDIRECT_TO_URL, constants.L7POLICY_ACTION_REDIRECT_PREFIX] and - redirect_http_code) else None) + redirect_http_code) else None, + provisioning_status=provisioning_status) def sample_l7rule_tuple(id, @@ -975,10 +985,12 @@ def sample_l7rule_tuple(id, value='/api', invert=False, enabled=True, - sample_rule=1): + sample_rule=1, + provisioning_status=constants.ACTIVE): in_l7rule = collections.namedtuple('l7rule', 'id, type, compare_type, ' - 'key, value, invert, enabled') + 'key, value, invert, enabled,' + 'provisioning_status') if sample_rule == 2: type = constants.L7RULE_TYPE_HEADER compare_type = constants.L7RULE_COMPARE_TYPE_CONTAINS @@ -1049,7 +1061,8 @@ def sample_l7rule_tuple(id, key=key, value=value, invert=invert, - enabled=enabled) + enabled=enabled, + provisioning_status=provisioning_status) def sample_base_expected_config(frontend=None, logging=None, backend=None, diff --git a/octavia/tests/unit/common/sample_configs/sample_configs_split.py b/octavia/tests/unit/common/sample_configs/sample_configs_split.py index 1ab198ce72..ba8013a228 100644 --- a/octavia/tests/unit/common/sample_configs/sample_configs_split.py +++ b/octavia/tests/unit/common/sample_configs/sample_configs_split.py @@ -622,7 +622,8 @@ def sample_listener_tuple(proto=None, monitor=True, alloc_default_pool=True, ssl_type_l7=False, pool_cert=False, pool_ca_cert=False, pool_crl=False, tls_enabled=False, hm_host_http_check=False, - id='sample_listener_id_1', recursive_nest=False): + id='sample_listener_id_1', recursive_nest=False, + provisioning_status=constants.ACTIVE): proto = 'HTTP' if proto is None else proto if be_proto is None: be_proto = 'HTTP' if proto is 'TERMINATED_HTTPS' else proto @@ -639,7 +640,7 @@ def sample_listener_tuple(proto=None, monitor=True, alloc_default_pool=True, 'timeout_member_connect, timeout_member_data, ' 'timeout_tcp_inspect, client_ca_tls_certificate_id, ' 'client_ca_tls_certificate, client_authentication, ' - 'client_crl_container_id') + 'client_crl_container_id, provisioning_status') if l7: pools = [ sample_pool_tuple( @@ -745,6 +746,7 @@ def sample_listener_tuple(proto=None, monitor=True, alloc_default_pool=True, constants.CLIENT_AUTH_MANDATORY if client_ca_cert else constants.CLIENT_AUTH_NONE), client_crl_container_id='cont_id_crl' if client_crl_cert else '', + provisioning_status=provisioning_status, ) if recursive_nest: listener.load_balancer.listeners.append(listener) @@ -780,14 +782,16 @@ def sample_pool_tuple(proto=None, monitor=True, persistence=True, monitor_proto=None, backup_member=False, disabled_member=False, has_http_reuse=True, pool_cert=False, pool_ca_cert=False, pool_crl=False, - tls_enabled=False, hm_host_http_check=False): + tls_enabled=False, hm_host_http_check=False, + provisioning_status=constants.ACTIVE): proto = 'HTTP' if proto is None else proto monitor_proto = proto if monitor_proto is None else monitor_proto in_pool = collections.namedtuple( 'pool', 'id, protocol, lb_algorithm, members, health_monitor, ' 'session_persistence, enabled, operating_status, ' 'tls_certificate_id, ca_tls_certificate_id, ' - 'crl_container_id, tls_enabled, ' + constants.HTTP_REUSE) + 'crl_container_id, tls_enabled, provisioning_status, ' + + constants.HTTP_REUSE) if (proto == constants.PROTOCOL_UDP and persistence_type == constants.SESSION_PERSISTENCE_SOURCE_IP): kwargs = {'persistence_type': persistence_type, @@ -830,17 +834,19 @@ def sample_pool_tuple(proto=None, monitor=True, persistence=True, tls_certificate_id='pool_cont_1' if pool_cert else None, ca_tls_certificate_id='pool_ca_1' if pool_ca_cert else None, crl_container_id='pool_crl' if pool_crl else None, - tls_enabled=tls_enabled) + tls_enabled=tls_enabled, provisioning_status=provisioning_status) -def sample_member_tuple(id, ip, enabled=True, operating_status='ACTIVE', +def sample_member_tuple(id, ip, enabled=True, + operating_status=constants.ACTIVE, + provisioning_status=constants.ACTIVE, monitor_ip_port=False, backup=False): in_member = collections.namedtuple('member', 'id, ip_address, protocol_port, ' 'weight, subnet_id, ' 'enabled, operating_status, ' 'monitor_address, monitor_port, ' - 'backup') + 'backup, provisioning_status') monitor_address = '192.168.1.1' if monitor_ip_port else None monitor_port = 9000 if monitor_ip_port else None return in_member( @@ -853,7 +859,7 @@ def sample_member_tuple(id, ip, enabled=True, operating_status='ACTIVE', operating_status=operating_status, monitor_address=monitor_address, monitor_port=monitor_port, - backup=backup) + backup=backup, provisioning_status=provisioning_status) def sample_session_persistence_tuple(persistence_type=None, @@ -872,12 +878,14 @@ def sample_session_persistence_tuple(persistence_type=None, def sample_health_monitor_tuple(proto='HTTP', sample_hm=1, - host_http_check=False): + host_http_check=False, + provisioning_status=constants.ACTIVE): proto = 'HTTP' if proto is 'TERMINATED_HTTPS' else proto monitor = collections.namedtuple( 'monitor', 'id, type, delay, timeout, fall_threshold, rise_threshold,' 'http_method, url_path, expected_codes, enabled, ' - 'check_script_path, http_version, domain_name') + 'check_script_path, http_version, domain_name, ' + 'provisioning_status') if sample_hm == 1: id = 'sample_monitor_id_1' @@ -895,7 +903,8 @@ def sample_health_monitor_tuple(proto='HTTP', sample_hm=1, 'http_method': 'GET', 'url_path': url_path, 'expected_codes': '418', - 'enabled': True + 'enabled': True, + 'provisioning_status': provisioning_status, } if host_http_check: kwargs.update({'http_version': 1.1, 'domain_name': 'testlab.com'}) @@ -914,12 +923,14 @@ def sample_l7policy_tuple(id, redirect_pool=None, redirect_url=None, redirect_prefix=None, enabled=True, redirect_http_code=302, - sample_policy=1): + sample_policy=1, + provisioning_status=constants.ACTIVE): in_l7policy = collections.namedtuple('l7policy', 'id, action, redirect_pool, ' 'redirect_url, redirect_prefix, ' 'l7rules, enabled,' - 'redirect_http_code') + 'redirect_http_code, ' + 'provisioning_status') l7rules = [] if sample_policy == 1: action = constants.L7POLICY_ACTION_REDIRECT_TO_POOL @@ -967,20 +978,20 @@ def sample_l7policy_tuple(id, redirect_http_code=redirect_http_code if (action in [constants.L7POLICY_ACTION_REDIRECT_TO_URL, constants.L7POLICY_ACTION_REDIRECT_PREFIX] and - redirect_http_code) else None) + redirect_http_code) else None, + provisioning_status=provisioning_status) def sample_l7rule_tuple(id, type=constants.L7RULE_TYPE_PATH, compare_type=constants.L7RULE_COMPARE_TYPE_STARTS_WITH, - key=None, - value='/api', - invert=False, - enabled=True, - sample_rule=1): + key=None, value='/api', + invert=False, enabled=True, + sample_rule=1, provisioning_status=constants.ACTIVE): in_l7rule = collections.namedtuple('l7rule', 'id, type, compare_type, ' - 'key, value, invert, enabled') + 'key, value, invert, enabled, ' + 'provisioning_status') if sample_rule == 2: type = constants.L7RULE_TYPE_HEADER compare_type = constants.L7RULE_COMPARE_TYPE_CONTAINS @@ -1051,7 +1062,7 @@ def sample_l7rule_tuple(id, key=key, value=value, invert=invert, - enabled=enabled) + enabled=enabled, provisioning_status=provisioning_status) def sample_base_expected_config(frontend=None, logging=None, backend=None, diff --git a/releasenotes/notes/fix-deleted-members-in-haproxy-0dcde6e3d28b100c.yaml b/releasenotes/notes/fix-deleted-members-in-haproxy-0dcde6e3d28b100c.yaml new file mode 100644 index 0000000000..5d41f10d3f --- /dev/null +++ b/releasenotes/notes/fix-deleted-members-in-haproxy-0dcde6e3d28b100c.yaml @@ -0,0 +1,6 @@ +--- +fixes: + - | + Fixed an issue when building the HAProxy configuration files, some DELETED + members could have been included in the server list after adding new + members.