Перейти к основному содержимому

Приложение 3. Использование HAProxy

Работоспособность PostgreSQL сервера сильно зависит от количества активных соединений к БД. Оптимальное количество процессов для обработки соединений 100-200. Настройка количества соединений производится в конфигурационных файлах сервера PostgreSQL. Например, /var/lib/pgsql/11/data/postgresql.conf.

осторожно

Рекомендуем использовать настройку конфигурации сервера с использованием команд ALTER SYSTEM. Это позволяет обеспечить применение измененных параметров при старте экземпляра PostgreSQL и сохраняет возможность отката к настройкам по умолчанию или предыдущим настройка с помощью корректировки/удаления файла postgresql.auto.conf.

По умолчанию система Luxms BI настраивает 150 соединений к БД. Это значение может быть изменено при эксплуатации при необходимости.

При увеличении количества активных пользователей системы Luxms BI установленное количество соединений может быть недостаточным и вызвать отказ в обслуживании. Для обеспечения работоспособности при высокой нагрузке мы рекомендуем использование HAProxy в качестве менеджера пула соединений к БД.

HAProxy в роли менеджера пула соединений

Для установки HAProxy необходимо выполнить следующий перечень команд:

sudo yum -y install haproxy
sudo setsebool -P haproxy_connect_any=1
cp /etc/haproxy/haproxy.cfg /etc/haproxy/haproxy.cfg.default

Ниже расположен конфигурационный файл HAProxy, включающий в себя настройки для:

  • Журналирования событий балансировщика.
  • Предоставления web-интерфейса для управления и просмотра статистики по балансировщику нагрузки.
  • Обеспечение очереди для запросов к БД PostgreSQL.

Замените содержимое конфигурационного файла /etc/haproxy/haproxy.cfg, тем более что предыдущие команды создали его резервную копию:

global
daemon
user haproxy
group haproxy
pidfile /var/run/haproxy.pid
log /dev/log local0
maxconn 102400

defaults
log global
mode tcp
retries 2
timeout client 30m
timeout connect 4s
timeout server 30m
timeout check 5s

listen stats
bind 127.0.0.1:2000
maxconn 100
mode http
option httplog
stats uri /stats
stats enable
stats refresh 1s
stats admin if LOCALHOST

listen postgres
bind *:5432
maxconn 10240
timeout queue 30s
server local localhost:9898 maxconn 100

Поскольку запуск HAProxy произведен не в chroot-окружении, не требуется дополнительной настройки для организации журналирования событий сервиса - журнальные записи сохраняются в системном journald. Для просмотра журнальных записей достаточно набрать команду:

sudo journalctl -u haproxy

После корректировки/создания конфигураций, необходимо изменить порт для экземпляра PostgreSQL. Изменение порта экземпляра БД позволяет не производить многочисленных корректировок конфигурационных файлов компонентов системы Luxms BI. Выполните следующие команды:

su - postgres -c '/usr/pgsql11/bin/psql "ALTER SYSTEM SET PORT TO 9898;"'
sudo systemctl restart postgresql-11 haproxy

С этого момента система Luxms BI будет использовать HAProxy как менеджер пула соединений к БД PostgreSQL.

к сведению

Порт 9898/TCP уже зарегистрирован в SELinux как postgresql_port_t, поэтому дополнительных настроек безопасности не требуется.

Не забудьте добавить в профиль сервисной учетной записи postgres измененное значение порта, это облегчит работу с утилитами PostgreSQL:

--- .bash_profile.old   2021-06-05 00:47:06.303382240 +0300
+++ .bash_profile 2021-06-05 00:37:04.264916442 +0300
@@ -1,6 +1,7 @@
[ -f /etc/profile ] && source /etc/profile
PGDATA=/var/lib/pgsql/11/data
-export PGDATA
+PGPORT=9898
+export PGDATA PGPORT
# If you want to customize your settings,
# Use the file below. This is not overridden
# by the RPMS.

Подключение к web-интерфейсу HAProxy для просмотра статистики и управления

Рекомендуем использование SSH SOCKS-прокси и плагина для Вашего браузера, например, для FireFox добавьте FoxyProxy Standard.

И настройте расширение:

foxyproxy.png

Обеспечьте создание SOCKS-прокси через SSH-соединение

ssh -D 1080 <Luxms BI host IP/DNS>

В качестве альтернативы Вы можете откорректировать конфигурационный файл HAProxy (директиву bind, разрешив доступ к интерфейсу других хостов) и добавить разрешения для доступа в фаервол сервера.

Тюнинг операционной системы

Настройка сетевого стека ядра для хоста с установленным HAProxy в чем-то похожа на настройку тестирующего хоста, создающего нагрузку:

/etc/sysctl.d/98-luxmsbi.conf:

net.core.netdev_max_backlog = 5000
net.core.somaxconn = 65535
net.ipv4.ip_local_port_range = 1025 65000
net.ipv4.tcp_max_syn_backlog = 5000
net.ipv4.tcp_tw_reuse = 1

HAProxy как балансировщик для кластера

Кластер PostgreSQL под управлением Patroni[consul] позволяет предоставлять доступ к экземпляру базы данных с возможностью добавления/изменения данных и к нескольким экземплярам с возможностью только чтения данных. Перенаправление запросов на чтение на выделенные сервера позволяет снизить общую нагрузку на основной экземпляр и обеспечить устойчивую работоспособность системы.

В случае выхода/вывода из рабочего режима одного из узлов кластера PostgreSQL Patroni оперативно выполняет передачу ролей и реконфигурацию кластера. Что требует такого же оперативного изменения конфигураций на серверах приложений.

В текущей архитектуре для балансировки нагрузки используется HAProxy. А для динамического изменения конфигурации HAProxy при изменении в кластере PostgreSQL используется решение Consul-Template.

Consul-Template. Установка и настройка

  1. Поместить поставляемые шаблоны конфигурационных файлов (см. ниже) и архив с приложением на хост, в папку /tmp/consul. И выполнить команды:
cd /tmp/consul
#curl -kO https://releases.hashicorp.com/consul-template/0.24.1/consul-template_0.24.1_linux_amd64.tgz
sudo -- sh -c 'unzip -u -d /usr/sbin consul-template_0.24.1_linux_amd64.tgz \
&& chmod ug+x /usr/sbin/consul \
&& rm -r /tmp/consul-template_0.24.1_linux_amd64.tgz'

sudo mkdir -p /etc/consul-template.d /var/lib/consul/templates
sudo cp consul-template.hcl /etc/consul-template.d/00-consul-template.hcl
sudo cp haproxy.hcl /etc/consul-template.d/
sudo cp haproxy.ctmpl /var/lib/consul/templates/
sudo chown -R consul.consul /etc/consul-template.d /var/lib/consul/templates
sudo -- sh -c 'cp consul-template.service /etc/systemd/system/ \
&& sudo systemctl daemon-reload
&& sudo systemctl enable consul-template'

HAProxy. Установка и конфигурирование

default

Для разрешения проблемы HAProxyCannot bind socket” необходимо установить флаг SELinux:

setsebool -P haproxy_connect_any=1

:::

Для установки HAProxy необходимо выполнить следующий перечень команд:

sudo yum -y haproxy
sudo setsebool -P haproxy_connect_any=1
sudo systemctl enable haproxy
sudo systemctl start consul-template haproxy

Шаблоны конфигурационных файлов

/etc/consul-template.d/00-consul-template.hcl

consul {
address = "127.0.0.1:8500"
token = "{{ consul_token }}"
retry {
enabled = true
attempts = 12
backoff = "250ms"
max_backoff = "10s"
}
}

reload_signal = "SIGHUP"

kill_signal = "SIGINT"

max_stale = "10m"

log_level = "warn"

# pid_file = "/run/consul-template.pid"

wait {
min = "2s"
max = "5s"
}

deduplicate {
enabled = true
prefix = "consul-template/dedup/"
}
/etc/consul-template.d/haproxy.hcl
template {
source = "/var/lib/consul/templates/haproxy.ctmpl"
destination = "/etc/haproxy/haproxy.cfg"
command = "systemctl reload haproxy"
command_timeout = "10s"
error_on_missing_key = false
backup = true
wait {
min = "2s"
max = "10s"
}
}
к сведению

Документация по функциям и встроенным переменным для написания шаблонов Consul Template language.

/var/lib/consul/templates/haproxy.ctmpl

# Rendered by consul-template.service {{ timestamp }}

global
daemon
chroot /var/lib/haproxy
user haproxy
group haproxy
pidfile /var/run/haproxy.pid
log /dev/log local0
maxconn 102400

defaults
log global
mode tcp
retries 2
timeout client 30m
timeout connect 4s
timeout server 30m
timeout check 5s

listen stats
bind *:2000
maxconn 100
mode http
option httplog
stats uri /stats
stats enable
stats refresh 10s
stats admin if LOCALHOST

### Listener for PostgreSQL LEADER database
listen db-rw
bind 127.0.0.1:5432
maxcon 10240
timeout queue 30s
option httpchk OPTIONS /master
http-check expect status 200
default-server inter 3s rise 2 fall 3 maxconn 100 shutdown-sessions {{range service "master.db-main"}}
server {%raw%}{{.Node}} {{.Address}}:{{.Port}} check port 8008{{end}}

### Listener for PostgreSQL REPLICA database
listen db-ro
bind 127.0.0.1:5433
maxconn 10240
timeout queue 30s
option httpchk OPTIONS /replica
http-check expect status 200
balance roundrobin
default-server inter 3s rise 2 fall 3 maxconn 100 shutdown-sessions {{range service "replica.db-main"}}
server {{.Node}} {{.Address}}:{{.Port}} check port 8008{{end}}

Для использования шаблона в ansible (Jinja2 template) необходимо экранировать переменные consul-template с помощью конструкции {%raw%} ... {%endraw%}

# Rendered by consul-template.service {%raw%}{{ timestamp }}{%endraw%}

global
daemon
chroot /var/lib/haproxy
user haproxy
group haproxy
pidfile /var/run/haproxy.pid
log /dev/log local0
maxconn 102400

defaults
log global
mode tcp
retries 2
timeout client 30m
timeout connect 4s
timeout server 30m
timeout check 5s

listen stats
bind *:2000
maxconn 100
mode http
option httplog
stats uri /stats
stats enable
stats refresh 10s
stats admin if LOCALHOST

### Listener for PostgreSQL LEADER database
listen db-rw
bind 127.0.0.1:{{ db_rw_port}}
maxcon 10240
timeout queue 30s
option httpchk OPTIONS /master
http-check expect status 200
default-server inter 3s rise 2 fall 3 maxconn 100 shutdown-sessions {%raw%}{{range service "master.{%endraw%}{{ consul_service }}{%raw%}"}}{%endraw%}
server {%raw%}{{.Node}} {{.Address}}:{{.Port}} check port 8008{{end}}{%endraw%}

### Listener for PostgreSQL REPLICA database
listen db-ro
bind 127.0.0.1:{{ db_ro_port}}
maxconn 10240
timeout queue 30s
option httpchk OPTIONS /replica
http-check expect status 200
balance roundrobin
default-server inter 3s rise 2 fall 3 maxconn 100 shutdown-sessions {%raw%}{{range service "replica.{%endraw%}{{ consul_service }}{%raw%}"}}{%endraw%}
server {%raw%}{{.Node}} {{.Address}}:{{.Port}} check port 8008{{end}}{%endraw%}

/etc/systemd/system/consul-template.service

[Unit]
Description=Consul Template Service
Documentation=https://github.com/hashicorp/consul-template/
After=network-online.target
Wants=network-online.target

[Service]
Type=simple
#User=consul
#Group=consul
ExecStart=/usr/sbin/consul-template -config=/etc/consul-template.d/
ExecReload=/bin/kill -HUP $MAINPID
KillSignal=SIGINT
TimeoutStopSec=5
Restart=on-failure
SyslogIdentifier=consul

[Install]
WantedBy=multi-user.target