Haproxy agent-check Статус DRAIN (агента) по-прежнему принимает новые соединения - PullRequest
0 голосов
/ 05 марта 2020

Я пытаюсь выполнить балансировку нагрузки для моего приложения Node.js, которое использует веб-сокеты. Мне нужен haproxy, чтобы остановить балансировку нагрузки новых соединений на сервере, который достиг максимального количества соединений, сохраняя при этом существующие в целости и сохранности.

Я делаю это, выполняя проверку агента для каждого из моих серверов. Если сервер не может принять новые соединения, он отвечает «утечкой» на проверку агента. Если сервер может ответить на новое соединение, он отвечает «готов» на проверку агента.

Вот мой файл конфигурации haproxy.cfg:

global
 daemon
 maxconn 240000
 log /dev/log local0 debug
 log /dev/log local1 notice
 tune.ssl.default-dh-param 2048
defaults
 mode http
 log global
 option httplog
 option dontlognull
 option dontlog-normal
 option http-server-close
 option redispatch
 timeout connect 20000ms
 timeout http-request  1m
 timeout client 2100000ms
 timeout server 2100000ms
 timeout queue  30s
 timeout check  5s
 timeout http-keep-alive 180s
 timeout tunnel 3600s
 timeout tarpit          60s

frontend stats
    bind *:8084
    stats enable
    stats uri /stats
    stats refresh 10s
    stats admin if TRUE

frontend test
    mode http
    bind *:5000

    default_backend ws


backend ws
    mode http
    fullconn 100000
    balance roundrobin
    cookie SERVERID insert indirect nocache

    server 1 backend1:9999 check agent-check agent-port 8080 cookie 1 inter 500 fall 1 rise 2

А здесь как я отвечаю на проверку агента haproxy в моем приложении Node.js:

const healthCheckServer = net.createServer((c) => {
    let data = '';
    if (currentConn < MAX_CONN) {
        data += 'ready';
    } else {
        data += 'drain';
    }
    c.write(data + '\r\n');
    c.destroy();
});

healthCheckServer.listen(8080, '0.0.0.0');

Когда число подключений к моему приложению достигает своего максимума, haproxy корректно меняет состояние сервера на DRAIN (agent) (я могу наблюдать это в haproxy веб-панели). Проблема в том, что новые соединения по-прежнему принимаются приложением.

Я новичок в haproxy, поэтому кто-то может указать мне, где я ошибаюсь?

1 Ответ

0 голосов
/ 05 марта 2020

Обнаружено, что когда сервер очищается агентом (состояние установлено на DRAIN (agent)), и если сервер является единственным, существующим в бэкэнде, он все равно будет принимать новые подключения.

При наличии нескольких серверов присутствует и каждый сервер истощен, поведение такое же, как и ожидалось: haproxy возвращает HTTP 503.

ОБНОВЛЕНИЕ: Оказалось, что я все время смотрел в неправильном направлении.

Сначала я должен был отметить свой бэкэнд, который обрабатывает соединения WebSocket, как не-http (удалить строку mode http). Я предполагаю, что haproxy неправильно подсчитывает текущие сеансы для http-бэкенда при использовании WebSockets. Удаление mode http решило мою проблему.

Во-вторых, возвращение maxconn:<conn> в агент-проверке выглядит гораздо более простым и более идиоматическим c способом ограничения числа одновременных соединений.

Источники :

  1. https://cbonte.github.io/haproxy-dconv/1.8/configuration.html#5 .2-агент-проверка
  2. https://www.haproxy.com/blog/websockets-load-balancing-with-haproxy/

Надеюсь, это кому-нибудь поможет.

...