<
  • Главная
Статьи

Відмов кластер для балансування навантаження

  1. КОНЦЕПЦІЯ
  2. РЕАЛІЗАЦІЯ:
  3. ТЕСТУВАННЯ:
  4. ПІСЛЯМОВА:

Поговоримо про горизонтальному масштабуванні. Припустимо, ваш проект виріс до розмірів, коли один сервер не справляється з навантаженням, і можливостей для вертикального зростання ресурсів вже немає.

В цьому випадку подальший розвиток інфраструктури проекту зазвичай відбувається за рахунок збільшення кількості однотипних серверів з розподілом навантаження між ними. Такий підхід не тільки дозволяє вирішити проблему з ресурсами, але і додає надійності проекту - при виході з ладу одного або декількох компонентів його працездатність загалом не буде порушена.

Велику роль у цій схемі грає балансувальник - система, яка займається розподілом запитів / трафіку. На етапі її проектування важливо передбачити такі ключові вимоги:

  • Відмовостійкість. Потрібно як мінімум два сервера, які одночасно займаються завданням розподілу запитів / трафіку. Без явного поділу ролей на ведучого і резервного.
  • Масштабування. Додавання нових серверів в систему має давати пропорційну прибавку в ресурсах.

Фактично, це опис кластера, вузлами якого є сервери-балансери.

У цій статті ми хочемо поділитися рецептом подібного кластера, простого і невибагливого до ресурсів, концепцію якого успішно застосовуємо у власній інфраструктурі для балансування запитів до серверів нашої панелі управління, внутрішнього DNS сервера, кластеру Galera і різноманітними мікросервісам.

Домовимося про терміни:

Сервери, що входять до складу кластера, будемо називати вузлами або балансер.

Кінцевими серверами будемо називати хости, на які проксіруется трафік через кластер.

Віртуальним IP будемо називати адресу, "плаваючий" між усіма вузлами, і на який повинні вказувати імена сервісів в DNS.

Що потрібно:

Для настройки кластера буде потрібно як мінімум два сервера (або вірт.машіни) з двома мережевими інтерфейсами на кожному.

Перший інтерфейс буде використовуватися для зв'язку із зовнішнім світом. Тут будуть налаштовані реальний і віртуальний IP адреси.

Другий інтерфейс буде використовуватися під службовий трафік, для спілкування вузлів один з одним. Тут буде налаштований адресу з приватної ( "сірої") мережі 172.16.0.0/24.

Другі інтерфейси кожного з вузлів повинні знаходитися в одному сегменті мережі.

Технології, що використовуються:

VRRP, Virtual Router Redundancy Protocol - в контексті цієї статті, реалізація "плаваючого" між вузлами кластера віртуального IP адреси. В один момент часу таку адресу може бути піднято на якомусь одному вузлі, іменованому MASTER. Другий вузол називається BACKUP. Обидва вузла постійно обмінюються спеціальними heartbeat повідомленнями. Отримання або неотримання таких повідомлень в рамках заданих проміжків дає підстави для перепризначення віртуального IP на "живий" сервер. Більш докладно про протокол можна прочитати тут .

LVS, Linux Virtual Server - механізм балансування на транспортному / сеансовому рівні, вбудований в ядро ​​Linux у вигляді модуля IPVS. Хороший опис можливостей LVS можна знайти тут і тут . Суть роботи зводиться до вказівкою того, що є певна пара "IP + порт" і вона є віртуальним сервером. Для цієї пари призначаються адреси реальних серверів, відповідальних за опрацювання запитів, задається алгоритм балансування, а також режим перенаправлення запитів.

У нашій системі ми будемо використовувати Nginx як проміжна ланка між LVS і кінцевими серверами, на які потрібно проксіровать трафік. Nginx буде присутній на кожному вузлі.

Для налаштувань VRRP і взаємодії з IPVS будемо використовувати демон Keepalived , Написаний в рамках проекту Linux Virtual Server.

КОНЦЕПЦІЯ

Система буде являти собою зв'язування з двох незалежних один від одного рівнозначних вузлів-балансер, об'єднаних в кластер засобами технології LVS і протоколу VRRP.

Точкою входу для трафіку буде віртуальний IP адреса, піднятий або на одному, або на другому вузлі.

Вступники запити LVS перенаправляє до одного з запущених екземплярів Nginx - локальному або на сусідньому вузлі. Такий підхід дозволяє рівномірно розмазувати запити між усіма вузлами кластера, тобто більш оптимально використовувати ресурси кожного балансер.

Робота Nginx полягає в проксінг запитів на кінцеві сервера. Починаючи з версії 1.9.13 доступні функції проксінг на рівні транспортних протоколів tcp і udp.

Кожен vhost / stream буде налаштований приймати запити як через службову інтерфейс з сусіднього балансер так і вступники на віртуальний IP. Причому навіть у тому випадку, якщо віртуальний IP адреса фізично не піднято на даному балансер (Keepalived призначив сервера роль BACKUP).

Таким чином, схема ходіння трафіку в залежності від стану балансер (MASTER або BACKUP) виглядає так:

MASTER:

  • запит приходить на віртуальний IP. IPVS маршрутизує пакет на локальний сервер;
  • оскільки локальний Nginx слухає в тому числі віртуальний IP, він отримує запит;
  • згідно налаштувань проксінг для даного віртуального IP Nginx відправляє запит одного з перерахованих апстрімов;
  • отриману відповідь відправляється клієнтові.

BACKUP:

  • запит приходить на віртуальний IP. IPVS маршрутизує пакет на сусідній сервер;
  • на сусідньому балансер цей віртуальний IP не тримаючи. Тому dst_ip в пакеті потрібно замінити на відповідний сірий IP з мережі поточного балансер. Для цього використовується DNAT;
  • після цього локальний Nginx отримує запит на сірий IP адреса;
  • за налаштувань проксінг для даного віртуального IP Nginx відправляє запит одного з перерахованих апстрімов;
  • отриману відповідь відправляється клієнту безпосередньо з src_ip рівним віртуальному IP (за участю conntrack)

РЕАЛІЗАЦІЯ:

В якості операційної системи будемо використовувати Debian Jessie з підключеними backports репозиторіями .

Встановимо на кожен узел-балансер пакети з необхідною для праці кластера ПО і зробимо кілька загальносистемних налаштувань:

apt-get update apt-get install -t jessie-backports nginx apt-get install keepalived ipvsadm

На інтерфейсі eth1 налаштуємо адреси з сірої мережі 172.16.0.0/24:

allow-hotplug eth1 iface eth1 inet static address 172.16.0.1 # На другому балансер - 172.16.0.2 netmask 255.255.255.0

Віртуальний IP адреса прописувати на інтерфейсі eth0 не потрібно. Це зробить Keepalived.

У файл /etc/sysctl.d/local.conf додамо наступні директиви:

net.ipv4.ip_nonlocal_bind = 1 net.ipv4.vs.drop_entry = 1 net.nf_conntrack_max = 4194304

Перша включає можливість слухати IP, які не підняті локально (це потрібно для роботи Nginx). Друга включає автоматичний захист від DDoS на рівні балансувальника IPVS (при нестачі пам'яті під таблицю сесій почнеться автоматичне вичищення деяких записів). Третя збільшує розмір conntrack таблиці.

В / etc / modules включаємо завантаження модуля IPVS при старті системи:

ip_vs conn_tab_bits = 18

Параметр conn_tab_bits визначає розмір таблиці з сполуками. Значення одеського форуму є ступенем двійки. Максимально допустиме значення - 20.

До речі, якщо модуль не завантажиться до старту Keepalived, останній починає сегфолтіться.

Тепер перезавантажити обидва вузла-балансер. Так ми переконаємося, що при старті вся конфігурація коректно підніметься.

Загальні налаштування виконані. Подальші дії будемо виконувати в контексті двох завдань:

  • Балансування http трафіку між трьома веб-серверами
  • Балансування udp трафіку на 53 порт двох DNS серверів

Вхідні дані:

  • В якості віртуального IP адреси будемо використовувати ** 192.168.0.100 **.
  • У веб-серверів будуть адреси ** 192.168.0.101 ** ** 192.168.0.102 ** і ** 192.168.0.103 ** відповідно з їх порядковими номерами.
  • У DNS серверів ** 192.168.0.201 ** і ** 192.168.0.202 **.

Почнемо з конфігурації Nginx.

Додамо опис секції stream в /etc/nginx/nginx.conf:

stream {include / etc / nginx / stream-enabled / *; }

І створимо відповідний каталог:

mkdir / etc / nginx / stream-enabled

Налаштування для веб-серверів додамо в файл /etc/nginx/sites-enabled/web_servers.conf

upstream web_servers {server 192.168.0.101:80; server 192.168.0.102:80; server 192.168.0.103:80; } Server {listen 172.16.0.1:80 default_server; # На другому балансер - 172.16.0.2 listen 192.168.0.100:80 default_server; location / {proxy_set_header Host $ host; proxy_set_header X-Real-IP $ remote_addr; proxy_set_header X-Forwarded-For $ proxy_add_x_forwarded_for; proxy_pass http: // web_servers; proxy_redirect default; }}

Налаштування для DNS-серверів додамо в файл /etc/nginx/stream-enabled/dns_servers.conf

upstream dns_servers {server 192.168.0.201:53; server 192.168.0.202:53; } Server {listen 172.16.0.1:53 udp reuseport; # На другому балансер - 172.16.0.2 listen 192.168.0.100:53 udp reuseport; proxy_pass dns_servers; }

Далі залишається конфігурувати Keepalived (VRRP + LVS). Це трохи складніше, оскільки нам потрібно написати спеціальний скрипт, який буде запускатися при переході вузла-балансер між станами MASTER / BACKUP.

Всі настройки Keepalived повинні знаходитися в одному файлі - /etc/keepalived/keepalived.conf. Тому всі нижченаведені блоки з конфігураціями VRRP і LVS потрібно послідовно зберегти в цьому файлі.

Налаштування VRRP:

vrrp_instance 192.168.0.100 {interface eth1 # Інтерфейс на якому буде працювати VRRP track_interface {# Якщо на одному з цих інтерфейсів пропаде лінк або eth0 # він буде виключений, балансер перейде в стан eth1 # FAULT, тобто з нього буде видалений віртуальний IP і # всі налаштування LVS} virtual_router_id 1 # Повинен співпадати на обох вузлах nopreempt # Не змінювати роль поточного балансер на BACKUP # якщо в мережі з'явився сусід з більш високим пріоритетом priority 102 # Пріоритет. Може відрізнятися на різних вузлах authentication {auth_type PASS auth_pass secret # тут потрібно встановити свій пароль} virtual_ipaddress {192.168.0.100/24 ​​dev eth0} notify / usr / local / bin / nat-switch}

Скрипт, який згадувався вище - / usr / local / bin / nat-switch. Він запускається кожного разу, коли у поточного VRRP інстанси змінюється стан. Його завдання полягає в тому, щоб балансер, що знаходиться в стані BACKUP, вмів коректно обробити пакети, адресовані на віртуальний IP. Для вирішення цієї ситуації використовуються можливості DNAT. А саме, правило виду:

-A PREROUTING -d 192.168.0.100/32 -i eth1 -j DNAT --to-destination $ {IP_on_eth1}

При переході в стан MASTER, скрипт видаляє це правило.

тут можна знайти варіант скрипта nat-switch, написаний для даного прикладу.

Налаштування LVS для групи веб-серверів:

virtual_server 192.168.0.100 80 {lb_algo wlc # Алгоритм балансування # wlc - більше запросив до серверів з меншим кол-вом # активних сполук. lb_kind DR # Режими перенаправлення запитів. Direct routing protocol TCP delay_loop 6 # Інтервал між запусками healthchecker'а real_server 172.16.0.1 80 {weight 1 TCP_CHECK {# Проста перевірка доступності локального connect_timeout 2 # і сусіднього примірників Nginx}} real_server 172.16.0.2 80 {weight 1 TCP_CHECK {connect_timeout 2} }}

Налаштування LVS для групи DNS-серверів:

virtual_server 192.168.0.100 53 {lb_algo wlc lb_kind DR protocol UDP delay_loop 6 real_server 172.16.0.1 53 {weight 1 MISC_CHECK {connect_timeout 2 misc_path "/ bin / nc -zn -u 172.16.0.1 53"}} real_server 172.16.0.2 53 {weight 1 MISC_CHECK {connect_timeout 2 misc_path "/ bin / nc -zn -u 172.16.0.2 53"}}}

На завершення перезавантажити конфігурацію Nginx і Keepalived:

nginx -s reload && /etc/init.d/keepalived reload

ТЕСТУВАННЯ:

Подивимося як балансувальник розподіляє запити до кінцевих серверів. Для цього на кожному з веб-серверів створимо index.php з яким-небудь простим вмістом:

<? Php sleep (rand (2, 8)); echo ( "Hello from" .gethostname (). "!"); ?>

І зробимо кілька запитів по http до віртуального IP 192.168.0.100:

for i in $ (seq 10); do printf 'GET / HTTP / 1.0 \ n \ n \ n' | nc 192.168.0.100 80 | grep Hello done

результат:

Hello from server-1! Hello from server-2! Hello from server-2! Hello from server-3! Hello from server-3! Hello from server-1! Hello from server-1! Hello from server-2! Hello from server-2! Hello from server-3!

Якщо в процесі виконання цього циклу подивитися на статистику роботи LVS (на MASTER вузлі), то ми можемо побачити наступну картину:

ipvsadm -Ln

результат:

IP Virtual Server version 1.2.1 (size = 262144) Prot LocalAddress: Port Scheduler Flags -> RemoteAddress: Port Forward Weight ActiveConn InActConn TCP 192.168.0.100:80 wlc -> 172.16.0.1:80 Route 1 + 1 3 -> 172.16.0.2 : 80 Route 1 1 3 UDP 192.168.0.100:53 wlc -> 172.16.0.1:53 Route 1 0 0 -> 172.16.0.2:53 Route 1 0 0

Тут видно як відбувається розподіл запитів між вузлами кластера: є два активних з'єднання, які обробляються в даний момент і 6 вже оброблених з'єднань.

Статистику по всі з'єднанням, які проходять через LVS, можна подивитися так:

ipvsadm -Lnc

результат:

IPVS connection entries pro expire state source virtual destination TCP 14:57 ESTABLISHED 192.168.0.254:59474 192.168.0.100:80 172.16.0.1:80 TCP 1:49 FIN_WAIT 192.168.0.254:59464 192.168.0.100:80 172.16.0.1:80 TCP 1:43 FIN_WAIT 192.168.0.254:59462 192.168.0.100:80 172.16.0.1:80 TCP 14:59 ESTABLISHED 192.168.0.254:59476 192.168.0.100:80 172.16.0.2:80 TCP 1:56 FIN_WAIT 192.168.0.254:59468 192.168 .0.100: 80 172.16.0.1:80 TCP 1:57 FIN_WAIT 192.168.0.254:59472 192.168.0.100:80 172.16.0.2:80 TCP 1:50 FIN_WAIT 192.168.0.254:59466 192.168.0.100:80 172.16.0.2:80 TCP 1:43 FIN_WAIT 192.168.0.254:59460 192.168.0.100:80 172.16.0.2:80

Тут, відповідно, бачимо те ж саме: 2 активних і 6 неактивний з'єднань.

ПІСЛЯМОВА:

Описану схему кластера не вийде реалізувати в рамках наших хмарних VDS.

Запропонована нами конфігурація може послужити відправним пунктом для проектування приватного рішення під конкретний проект із своїми вимогами і особливостями.



Новости
  • Виртуальный хостинг

    Виртуальный хостинг. Возможности сервера распределяются в равной мере между всеми... 
    Читать полностью

  • Редизайн сайта

    Редизайн сайта – это полное либо частичное обновление дизайна существующего сайта.... 
    Читать полностью

  • Консалтинг, услуги контент-менеджера

    Сопровождение любых интернет ресурсов;- Знание HTML и CSS- Поиск и обновление контента;-... 
    Читать полностью

  • Трафик из соцсетей

    Сравнительно дешевый способ по сравнению с поисковым и контекстным видами раскрутки... 
    Читать полностью

  • Поисковая оптимизация

    Поисковая оптимизация (англ. search engine optimization, SEO) — поднятие позиций сайта в результатах... 
    Читать полностью