From 934e4565fe0f71589d15beac538f8da6c6e8bf6b Mon Sep 17 00:00:00 2001 From: "alessandro.ceglie" Date: Mon, 18 Oct 2021 11:15:11 +0200 Subject: [PATCH 1/4] added enviroment variable to set stats refresh timing by setting env STATS_REFRESH. --- haproxy/Readme.md | 4 ++++ haproxy/docker-entrypoint.sh | 1 + haproxy/src/configure.py | 4 +++- 3 files changed, 8 insertions(+), 1 deletion(-) diff --git a/haproxy/Readme.md b/haproxy/Readme.md index 8ca5582..4eaac52 100644 --- a/haproxy/Readme.md +++ b/haproxy/Readme.md @@ -75,6 +75,9 @@ that served the page changes, as HAProxy switches between them. The stats page can be accessed at http://localhost:1936 where you have to log in using the `STATS_AUTH` authentication details (default `admin:admin`). +You may want to set `STATS_REFRESH` option to let the statistics page auto update +i.e `STATS_REFRESH="5s"` to update every five seconds (default `0s`: no refresh) + Note that it may take **up to one minute** until backends are plugged-in due to the minimum possible `DNS_TTL`. @@ -129,6 +132,7 @@ either when running the container or in a `docker-compose.yml` file. * `STATS_PORT` The port to bind statistics to - default `1936` * `STATS_AUTH` The authentication details (written as `user:password` for the statistics page - default `admin:admin` + * `STATS_REFRESH` Refresh timing for the statistics page - default `0s` (no refresh) * `FRONTEND_NAME` The label of the frontend - default `http-frontend` * `FRONTEND_PORT` The port to bind the frontend to - default `5000` * `FRONTEND_MODE` Frontend mode - default `http` or `BACKENDS_MODE` if declared diff --git a/haproxy/docker-entrypoint.sh b/haproxy/docker-entrypoint.sh index 16b957b..c41dd1b 100755 --- a/haproxy/docker-entrypoint.sh +++ b/haproxy/docker-entrypoint.sh @@ -54,6 +54,7 @@ if ! test -e /usr/local/etc/haproxy/haproxy.cfg; then if [ -n "$SERVICE_NAMES" ]; then echo "export SERVICE_NAMES=\"$SERVICE_NAMES\"" >> /etc/environment; fi if [ -n "$STATS_AUTH" ]; then echo "export STATS_AUTH=\"$STATS_AUTH\"" >> /etc/environment; fi if [ -n "$STATS_PORT" ]; then echo "export STATS_PORT=\"$STATS_PORT\"" >> /etc/environment; fi + if [ -n "$STATS_REFRESH" ]; then echo "export STATS_REFRESH=\"$STATS_REFRESH\"" >> /etc/environment; fi if [ -n "$TIMEOUT_CLIENT" ]; then echo "export TIMEOUT_CLIENT=\"$TIMEOUT_CLIENT\"" >> /etc/environment; fi if [ -n "$TIMEOUT_CONNECT" ]; then echo "export TIMEOUT_CONNECT=\"$TIMEOUT_CONNECT\"" >> /etc/environment; fi if [ -n "$TIMEOUT_SERVER" ]; then echo "export TIMEOUT_SERVER=\"$TIMEOUT_SERVER\"" >> /etc/environment; fi diff --git a/haproxy/src/configure.py b/haproxy/src/configure.py index aec0c80..9d70290 100644 --- a/haproxy/src/configure.py +++ b/haproxy/src/configure.py @@ -20,6 +20,7 @@ PROXY_PROTOCOL_ENABLED = (os.environ.get('PROXY_PROTOCOL_ENABLED', 'false').lower() == "true") STATS_PORT = os.environ.get('STATS_PORT', '1936') STATS_AUTH = os.environ.get('STATS_AUTH', 'admin:admin') +STATS_REFRESH = os.environ.get('STATS_REFRESH', '0s') BACKENDS = os.environ.get('BACKENDS', '').split(' ') BACKENDS_PORT = os.environ.get('BACKENDS_PORT', '80') BACKENDS_MODE = os.environ.get('BACKENDS_MODE', FRONTEND_MODE) @@ -44,6 +45,7 @@ stats uri / stats hide-version stats auth $auth + stats refresh $refresh """) frontend_conf = Template(""" @@ -235,7 +237,7 @@ configuration.write( listen_conf.substitute( - port=STATS_PORT, auth=STATS_AUTH + port=STATS_PORT, auth=STATS_AUTH, refresh=STATS_REFRESH ) ) From 00387eec96577685538a964131a01c89b350b67c Mon Sep 17 00:00:00 2001 From: "alessandro.ceglie" Date: Mon, 18 Oct 2021 11:24:32 +0200 Subject: [PATCH 2/4] sanity code --- haproxy/src/configure.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/haproxy/src/configure.py b/haproxy/src/configure.py index 9d70290..666ea0c 100644 --- a/haproxy/src/configure.py +++ b/haproxy/src/configure.py @@ -237,7 +237,9 @@ configuration.write( listen_conf.substitute( - port=STATS_PORT, auth=STATS_AUTH, refresh=STATS_REFRESH + port=STATS_PORT, + auth=STATS_AUTH, + refresh=STATS_REFRESH ) ) From 9951c422e66cfcd5c1a058585111034c361426f2 Mon Sep 17 00:00:00 2001 From: "alessandro.ceglie" Date: Mon, 18 Oct 2021 16:09:30 +0200 Subject: [PATCH 3/4] added maxconn parameter --- haproxy/Readme.md | 1 + haproxy/docker-entrypoint.sh | 1 + haproxy/src/configure.py | 8 +++++--- 3 files changed, 7 insertions(+), 3 deletions(-) diff --git a/haproxy/Readme.md b/haproxy/Readme.md index 8ca5582..944302c 100644 --- a/haproxy/Readme.md +++ b/haproxy/Readme.md @@ -152,6 +152,7 @@ either when running the container or in a `docker-compose.yml` file. * `HTTPCHK` The HTTP method and uri used to check on the servers health - default `HEAD /` * `HTTPCHK_HOST` Host Header override on http Health Check - default `localhost` * `INTER` parameter sets the interval between two consecutive health checks. If not specified, the default value is `2s` + * `MAXCONN` parameter sets the maximum number of connection that each backend will accept and, by default, is set to `0` (no limit) * `FAST_INTER` parameter sets the interval between two consecutive health checks when the server is any of the transition state (read above): UP - transitionally DOWN or DOWN - transitionally UP. If not set, then `INTER` is used. * `DOWN_INTER` parameter sets the interval between two consecutive health checks when the server is in the DOWN state. If not set, then `INTER` is used. * `RISE` number of consecutive valid health checks before considering the server as UP. Default value is `2` diff --git a/haproxy/docker-entrypoint.sh b/haproxy/docker-entrypoint.sh index 16b957b..def26f8 100755 --- a/haproxy/docker-entrypoint.sh +++ b/haproxy/docker-entrypoint.sh @@ -51,6 +51,7 @@ if ! test -e /usr/local/etc/haproxy/haproxy.cfg; then if [ -n "$LOG_LEVEL" ]; then echo "export LOG_LEVEL=\"$LOG_LEVEL\"" >> /etc/environment; fi if [ -n "$PROXY_PROTOCOL_ENABLED" ]; then echo "export PROXY_PROTOCOL_ENABLED=\"$PROXY_PROTOCOL_ENABLED\"" >> /etc/environment; fi if [ -n "$RISE" ]; then echo "export RISE=\"$RISE\"" >> /etc/environment; fi + if [ -n "$MAXCONN" ]; then echo "export MAXCONN=\"$MAXCONN\"" >> /etc/environment; fi if [ -n "$SERVICE_NAMES" ]; then echo "export SERVICE_NAMES=\"$SERVICE_NAMES\"" >> /etc/environment; fi if [ -n "$STATS_AUTH" ]; then echo "export STATS_AUTH=\"$STATS_AUTH\"" >> /etc/environment; fi if [ -n "$STATS_PORT" ]; then echo "export STATS_PORT=\"$STATS_PORT\"" >> /etc/environment; fi diff --git a/haproxy/src/configure.py b/haproxy/src/configure.py index aec0c80..99a2b98 100644 --- a/haproxy/src/configure.py +++ b/haproxy/src/configure.py @@ -35,6 +35,7 @@ DOWN_INTER = os.environ.get('DOWN_INTER', INTER) RISE = os.environ.get('RISE', '2') FALL = os.environ.get('FALL', '3') +MAXCONN = os.environ.get('MAXCONN', '2') listen_conf = Template(""" @@ -62,7 +63,7 @@ backend $backend mode $mode balance $balance - default-server inter $inter fastinter $fastinter downinter $downinter fall $fall rise $rise + default-server inter $inter fastinter $fastinter downinter $downinter fall $fall rise $rise maxconn $maxconn cookie $cookies_name insert $cookies_params """) cookies = "cookie \\\"@@value@@\\\"" @@ -74,7 +75,7 @@ backend $backend mode $mode balance $balance - default-server inter $inter fastinter $fastinter downinter $downinter fall $fall rise $rise + default-server inter $inter fastinter $fastinter downinter $downinter fall $fall rise $rise maxconn $maxconn cookie $cookies_name prefix $cookies_params """) cookies = "" @@ -105,7 +106,8 @@ fall=FALL, rise=RISE, cookies_name=COOKIES_NAME, - cookies_params=COOKIES_PARAMS + cookies_params=COOKIES_PARAMS, + maxconn=MAXCONN ) if BACKENDS_MODE == 'http': From 60ce781891f07831190241ebd78feb18a5a06fcc Mon Sep 17 00:00:00 2001 From: "alessandro.ceglie" Date: Thu, 25 Aug 2022 16:30:39 +0200 Subject: [PATCH 4/4] add weight parameter to backends updated changelog --- CHANGELOG.md | 5 +++++ haproxy/Readme.md | 9 +++++---- haproxy/src/configure.py | 6 +++++- 3 files changed, 15 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index a0dabf1..94a7ecb 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,10 @@ # Changelog +## 2022-08-25 +- Add `MAXCONN` environment variable to limit max connection among backends (default to `0` - unlimited) [sauzher] +- Add `STATS_REFRESH` environment variable to enable auto refresh. (default to `0` - no refresh) [sauzher] +- Add optional weight parameter for remote backends `host:port:weight` (default to `1` - all same weight) [sauzher] + ## 2021-06-14 (1.8-1.7) - Upgrade HAProxy to 1.8.30 diff --git a/haproxy/Readme.md b/haproxy/Readme.md index 6c9aa1e..a062128 100644 --- a/haproxy/Readme.md +++ b/haproxy/Readme.md @@ -84,12 +84,14 @@ minimum possible `DNS_TTL`. ### Run with backends specified as environment variable $ docker run --env BACKENDS="192.168.1.5:80 192.168.1.6:80" eeacms/haproxy +or + $ docker run --env BACKENDS="192.168.1.5:80:4 192.168.1.6:80:1" eeacms/haproxy Using the `BACKENDS` variable is a way to quick-start the container. -The servers are written as `server_ip:server_listening_port`, +The servers are written as `server_ip:server_listening_port:weight`, separated by spaces (and enclosed in quotes, to avoid issues). The contents of the variable are evaluated in a python script that writes -the HAProxy configuration file automatically. +the HAProxy configuration file automatically. `weight` is optional and defaulted to `1` If there are multiple DNS records for one or more of your `BACKENDS` (e.g. when deployed using rancher-compose), you can use `DNS_ENABLED` environment variable. This way, haproxy will load-balance @@ -140,7 +142,7 @@ either when running the container or in a `docker-compose.yml` file. * `COOKIES_NAME` Will be added on cookie declaration - default `SRV_ID` * `COOKIES_PARAMS` Will be added on cookie declaration - example `indirect nocache maxidle 30m maxlife 8h` or `maxlife 24h` - documentation https://cbonte.github.io/haproxy-dconv/1.8/configuration.html#4-cookie * `BACKEND_NAME` The label of the backend - default `http-backend` - * `BACKENDS` The list of `server_ip:server_listening_port` to be load-balanced by HAProxy, separated by space - by default it is not set + * `BACKENDS` The list of `server_ip:server_listening_port:weight` to be load-balanced by HAProxy, separated by space - by default it is not set - by default weight is 1 * `BACKENDS_PORT` Port to use when auto-discovering backends, or when `BACKENDS` are specified without port - by default `80` * `BACKENDS_MODE` Backends mode - default `http` or `FRONTEND_MODE` if declared * `BALANCE` The algorithm used for load-balancing - default `roundrobin` @@ -161,7 +163,6 @@ either when running the container or in a `docker-compose.yml` file. * `RISE` number of consecutive valid health checks before considering the server as UP. Default value is `2` * `FALL` number of consecutive invalid health checks before considering the server as DOWN. Default value is `3` - ## Logging By default the logs from haproxy are present in the docker log, by using the rsyslog inside the container (UDP port 514). No access logs are present by default, but this can be changed by setting the log level. diff --git a/haproxy/src/configure.py b/haproxy/src/configure.py index fb3ae02..5ca4fdd 100644 --- a/haproxy/src/configure.py +++ b/haproxy/src/configure.py @@ -90,7 +90,7 @@ """) backend_conf_plus = Template(""" - server $name-$index $host:$port $cookies check + server $name-$index $host:$port $cookies check weight $weight """) health_conf = """ @@ -146,6 +146,7 @@ index=ip.replace(".", "-"), host=ip, port=port, + weight=1, cookies=cookies.replace('@@value@@', ip)) ################################################################################ @@ -157,11 +158,13 @@ server_port = backend_server.split(':') host = server_port[0] port = server_port[1] if len(server_port) > 1 else BACKENDS_PORT + weight = server_port[2] if len(server_port) > 2 else 1 backend_conf += backend_conf_plus.substitute( name=host.replace(".", "-"), index=index, host=host, port=port, + weight=weight, cookies=cookies.replace('@@value@@', host)) ################################################################################ @@ -212,6 +215,7 @@ index=index, host=host_ip, port=host_port, + weight=1, cookies=cookies.replace('@@value@@', host_ip) ) index += 1