Пользователь
0,0
рейтинг
21 сентября 2010 в 01:00

Администрирование → Балансировка нагрузки с LVS

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



DNS-RR


Первым делом напрашивается вариант с использованием Round-robin DNS. Если кто не знает, это метод позволяющий размазать запросы между n-ым количеством серверов просто отдавая на каждый DNS запрос новый IP.

Каковы минусы:
  • Сложно управлять: вы забили группу IP-адресов и все, никаких тебе управлений весами, состояние серверов не отслеживается и т.д.
  • Фактически вы размазываете запросы по диапазону IP, но не балансируете нагрузку на серверах
  • Кэширование DNS клиента может поломать всю малину


Хотя и не стоит добавлять между вводом и выводом «слишком много компьютера», хочется каких-либо методов контроля над ситуацией.

LVS


И тут на помощь к нам приходит Linux Virtual Server или LVS. Фактически, это модуль ядра (ipvs), существующий еще где-то с версии 2.0-2.2.

Что же он из себя представляет? Фактически это L4-роутер (я бы сказал что L3, но авторы настаивают на L4), позволяющий прозрачно и управляемо разруливать пакеты по заданным маршрутам.



Основная терминология следующая:
  • Director — собственно узел осуществляющий роутинг.
  • Realserver — рабочая лошадка, узел нашей фермы серверов.
  • VIP или Virtual IP — всего лишь IP нашего виртуального (собранного из кучи реальных) сервера.
  • Соответственно DIP и RIP — IP директора и реальных серверов.


На директоре включается этот самый модуль IPVS (IP Virtual Server), настраиваются правила проброса пакетов и поднимается VIP — обычно как алиас к внешнему интерфейсу. Пользователи будут ходить через VIP.

Пакеты, пришедшие на VIP пробрасываются выбранным методом до одного из Realserver'ов и там уже нормально отрабатываются. Клиенту кажется что он работает с одной машиной.

Правила


Правила проброса пакетов крайне просты: задаем виртуальный сервис, определяемый парой VIP:port. Сервис может быть TCP или UDP. Здесь же задаем метод ротации узлов (планировщик, scheduler). Далее задаем набор серверов из нашей фермы, также парой RIP:port, а также указываем метод проброса пакетов и вес, если того требует выбранный планировщик.

Выглядит это примерно следующим образом.

# ipvsadm -A -t 192.168.100.100:80 -s wlc
# ipvsadm -a -t 192.168.100.100:80 -r 192.168.100.2:80 -w 3
# ipvsadm -a -t 192.168.100.100:80 -r 192.168.100.3:80 -w 2
# ipvsadm -a -t 192.168.100.100:80 -r 127.0.0.1:80 -w 1


Да, не забудьте поставить пакет ipvsadmin, он должен быть в репозитории вашего дистрибутива. Во всяком случае в Debian и RedHat он есть.

В примере выше мы создаем виртуальный HTTP сервис 192.168.100.100 и включаем в него сервера 127.0.0.1, 192.168.100.2 и 192.168.100.3. Ключ "-w" задает вес сервера. Чем он выше, тем с бОльшей вероятностью он получит запрос. Если выставить вес в 0, то сервер будет исключен из всех операций. Очень удобно, если нужно вывести сервер из эксплуатации.

Пакеты по умолчанию пробрасываются методом DR. Вообще существуют следующие варианты роутинга:
  • Direct Routing (gatewaying) — пакет направляется напрямую на ферму, без изменений.
  • NAT (masquarading) — просто хитрый механизм NAT.
  • IPIP incapsulation (tunneling) — туннелирование.


DR является наиболее простым, но если вам, например, нужно поменять порт назначения, то придется рисовать правила в iptables. NAT же требует, чтобы маршрут по умолчанию у всей фермы был направлен на директора, что не всегда удобно, особенно если реальные сервера имеют и внешние адреса.

Планировщиков в комплекте поставки несколько, подробно можно почитать в инструкции. Рассмотрим лишь основные.
  • Round Robin — знакомая всем круговая порука.
  • Weighted Round Robin — тоже самое, но с использованием весов сервера.
  • Least Connection — отправляем пакет серверу с наименьшим количеством соединений.
  • Weighted Least Connection — тоже самое, но с учетом весов.


Ко всему прочему, можно сообщить, что сервис требует persistence, т.е. удерживание пользователя на одном из серверов в течении заданного промежутка времени — все новые запросы с одного и того же IP будут прокинуты на тот же сервер.

Подводные камни


Итак, согласно примеру выше, мы должны были получить виртуальный сервер на VIP 192.168.100.100, о чем нам ipvsadm и радостно сообщает:

ipvsadm -L -n
IP Virtual Server version 1.0.7 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.100.100:80 wlc
-> 192.168.100.2:80 Route 3 0 0
-> 192.168.100.3:80 Route 2 0 0
-> 127.0.0.1:80 Local 1 0 0


Однако, при попытке соединения ничего не произойдет! В чем же дело? Первым делом необходимо поднять алиас.
# ifconfig eth0:0 inet 192.168.100.100 netmask 255.255.255.255

Но и тут нас ждет неудача — пакет приходит на интерфейс реального сервера немодифицированным и следовательно тупо отпинывается ядром как не предназначающийся машине. Простейшим методом разрешения этого вопроса является поднятие VIP на loopback.

# ifconfig lo:0 inet 192.168.100.100 netmask 255.255.255.255

Ни в коем случае не поднимайте его на интерфейсе, который глядит в ту же подсеть, что и внешний интерфейс директора. В противном случае внешний роутер может закэшировать mac не той машины и весь трафик пойдет не туда.

Теперь пакетики должны побежать куда надо. Кстати, директор сам может быть реальным сервером, что мы и видим в нашем примере.

Единая точка отказа


В этом решении очевидной точкой отказа, вызывающей разрушение всего сервиса, будет сам директор.

Что ж, не беда, ipvsadm поддерживает запуск в режиме демона с возможностью синхронизации таблиц и текущих соединений между несколькими директорами. Один, очевидно, станет мастером, остальные будут слейвами.

Что остается нам? Переезжать VIP между директорами в случае отказа. Тут нам помогут HA решения вроде heartbeat.

Другой задачей будет мониторинг и своевременный вывод из эксплуатации серверов из нашей фермы. Проще всего это делать весами.

Для разруливания обоих вопросов написано множество решений, заточенных под разные типы сервисов. Мне лично больше всего понравилось решение Ultramonkey, от самих же авторов LVS.

У RedHat есть родная штука под названием Piranha, она имеет свой набор демонов для мониторинга фермы и директоров и даже некий топорненький веб-интерфейс, однако она не поддерживает более чем 2 директора в HA связке. Уж не знаю почему.

Ultramonkey


Итак, Ultramonkey состоит из 2-х основных пакетов — heartbeat и ldirectord. Первый занимается обеспечением HA для директоров, в том числе поднятие и переезд VIP (и вообще говоря может использоваться не только для директоров), а второй поддерживает конфиг ipvsadm и мониторит состояние фермы.

Для heartbeat необходимо нарисовать 3 конфига. Базовые версии снабжены подробными комментариями, поэтому просто приведу примеры.

authkeys
auth 2
#1 crc
2 sha1 mysecretpass
#3 md5 Hello!

Настраиваем авторизацию демонов на разных машинах.

haresources
Здесь у нас информация о том, для какого ресурса мы создаем HA и какие сервисы дергаем при переезде.
director1.foo.com IPaddr::192.168.100.100/24/eth0 ldirectord

Т.е. поднять на интерфейсе eth0 192.168.100.100/24 и запустить ldirectord.

ha.cf
keepalive 1
deadtime 20
udpport 694
udp eth0
node director1.foo.com # <-- должно совпадать с uname -n !
node director2.foo.com #

Говорим каким образом поддерживать HA кластер и кто собственно в него входит.

У ldirectord всего один конфиг и там в общем-то тоже все понятно.
checktimeout=10
checkinterval=2
autoreload=yes
logfile="/var/log/ldirectord.log"
# Virtual Service for HTTP
virtual=192.168.100.100:80
real=192.168.100.2:80 gate
real=192.168.100.3:80 gate
service=http
request="alive.html"
receive="I'm alive!"
scheduler=wlc
protocol=tcp
checktype=negotiate


Т.е. ldirectord будет каждые 2 секунды дергать через http файл alive.html и если в нем не будет строчки «I'm alive!» или, хуже того, сервер не ответит, демон тут же поставит ему вес 0 и он будет исключен из последующих пересылок.

Веса также можно расставлять самому, например пробегаясь кроном по полю и вычисляя их в зависимости от текущего loadavg и т.п. — прямой доступ к ipvsadm у вас никто не отнимает.

Применимость


Хотя везде по интернету в качестве сферы применения LVS в основном рассматривается балансировка веб-серверов, на самом деле им можно балансировать великое множество сервисов. Если протокол держится на одном порте и не имеет состояний, то его можно будет балансировать без особых проблем. Сложнее дело обстоит с мультипортовыми протоколами вроде samba и ftp, но и тут есть решения.

Кстати, в качестве реальных серверов не обязательно должен выступать Linux. Это можеть быть практически любая ОС со стеком TCP/IP.

Также существует еще и так называемый L7-роутер, который оперирует уже не портами, а знаниями о высокоуровневых протоколах. Товарищи японцы разрабатывают Ultramonkey-L7 для этого случая. Однако сейчас мы его касаться не будем.

Что еще почитать?




Какие решения для балансировки используете вы?
Буду рад любым замечаниям и комментариям.
@divanikus
карма
65,2
рейтинг 0,0
Реклама помогает поддерживать и развивать наши сервисы

Подробнее
Реклама

Самое читаемое Администрирование

Комментарии (47)

  • 0
    Отлично! а то платный bng надоел.
    Спасибо!
  • 0
    Спасибо! Из статьи не понял, каким маршрутом пакеты убегают обратно. Внешний канал такой конфигурации будет равен внешнему каналу директора или сумме внешних каналов всех серверов?
    • +2
      При DR пакеты убегают минуя директор, так что на директоре не виден исходящий трафик. Если воткнуть NAT, то побегут через директор конечно.
      • 0
        а куда именно они убегают?
        насколько я понимаю, схема выглядит примерно так:
        1) пришел запрос на директор (установилось соединение)
        2) директор прокинул запрос на внутрисеть (установил соединение, переслал запрос, получил ответ)
        3) внутрисетевой сервер получил запрос (установилось соединение), отработал и…
        4а) в моем понимании: отдал результат директору, который отдал его клиенту
        4б) в Вашем понимании: отправил данные куда-то (куда?)
        • 0
          все, понял куда они убегают:
          — запрос на директор пришел через внешний gateway
          — ответ от конечного сервера ушел прямо на этот внешний gateway
          • 0
            Именно
      • 0
        А не нарушает ли это само понятие маршрутизации? ведь если смоттреть со стороны gateway'a (rfr описано комментариями выше), получается. что шлюз отправил порт на один IP (в примере из статьи — 192.168.100.100 (я правильно понял?)), а ответ получает — от одного из реальных серверов, тоесть от 192.168.100.2 или .3
        Например, при варианте, когда на шлюзе стоит нат, такой расклад не прокатит.
        Да и при стандартной конфигурации шлюза тоже не будет работать, так как клиент ждет ответа от другого компьютера (порты не совпадут).
        Объясните, пожалуйста, более подробно, где я не прав?
        • 0
          Надо глянуть tcpdump. По-моему клиент получает ответ все от того же 192.168.100.100.
          • 0
            значит это где-то на клиенте должно быть прописано, или трафик все-таки ходит через директора…
            • 0
              Трафик ходит не через директора. Мы же специально создаем loopback, чтобы реальный сервер ловил пакет. Т.е. так как машина считает этот адрес своим, она видимо и отвечает от этого же имени.

              Понаблюдаю завтра, если вам так интересно. Вообще про это в HOWTO должно быть расписано.
  • +1
    А существует ли аналогичный функционал в FreeBSD?
    • +2
      CARP, как мне кажется наиболее близок…
    • 0
      Пример настройки так же здесь
  • 0
    Простой и доступный метод.
    Всегда поражался какими костылями делают это при создании кластеров.
    Кто своё ПО городит, готовые прокси ставит…
    • 0
      Экономные делают LVS или Nginx (но этот не все умеет балансить), чуть более извращенные ставят к примеру HAProxy, более извращенные и богатые ставят Cisco ASA и ему подобные
      • 0
        ASA в целом надежнее получается. Кроме нее есть Cisco CCS и аналогичные решения от Juniper. Преимущества — производительность и надежность. Конфигурируется часто проще (есть подробная документация) Недостаток — цена
        • 0
          А можете рассказать, как такое реализовать на ASA?
          Я их использую только как фаервол на данный момент.
      • 0
        А можете рассказать, как такое реализовать на ASA?
        Я их использую только как фаервол на данный момент.
        • 0
          К сожалению (или к счастью) мы ее не используем, хотя в и планировали. Ввиду отсутствия персонала шарящаго в Cisco отдали связку ASA/CCS сетевикам, они их превратили в «обычный» роутер. Вообще же для балансировки обычно используют CSS, а ASA больше как firewall и немного как HA свитч
          • 0
            HA Router/Firewall (иногда VPN) — для этого и используем их… надо почитать можно ли как ЛБ их юзать
    • 0
      Метод на самом деле не такой уж простой, ибо имеет много подводных камней с собственно TCP/IP. В общем в реализации скорее всего придется посидеть и с tcpdump и многократно покурить ман…
  • +1
    Однозначно статью в избранное, мало того что она трушная, дак еще и на все 100% относится к тематике хабра, а не «как запустить far в linux под wine» =)
  • 0
    Фактически это L4-роутер (я бы сказал что L3, но авторы настаивают на L4)
    Не, реально L4. Свичинг не по IP, а по сочетанию IP:port
    • 0
      Ну авторы на этот счет шутят:

      Layer 4 Switching: Determining the path of packets based on information available at layer 4 of the OSI 7 layer protocol stack. In the context of the Internet, this implies that the IP address and port are available as is the underlying protocol, TCP/IP or UCP/IP. This is used to effect load balancing by keeping an affinity for a client to a particular server for the duration of a connection.

      This is all fine except

      Nevo Hed nevo (at) aviancommunications (dot) com 13 Jun 2001
      The IP layer is L3.

      Alright, I lied. TCPIP is a 4 layer protocol and these layers do not map well onto the 7 layers of the OSI model. (As far as I can tell the 7 layer OSI model is only used to torture students in classes.) It seems that everyone has agreed to pretend that tcpip uses the OSI model and that tcpip devices like the LVS director should therefore be named according to the OSI model. Because of this, the name «L4 switch» really isn't correct, but we all use it anyhow.
  • 0
    Спасибо, познавательно. Было бы интересно понять преимущества этого решения в сравнение с другими.

    1) Если мы говорим о балансировке HTTP трафика, то кой профит по сравнению с Nginx? Балансер Nginx так же имеет единую точку отказа. Но, я так понял, что и LVS решает это проблему, только в сочетание с другими инструментами.

    2) Если говорить о TCP трафике в целом, то что дает LVS в сравнение с HAProxy?

    Теоретически, модуль ядра должен давать лучшею производительность. Но хотелось бы услышать ваше мнение.
    • +1
      Насколько я понял из habrahabr.ru/blogs/sysadm/104621/#comment_3269451, при гигабитных сетевых картах в серверах и необходимости раздавать к примеру 4 гигабита, вам не придется ставить 4 фронтенда/балансера, между которыми снова таки нужно разбрасывать запросы.
    • 0
      Честно говоря не особо вникал в HAProxy, ибо, как мне показалось, он больше заточен на L7 и HTTP. Хотя судя по документации он умеет почти тоже самое что и LVS-NAT. Когда я обратился к этой теме, мне нужно было решение для прозрачного роутинга ssh на менее загруженную машину. И тут LVS, на мой взгляд, достаточно.

      Если рассуждать более общими категориями, то L4-роутер на уровне ядра должен быть в разы быстрее L7-роутера и гораздо лучше масштабироваться. Но соответственно вы теряете все преимущества L7 — анализ заголовков.
  • +1
    Познавательно. Про UltraMonkey читал не так давно.

    В качестве балансировщика именно для HTTP под виндой можно обойтись NLB.

    Немного не понятно, зачем использовать LVS, если есть HAProxy.

    Также хотелось бы узнать о средствах балансировки нагрузки именно RDP-трафика. Я встречал только платные решения типа 2XLoadBalancer.
    • 0
      Win2008, вроде, умеет создавать ферму терминальных серверов из коробки. Или речь не об этом?
      • 0
        Да, Win2008 вроде умеет.
        Интересует балансировка именно на Win2003
        NLB+Session Directory немного не то
        • 0
          Точно умеет. Для win2k3 из работоспособного ничего бесплатнее Citrix за много лет так и не нашли.
    • 0
      К сожалению с RDP помочь не могу. У нас ssh и X11…
  • 0
    спасибо. отличная статья. сам использую для балансироски CSS
  • 0
    Спасибо. Просто и лаконично! Добавил в мемориз.
  • 0
    спасибо
  • 0
    а как быть с субд?
    • 0
      Смотреть в сторону реплакции, я думаю. LVS пожалуй поможет для фермы read-only слэйвов.
      Вообще тема сложная и мной (пока) не изученная.
  • 0
    Кстати, при DNS-RR можно кривенько балансировать нагрузку создавая разное количество RR для каждого из серверов. Т.е. если
    www IN A 1.1.1.1
    www IN A 1.1.1.2
    www IN A 1.1.1.2
    www IN A 1.1.1.2
    То сервер 1.1.1.2 получит в три раза больше трафика чем первый.

    • 0
      А если нагрузку надо перераспределять каждые минут 10? А если в качестве DNS-сервера выступает контроллер домена на винде? :)
      • 0
        Думаю это решаемо скриптом с шедулером. Насколько я знаю, у виндового ДНС есть апи.
        • 0
          Но опять же могут возникнуть проблемы с кэшированием ответов… В общем вроде бы так никто не делает, хотя могу и ошибаться.
    • 0
      это не работает, идентичные A записи игнорируются.
      BIND 9.6
  • НЛО прилетело и опубликовало эту надпись здесь
  • 0
    Да парни, я уже 7 лет сижу на balance-ng — и бед не знаю…
    Сессии шарятся, у серверов есть весовые коэф. и работает безотказно.
    Не скажу что много трафика проходит — ну в среднем 100 мегабит в пике 300-400 это при 100 мегабитных картах и 8 веб серверах на отдачу.
    • 0
      с 4-мя гигабитами не взлетит, например
  • 0
    Простите за возможно глупый вопрос, я не силен в сетях.
    1) Подскажите, как физически соединены Director и Real Server'ы в сеть? У director'а два сетевых ethernet'а, один из которых — для внешнего IP, а другой — в коммутатор с real-серверами?
    2) Одинакова ли будет топология сети (физическая) в схемах DR и NAT или нет?
    3) Правильно ли я понимаю, вопрос ограничения ~64К открытых портов для данной схемы не актуален?
    • 0
      1) Формально они все могут иметь по одной сетевой карте и воткнуты в один и тот же коммутатор. Директором в этом случае будет тот сервер, у которого сейчас VIP, который, в свою очередь, всего лишь alias. 2 сетевые карты на директоре может потребоваться в сценарии NAT.
      2) В DR исходящие пакеты уходят от серверов напрямую, в NAT же все исходящие пакеты идут назад через директор. В этом случае директор выступает в роли роутера в обе стороны.
      3) Честно говоря не задумывался над проблемой. Входящих портов действительно будет не больше ~64К, с исходящими портами не уверен, но вроде бы предпосылок для ограничений нет, кроме очевидного ~64K на сервер.

      Кстати для организации HA вместо UltraMonkey рекомендую Pacemaker, следующая моя статья была как раз про него.

Только зарегистрированные пользователи могут оставлять комментарии. Войдите, пожалуйста.