UDP jinja template

This is the jinja template[1] for keepalived to enable lvs configuration.
And including some transform function from obj to rendered configuration.

These files will split with the current Octavia repo, before other parts are
ok.

Patch List:

[1] Finish keepalived LVS jinja template for UDP support
[2] Extend the ability of amp agent for upload/refresh the keepalived
process
[3] Extend the db model and db table with necessary fields for met the new udp backend
[4] Add logic/workflow elements process in UDP cases
[5] Extend the existing API to access udp parameters in Listener API
[6] Extend the existing pool API to access the new option in
session_persistence fields

Story: 1657091
Task: 23208
Change-Id: Ib23edb7190ffb777e4a95f45a253e8a632beb046
This commit is contained in:
ZhaoBo 2017-11-16 14:11:25 +08:00 committed by Michael Johnson
parent 06c6131bff
commit 008ccb652d
10 changed files with 757 additions and 15 deletions

View File

@ -0,0 +1,4 @@
#!/bin/bash
nc_cmd=`which nc`
$nc_cmd -uzv -w1 $1 $2 > /dev/null
exit $?

View File

@ -31,6 +31,7 @@ HEALTH_MONITOR_TCP = 'TCP'
HEALTH_MONITOR_HTTP = 'HTTP'
HEALTH_MONITOR_HTTPS = 'HTTPS'
HEALTH_MONITOR_TLS_HELLO = 'TLS-HELLO'
HEALTH_MONITOR_UDP_CONNECT = 'UDP-CONNECT'
SUPPORTED_HEALTH_MONITOR_TYPES = (HEALTH_MONITOR_HTTP, HEALTH_MONITOR_HTTPS,
HEALTH_MONITOR_PING, HEALTH_MONITOR_TCP,
HEALTH_MONITOR_TLS_HELLO)
@ -65,6 +66,7 @@ UPDATE_STATS = 'UPDATE_STATS'
UPDATE_HEALTH = 'UPDATE_HEALTH'
PROTOCOL_TCP = 'TCP'
PROTOCOL_UDP = 'UDP'
PROTOCOL_HTTP = 'HTTP'
PROTOCOL_HTTPS = 'HTTPS'
PROTOCOL_TERMINATED_HTTPS = 'TERMINATED_HTTPS'

View File

View File

@ -0,0 +1,199 @@
# Copyright (c) 2018 OpenStack Foundation
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
import os
import jinja2
from octavia.common.config import cfg
from octavia.common import constants
CONF = cfg.CONF
PROTOCOL_MAP = {
constants.PROTOCOL_UDP: 'udp'
}
BALANCE_MAP = {
constants.LB_ALGORITHM_ROUND_ROBIN: 'rr',
constants.LB_ALGORITHM_LEAST_CONNECTIONS: 'lc',
constants.LB_ALGORITHM_SOURCE_IP: 'sh'
}
BASE_PATH = CONF.haproxy_amphora.base_path
CHECK_SCRIPT_NAME = 'udp_check.sh'
KEEPALIVED_LVS_TEMPLATE = os.path.abspath(
os.path.join(os.path.dirname(__file__),
'templates/keepalivedlvs.cfg.j2'))
JINJA_ENV = None
class LvsJinjaTemplater(object):
def __init__(self, base_amp_path=None, keepalivedlvs_template=None):
"""Keepalived LVS configuration generation
:param base_amp_path: Base path for amphora data
:param keepalivedlvs_template: Absolute path to Jinja template
"""
self.base_amp_path = base_amp_path or BASE_PATH
self.keepalivedlvs_template = (keepalivedlvs_template or
KEEPALIVED_LVS_TEMPLATE)
def build_config(self, listener, **kwargs):
"""Convert a logical configuration to the Keepalived LVS version
:param listener: The listener configuration
:return: Rendered configuration
"""
return self.render_loadbalancer_obj(listener)
def _get_template(self):
"""Returns the specified Jinja configuration template."""
global JINJA_ENV
if not JINJA_ENV:
template_loader = jinja2.FileSystemLoader(
searchpath=os.path.dirname(self.keepalivedlvs_template))
JINJA_ENV = jinja2.Environment(
autoescape=True,
loader=template_loader,
trim_blocks=True,
lstrip_blocks=True,
extensions=['jinja2.ext.do'])
return JINJA_ENV.get_template(os.path.basename(
self.keepalivedlvs_template))
def render_loadbalancer_obj(self, listener, **kwargs):
"""Renders a templated configuration from a load balancer object
:param host_amphora: The Amphora this configuration is hosted on
:param listener: The listener configuration
:return: Rendered configuration
"""
loadbalancer = self._transform_loadbalancer(
listener.load_balancer,
listener)
return self._get_template().render(
{'loadbalancer': loadbalancer},
constants=constants)
def _transform_loadbalancer(self, loadbalancer, listener):
"""Transforms a load balancer into an object that will
be processed by the templating system
"""
t_listener = self._transform_listener(listener)
ret_value = {
'vip_address': loadbalancer.vip.ip_address,
'listener': t_listener,
'enabled': loadbalancer.enabled
}
return ret_value
def _transform_listener(self, listener):
"""Transforms a listener into an object that will
be processed by the templating system
"""
ret_value = {
'id': listener.id,
'protocol_port': listener.protocol_port,
'protocol_mode': PROTOCOL_MAP[listener.protocol],
'enabled': listener.enabled
}
if listener.connection_limit and listener.connection_limit > -1:
ret_value['connection_limit'] = listener.connection_limit
if listener.default_pool:
ret_value['default_pool'] = self._transform_pool(
listener.default_pool)
return ret_value
def _transform_pool(self, pool):
"""Transforms a pool into an object that will
be processed by the templating system
"""
ret_value = {
'id': pool.id,
'protocol': PROTOCOL_MAP[pool.protocol],
'lb_algorithm': BALANCE_MAP.get(pool.lb_algorithm,
'roundrobin'),
'members': [],
'health_monitor': '',
'session_persistence': '',
'enabled': pool.enabled
}
members = [self._transform_member(x) for x in pool.members]
ret_value['members'] = members
if pool.health_monitor:
ret_value['health_monitor'] = self._transform_health_monitor(
pool.health_monitor)
if pool.session_persistence:
func = self._transform_session_persistence
ret_value['session_persistence'] = func(
pool.session_persistence)
return ret_value
@staticmethod
def _transform_session_persistence(persistence):
"""Transforms session persistence into an object that will
be processed by the templating system
"""
return {
'type': persistence.type,
'persistence_timeout': persistence.persistence_timeout,
'persistence_granularity': persistence.persistence_granularity
}
@staticmethod
def _transform_member(member):
"""Transforms a member into an object that will
be processed by the templating system
"""
return {
'id': member.id,
'address': member.ip_address,
'protocol_port': member.protocol_port,
'weight': member.weight,
'enabled': member.enabled
}
def _get_default_lvs_check_script_path(self):
return (CONF.haproxy_amphora.base_path +
'/lvs/check/' + CHECK_SCRIPT_NAME)
def _transform_health_monitor(self, monitor):
"""Transforms a health monitor into an object that will
be processed by the templating system
"""
return {
'id': monitor.id,
'type': monitor.type,
'delay': monitor.delay,
'timeout': monitor.timeout,
'enabled': monitor.enabled,
'fall_threshold': monitor.fall_threshold,
'check_script_path': (self._get_default_lvs_check_script_path()
if monitor.type ==
constants.HEALTH_MONITOR_UDP_CONNECT else
None)
}

View File

@ -0,0 +1,20 @@
{# Copyright (c) 2018 OpenStack Foundation
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
#
#}
# Configuration for Listener {{ udp_listener_id }}
{% block global_definitions %}{% endblock global_definitions %}
{% block proxies %}{% endblock proxies %}

View File

@ -0,0 +1,28 @@
{# Copyright (c) 2018 OpenStack Foundation
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
#
#}
{% extends 'base.j2' %}
{% from 'macros.j2' import virtualserver_macro %}
{% set udp_listener_id = loadbalancer.listener.id %}
{% block global_definitions %}
net_namespace amphora-haproxy
{% endblock global_definitions %}
{% block proxies %}
{% if loadbalancer.enabled and loadbalancer.listener.enabled %}
{{- virtualserver_macro(constants, loadbalancer.listener,
loadbalancer.vip_address,
loadbalancer.listener.get('default_pool', None)) }}
{% endif %}
{% endblock proxies %}

View File

@ -0,0 +1,105 @@
{# Copyright (c) 2018 OpenStack Foundation
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
#
#}
{%- macro lb_algo_macro(pool) -%}
lb_algo {{ pool.lb_algorithm }}
{%- endmacro -%}
{% macro misc_path_macro(member, health_monitor) -%}
misc_path "{{ health_monitor.check_script_path }} {{ member.address }} {{ member.protocol_port }}"
{%- endmacro %}
{%- macro misc_check_macro(pool, member, health_monitor) -%}
MISC_CHECK {
{{ misc_path_macro(member, health_monitor) }}
misc_timeout {{ pool.health_monitor.delay }}
misc_dynamic
}
{%- endmacro -%}
{% macro health_monitor_rs_macro(constants, pool, member) %}
{% if pool.health_monitor and pool.health_monitor.enabled %}
{% if pool.health_monitor.timeout %}
delay_before_retry {{ pool.health_monitor.timeout }}
{% endif %}
{% if pool.health_monitor.fall_threshold %}
retry {{ pool.health_monitor.fall_threshold }}
{% endif %}
{% if pool.health_monitor.type == constants.HEALTH_MONITOR_UDP_CONNECT %}
{{ misc_check_macro(pool, member, pool.health_monitor) -}}
{% endif %}
{% endif %}
{% endmacro %}
{% macro realserver_macro(constants, pool, member, listener) %}
# Configuration for Member {{ member.id }}
real_server {{ member.address }} {{ member.protocol_port }} {
weight {{ member.weight }}
inhibit_on_failure
{% if listener.connection_limit %}
uthreshold {{ listener.connection_limit }}
{% endif %}
{% if pool.session_persistence and pool.session_persistence.type == constants.SESSION_PERSISTENCE_SOURCE_IP %}
persistence_timeout {{ pool.session_persistence.persistence_timeout }}
persistence_granularity {{ pool.session_persistence.persistence_granularity }}
{% endif %}
{{- health_monitor_rs_macro(constants, pool, member) }}
}
{% endmacro %}
{% macro health_monitor_vs_macro(default_pool) %}
{% if default_pool and default_pool.health_monitor and default_pool.health_monitor.enabled %}
{% if default_pool.health_monitor.delay %}
delay_loop {{ default_pool.health_monitor.delay }}
{% endif %}
{% if default_pool.health_monitor.timeout %}
delay_before_retry {{ default_pool.health_monitor.timeout }}
{% endif %}
{% if default_pool.health_monitor.fall_threshold %}
retry {{ default_pool.health_monitor.fall_threshold }}
{% endif %}
{% endif %}
{% endmacro %}
{% macro virtualserver_macro(constants, listener, lb_vip_address, default_pool) %}
{% set need_render = [] %}
{% if default_pool and default_pool.enabled and default_pool.members %}
{% for member in default_pool.members if member.enabled %}
{% do need_render.append(member.enabled) %}
{% endfor %}
{% endif %}
{% if need_render|length > 0 %}
virtual_server {{ lb_vip_address }} {{ listener.protocol_port }} {
{{ lb_algo_macro(default_pool) }}
{% if not default_pool.session_persistence %}
ops
{% endif %}
lb_kind NAT
protocol {{ listener.protocol_mode }}
{{ health_monitor_vs_macro(default_pool) }}
{% if default_pool.protocol.lower() == "udp" %}
# Configuration for Pool {{ default_pool.id }}
{% if default_pool.health_monitor and default_pool.health_monitor.enabled %}
# Configuration for HealthMonitor {{ default_pool.health_monitor.id }}
{% endif %}
{% for member in default_pool.members if member.enabled %}
{{- realserver_macro(constants, default_pool, member, listener) }}
{% endfor %}
{% endif %}
}
{% endif %}
{% endmacro %}

View File

@ -0,0 +1,270 @@
# Copyright 2018 OpenStack Foundation
# All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
from octavia.common import constants
from octavia.common.jinja.lvs import jinja_cfg
from octavia.tests.unit import base
from octavia.tests.unit.common.sample_configs import sample_configs
from oslo_config import cfg
from oslo_config import fixture as oslo_fixture
BASE_PATH = '/var/lib/octavia'
class TestLvsCfg(base.TestCase):
def setUp(self):
super(TestLvsCfg, self).setUp()
self.udp_jinja_cfg = jinja_cfg.LvsJinjaTemplater()
conf = oslo_fixture.Config(cfg.CONF)
conf.config(group="haproxy_amphora", base_path=BASE_PATH)
def test_udp_get_template(self):
template = self.udp_jinja_cfg._get_template()
self.assertEqual('keepalivedlvs.cfg.j2', template.name)
def test_render_template_udp_source_ip(self):
exp = ("# Configuration for Listener sample_listener_id_1\n\n"
"net_namespace amphora-haproxy\n\n"
"virtual_server 10.0.0.2 80 {\n"
" lb_algo rr\n"
" lb_kind NAT\n"
" protocol udp\n"
" delay_loop 30\n"
" delay_before_retry 31\n"
" retry 3\n\n\n"
" # Configuration for Pool sample_pool_id_1\n"
" # Configuration for HealthMonitor sample_monitor_id_1\n"
" # Configuration for Member sample_member_id_1\n"
" real_server 10.0.0.99 82 {\n"
" weight 13\n"
" inhibit_on_failure\n"
" uthreshold 98\n"
" persistence_timeout 33\n"
" persistence_granularity 255.255.0.0\n"
" delay_before_retry 31\n"
" retry 3\n"
" MISC_CHECK {\n"
" misc_path \"/var/lib/octavia/lvs/check/"
"udp_check.sh 10.0.0.99 82\"\n"
" misc_timeout 30\n"
" misc_dynamic\n"
" }\n"
" }\n\n"
" # Configuration for Member sample_member_id_2\n"
" real_server 10.0.0.98 82 {\n"
" weight 13\n"
" inhibit_on_failure\n"
" uthreshold 98\n"
" persistence_timeout 33\n"
" persistence_granularity 255.255.0.0\n"
" delay_before_retry 31\n"
" retry 3\n"
" MISC_CHECK {\n"
" misc_path \"/var/lib/octavia/lvs/check/"
"udp_check.sh 10.0.0.98 82\"\n"
" misc_timeout 30\n"
" misc_dynamic\n"
" }\n"
" }\n\n"
"}\n\n")
rendered_obj = self.udp_jinja_cfg.render_loadbalancer_obj(
sample_configs.sample_listener_tuple(
proto=constants.PROTOCOL_UDP,
persistence_type=constants.SESSION_PERSISTENCE_SOURCE_IP,
persistence_timeout=33,
persistence_granularity='255.255.0.0',
monitor_proto=constants.HEALTH_MONITOR_UDP_CONNECT,
connection_limit=98))
self.assertEqual(exp, rendered_obj)
def test_render_template_udp_one_packet(self):
exp = ("# Configuration for Listener sample_listener_id_1\n\n"
"net_namespace amphora-haproxy\n\n"
"virtual_server 10.0.0.2 80 {\n"
" lb_algo rr\n"
" ops\n"
" lb_kind NAT\n"
" protocol udp\n"
" delay_loop 30\n"
" delay_before_retry 31\n"
" retry 3\n\n\n"
" # Configuration for Pool sample_pool_id_1\n"
" # Configuration for HealthMonitor sample_monitor_id_1\n"
" # Configuration for Member sample_member_id_1\n"
" real_server 10.0.0.99 82 {\n"
" weight 13\n"
" inhibit_on_failure\n"
" uthreshold 98\n"
" delay_before_retry 31\n"
" retry 3\n"
" MISC_CHECK {\n"
" misc_path \"/var/lib/octavia/lvs/check/"
"udp_check.sh 10.0.0.99 82\"\n"
" misc_timeout 30\n"
" misc_dynamic\n"
" }\n"
" }\n\n"
" # Configuration for Member sample_member_id_2\n"
" real_server 10.0.0.98 82 {\n"
" weight 13\n"
" inhibit_on_failure\n"
" uthreshold 98\n"
" delay_before_retry 31\n"
" retry 3\n"
" MISC_CHECK {\n"
" misc_path \"/var/lib/octavia/lvs/check/"
"udp_check.sh 10.0.0.98 82\"\n"
" misc_timeout 30\n"
" misc_dynamic\n"
" }\n"
" }\n\n"
"}\n\n")
listener = sample_configs.sample_listener_tuple(
proto=constants.PROTOCOL_UDP,
monitor_proto=constants.HEALTH_MONITOR_UDP_CONNECT,
connection_limit=98,
persistence=False)
rendered_obj = self.udp_jinja_cfg.render_loadbalancer_obj(listener)
self.assertEqual(exp, rendered_obj)
def test_render_template_udp_with_health_monitor(self):
exp = ("# Configuration for Listener sample_listener_id_1\n\n"
"net_namespace amphora-haproxy\n\n"
"virtual_server 10.0.0.2 80 {\n"
" lb_algo rr\n"
" ops\n"
" lb_kind NAT\n"
" protocol udp\n"
" delay_loop 30\n"
" delay_before_retry 31\n"
" retry 3\n\n\n"
" # Configuration for Pool sample_pool_id_1\n"
" # Configuration for HealthMonitor sample_monitor_id_1\n"
" # Configuration for Member sample_member_id_1\n"
" real_server 10.0.0.99 82 {\n"
" weight 13\n"
" inhibit_on_failure\n"
" uthreshold 98\n"
" delay_before_retry 31\n"
" retry 3\n"
" MISC_CHECK {\n"
" misc_path \"/var/lib/octavia/lvs/check/"
"udp_check.sh 10.0.0.99 82\"\n"
" misc_timeout 30\n"
" misc_dynamic\n"
" }\n"
" }\n\n"
" # Configuration for Member sample_member_id_2\n"
" real_server 10.0.0.98 82 {\n"
" weight 13\n"
" inhibit_on_failure\n"
" uthreshold 98\n"
" delay_before_retry 31\n"
" retry 3\n"
" MISC_CHECK {\n"
" misc_path \"/var/lib/octavia/lvs/check/"
"udp_check.sh 10.0.0.98 82\"\n"
" misc_timeout 30\n"
" misc_dynamic\n"
" }\n"
" }\n\n"
"}\n\n")
rendered_obj = self.udp_jinja_cfg.render_loadbalancer_obj(
sample_configs.sample_listener_tuple(
proto=constants.PROTOCOL_UDP,
monitor_proto=constants.HEALTH_MONITOR_UDP_CONNECT,
persistence=False,
connection_limit=98))
self.assertEqual(exp, rendered_obj)
def test_render_template_udp_no_other_resources(self):
exp = ("# Configuration for Listener sample_listener_id_1\n\n"
"net_namespace amphora-haproxy\n\n\n")
rendered_obj = self.udp_jinja_cfg.render_loadbalancer_obj(
sample_configs.sample_listener_tuple(
proto=constants.PROTOCOL_UDP, monitor=False,
persistence=False, alloc_default_pool=False))
self.assertEqual(exp, rendered_obj)
def test_udp_transform_session_persistence(self):
persistence_src_ip = sample_configs.sample_session_persistence_tuple(
persistence_type=constants.SESSION_PERSISTENCE_SOURCE_IP,
persistence_cookie=None,
persistence_timeout=33,
persistence_granularity='255.0.0.0'
)
exp = sample_configs.UDP_SOURCE_IP_BODY
ret = self.udp_jinja_cfg._transform_session_persistence(
persistence_src_ip)
self.assertEqual(exp, ret)
def test_udp_transform_health_monitor(self):
in_hm = sample_configs.sample_health_monitor_tuple(
proto=constants.HEALTH_MONITOR_UDP_CONNECT
)
ret = self.udp_jinja_cfg._transform_health_monitor(in_hm)
self.assertEqual(sample_configs.RET_UDP_HEALTH_MONITOR, ret)
def test_udp_transform_member(self):
in_member = sample_configs.sample_member_tuple('member_id_1',
'192.0.2.10')
ret = self.udp_jinja_cfg._transform_member(in_member)
self.assertEqual(sample_configs.RET_UDP_MEMBER, ret)
def test_udp_transform_pool(self):
in_pool = sample_configs.sample_pool_tuple(
proto=constants.PROTOCOL_UDP,
persistence_type=constants.SESSION_PERSISTENCE_SOURCE_IP,
persistence_timeout=33, persistence_granularity='255.0.0.0',
)
ret = self.udp_jinja_cfg._transform_pool(in_pool)
self.assertEqual(sample_configs.RET_UDP_POOL, ret)
in_pool = sample_configs.sample_pool_tuple(
proto=constants.PROTOCOL_UDP,
persistence_type=constants.SESSION_PERSISTENCE_SOURCE_IP,
persistence_timeout=33, persistence_granularity='255.0.0.0',
monitor=False)
sample_configs.RET_UDP_POOL['health_monitor'] = ''
ret = self.udp_jinja_cfg._transform_pool(in_pool)
self.assertEqual(sample_configs.RET_UDP_POOL, ret)
def test_udp_transform_listener(self):
in_listener = sample_configs.sample_listener_tuple(
proto=constants.PROTOCOL_UDP,
persistence_type=constants.SESSION_PERSISTENCE_SOURCE_IP,
persistence_timeout=33,
persistence_granularity='255.0.0.0',
monitor_proto=constants.HEALTH_MONITOR_UDP_CONNECT,
connection_limit=98
)
ret = self.udp_jinja_cfg._transform_listener(in_listener)
self.assertEqual(sample_configs.RET_UDP_LISTENER, ret)
in_listener = sample_configs.sample_listener_tuple(
proto=constants.PROTOCOL_UDP,
persistence_type=constants.SESSION_PERSISTENCE_SOURCE_IP,
persistence_timeout=33,
persistence_granularity='255.0.0.0',
monitor_proto=constants.HEALTH_MONITOR_UDP_CONNECT,
connection_limit=-1)
ret = self.udp_jinja_cfg._transform_listener(in_listener)
sample_configs.RET_UDP_LISTENER.pop('connection_limit')
self.assertEqual(sample_configs.RET_UDP_LISTENER, ret)

View File

@ -15,10 +15,13 @@
import collections
from oslo_config import cfg
from octavia.common import constants
from octavia.tests.unit.common.sample_configs import sample_certs
CONF = cfg.CONF
def sample_amphora_tuple():
in_amphora = collections.namedtuple(
@ -336,6 +339,84 @@ RET_LB_L7 = {
'enabled': True,
'global_connection_limit': constants.HAPROXY_MAX_MAXCONN}
UDP_SOURCE_IP_BODY = {
'type': constants.SESSION_PERSISTENCE_SOURCE_IP,
'persistence_timeout': 33,
'persistence_granularity': '255.0.0.0'
}
RET_UDP_HEALTH_MONITOR = {
'id': 'sample_monitor_id_1',
'type': constants.HEALTH_MONITOR_UDP_CONNECT,
'delay': 30,
'timeout': 31,
'enabled': True,
'fall_threshold': 3,
'check_script_path': (CONF.haproxy_amphora.base_path +
'/lvs/check/udp_check.sh')
}
UDP_HEALTH_MONITOR_NO_SCRIPT = {
'id': 'sample_monitor_id_1',
'check_script_path': None,
'delay': 30,
'enabled': True,
'fall_threshold': 3,
'timeout': 31,
'type': 'UDP'
}
RET_UDP_MEMBER = {
'id': 'member_id_1',
'address': '192.0.2.10',
'protocol_port': 82,
'weight': 13,
'enabled': True
}
UDP_MEMBER_1 = {
'id': 'sample_member_id_1',
'address': '10.0.0.99',
'enabled': True,
'protocol_port': 82,
'weight': 13
}
UDP_MEMBER_2 = {
'id': 'sample_member_id_2',
'address': '10.0.0.98',
'enabled': True,
'protocol_port': 82,
'weight': 13
}
RET_UDP_POOL = {
'id': 'sample_pool_id_1',
'enabled': True,
'health_monitor': UDP_HEALTH_MONITOR_NO_SCRIPT,
'lb_algorithm': 'rr',
'members': [UDP_MEMBER_1, UDP_MEMBER_2],
'protocol': 'udp',
'session_persistence': UDP_SOURCE_IP_BODY
}
RET_UDP_LISTENER = {
'connection_limit': 98,
'default_pool': {
'id': 'sample_pool_id_1',
'enabled': True,
'health_monitor': RET_UDP_HEALTH_MONITOR,
'lb_algorithm': 'rr',
'members': [UDP_MEMBER_1, UDP_MEMBER_2],
'protocol': 'udp',
'session_persistence': UDP_SOURCE_IP_BODY
},
'enabled': True,
'id': 'sample_listener_id_1',
'protocol_mode': 'udp',
'protocol_port': '80'
}
def sample_loadbalancer_tuple(proto=None, monitor=True, persistence=True,
persistence_type=None, tls=False, sni=False,
@ -400,8 +481,10 @@ def sample_vip_tuple():
return vip(ip_address='10.0.0.2')
def sample_listener_tuple(proto=None, monitor=True, persistence=True,
persistence_type=None, persistence_cookie=None,
def sample_listener_tuple(proto=None, monitor=True, alloc_default_pool=True,
persistence=True, persistence_type=None,
persistence_cookie=None, persistence_timeout=None,
persistence_granularity=None,
tls=False, sni=False, peer_port=None, topology=None,
l7=False, enabled=True, insert_headers=None,
be_proto=None, monitor_ip_port=False,
@ -466,7 +549,10 @@ def sample_listener_tuple(proto=None, monitor=True, persistence=True,
proto=be_proto, monitor=monitor, persistence=persistence,
persistence_type=persistence_type,
persistence_cookie=persistence_cookie,
monitor_ip_port=monitor_ip_port, monitor_proto=monitor_proto),
persistence_timeout=persistence_timeout,
persistence_granularity=persistence_granularity,
monitor_ip_port=monitor_ip_port,
monitor_proto=monitor_proto) if alloc_default_pool else '',
connection_limit=connection_limit,
tls_certificate_id='cont_id_1' if tls else '',
sni_container_ids=['cont_id_2', 'cont_id_3'] if sni else [],
@ -527,6 +613,7 @@ def sample_tls_container_tuple(id='cont_id_1', certificate=None,
def sample_pool_tuple(proto=None, monitor=True, persistence=True,
persistence_type=None, persistence_cookie=None,
persistence_timeout=None, persistence_granularity=None,
sample_pool=1, monitor_ip_port=False,
monitor_proto=None, backup_member=False,
disabled_member=False):
@ -535,9 +622,15 @@ def sample_pool_tuple(proto=None, monitor=True, persistence=True,
in_pool = collections.namedtuple(
'pool', 'id, protocol, lb_algorithm, members, health_monitor,'
'session_persistence, enabled, operating_status')
persis = sample_session_persistence_tuple(
persistence_type=persistence_type,
persistence_cookie=persistence_cookie) if persistence is True else None
if (proto == constants.PROTOCOL_UDP and
persistence_type == constants.SESSION_PERSISTENCE_SOURCE_IP):
kwargs = {'persistence_type': persistence_type,
'persistence_timeout': persistence_timeout,
'persistence_granularity': persistence_granularity}
else:
kwargs = {'persistence_type': persistence_type,
'persistence_cookie': persistence_cookie}
persis = sample_session_persistence_tuple(**kwargs)
mon = None
if sample_pool == 1:
id = 'sample_pool_id_1'
@ -561,7 +654,7 @@ def sample_pool_tuple(proto=None, monitor=True, persistence=True,
lb_algorithm='ROUND_ROBIN',
members=members,
health_monitor=mon,
session_persistence=persis,
session_persistence=persis if persistence is True else None,
enabled=True,
operating_status='ACTIVE')
@ -590,19 +683,26 @@ def sample_member_tuple(id, ip, enabled=True, operating_status='ACTIVE',
def sample_session_persistence_tuple(persistence_type=None,
persistence_cookie=None):
persistence_cookie=None,
persistence_timeout=None,
persistence_granularity=None):
spersistence = collections.namedtuple('SessionPersistence',
'type, cookie_name')
'type, cookie_name, '
'persistence_timeout, '
'persistence_granularity')
pt = 'HTTP_COOKIE' if persistence_type is None else persistence_type
return spersistence(type=pt,
cookie_name=persistence_cookie)
cookie_name=persistence_cookie,
persistence_timeout=persistence_timeout,
persistence_granularity=persistence_granularity)
def sample_health_monitor_tuple(proto='HTTP', sample_hm=1):
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')
'http_method, url_path, expected_codes, enabled, '
'check_script_path')
if sample_hm == 1:
id = 'sample_monitor_id_1'
@ -610,10 +710,24 @@ def sample_health_monitor_tuple(proto='HTTP', sample_hm=1):
elif sample_hm == 2:
id = 'sample_monitor_id_2'
url_path = '/healthmon.html'
return monitor(id=id, type=proto, delay=30,
timeout=31, fall_threshold=3, rise_threshold=2,
http_method='GET', url_path=url_path,
expected_codes='418', enabled=True)
kwargs = {
'id': id,
'type': proto,
'delay': 30,
'timeout': 31,
'fall_threshold': 3,
'rise_threshold': 2,
'http_method': 'GET',
'url_path': url_path,
'expected_codes': '418',
'enabled': True
}
if proto == constants.HEALTH_MONITOR_UDP_CONNECT:
kwargs['check_script_path'] = (CONF.haproxy_amphora.base_path +
'lvs/check/' + 'udp_check.sh')
else:
kwargs['check_script_path'] = None
return monitor(**kwargs)
def sample_l7policy_tuple(id,