The OpenNET Project / Index page

[ новости /+++ | форум | теги | ]

Round Robin балансирование IP адресов исходящих соединений средствами iptables
Данное решение отличается изящностью, так как реализует все средствами iptables. 
Синтаксис: на машине, которая должна балансировать исходящие соединения,
выполнить скрипт balancer.sh:

  sh ./balancer.sh

Выключить балансер:

  sh ./balancer.sh off

Замечание: При работе создается временный файл ~/balancer-rules.sav,
используемый для уборки за собой при выключении балансера.

balancer.sh

   #!/bin/bash

   # Written by Stanislav S. Osipov, [email protected]
   # Created 2010.08.08
   # Script makes SNAT round robin balancing for connections between all real IPA of this host
   #
   # OpenVZ guest warning: you must allow the next options:
   #  IPTABLES="ip_tables iptable_filter iptable_mangle iptable_nat ip_conntrack ipt_conntrack ipt_state"

   myips=`/sbin/ifconfig | /bin/grep "inet a" | /usr/bin/awk "{print \\$2}" | /usr/bin/cut -d: -f2 
   | /bin/grep -v "^127\.\|^10\.\|^192\.168\.\|^172\.\([12][0-9]\|3[01]\)\."`

   myipscount=`/sbin/ifconfig | /bin/grep "inet a" | /usr/bin/awk "{print \\$2}" | /usr/bin/cut -d: -f2 
   | /bin/grep -v "^127\.\|^10\.\|^192\.168\.\|^172\.\([12][0-9]\|3[01]\)\." | /usr/bin/wc -l`

   if [ $myipscount -lt 2 ] && [ "$1" != "off" ]
   then
       /bin/echo "you have not enough IPAs for balancing"
       /bin/echo "I have $myipscount IPAs:"
       /bin/echo $myips
       exit 0
   fi

   #for connections, initiated from this host
   chain="OUTPUT"
   #for connections, initiated by other hosts, which go through this host
   #chain="FORWARD"

   /bin/echo "Cleaning old balancer iptables rules..."
   if [ -e ~/balancer-rules.sav ]
   then
       /bin/cat ~/balancer-rules.sav | /bin/bash
       /bin/echo > ~/balancer-rules.sav
   else
       /bin/echo "No previously dumped rules was found."
   fi
   /bin/echo "Cleaning was done."
   if [ "$1" == "off" ]
   then
       if [ -e ~/balancer-rules.sav ]
       then
           rm ~/balancer-rules.sav
       fi
       exit 0
   fi
   /bin/echo "I have $myipscount IPAs:
   $myips
   Generating and writing mangle table mark logic rules..."
   i=1
   while [ $i -le $myipscount ]
   do
       RULE1="/sbin/iptables -t mangle -A $chain -j CONNMARK --set-mark $i"
       RULE2="/sbin/iptables -t mangle -A $chain -m statistic --mode nth --every $((myipscount-i+1)) -j RETURN"
       /bin/echo $RULE1
       $RULE1
       /bin/echo $RULE2
       $RULE2
       /bin/echo $RULE1 | /bin/sed -e "s# -A # -D #" >> ~/balancer-rules.sav
       /bin/echo $RULE2 | /bin/sed -e "s# -A # -D #" >> ~/balancer-rules.sav
    ((i++))
   done
   /bin/echo "...mangle table mark rules was done."

   /bin/echo "Writing SNAT mark based rules:"
   i=1
   for ip in $myips
   do
       RULE="/sbin/iptables -t nat -A POSTROUTING -m connmark --mark $i -j SNAT --to $ip"
       /bin/echo $RULE
       $RULE
       /bin/echo $RULE | /bin/sed -e "s# -A # -D #" >> ~/balancer-rules.sav
       ((i++))
   done
   /bin/echo "...nat table SNAT rules was done.
   Round robin balancer is turned on.
   Thank you for using this script written by Stanislav S. Osipov!"


Как проверить

Создать файл в DocumentRoot на какой-нить машине с апачом такого вида: `ip.php`:

   <?
   echo $_SERVER['REMOTE_ADDR']."\n";
   ?>

И запустить такой тест с машины, которая работает с правилами балансера (для
успешного теста на машине должна стоять библиотека libwww-perl):

   i=1; count=20; url="http://my.www.ru/ip.php"; while [ $i -lt $count ]; do GET "$url"; ((i++)); done

Как выглядит в работе

   root@h1:~# i=1; count=10; url="http://my.www.ru/ip.php"; while [ $i -lt $count ]; do GET "$url"; ((i++)); done
   
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214

   root@h1:~# ./balancer.sh

   Cleaning old balancer iptables rules...
   No previously dumped rules was found.
   Cleaning was done.
   I have 3 IPAs:
   95.239.178.214
   95.239.178.220
   95.239.178.221

   Generating and writing mangle table mark logic rules...
   /sbin/iptables -t mangle -A OUTPUT -j CONNMARK --set-mark 1
   /sbin/iptables -t mangle -A OUTPUT -m statistic --mode nth --every 3 -j RETURN
   /sbin/iptables -t mangle -A OUTPUT -j CONNMARK --set-mark 2
   /sbin/iptables -t mangle -A OUTPUT -m statistic --mode nth --every 2 -j RETURN
   /sbin/iptables -t mangle -A OUTPUT -j CONNMARK --set-mark 3
   /sbin/iptables -t mangle -A OUTPUT -m statistic --mode nth --every 1 -j RETURN
   ...mangle table mark rules was done.
   Writing SNAT mark based rules:
   /sbin/iptables -t nat -A POSTROUTING -m connmark --mark 1 -j SNAT  --to 95.239.178.214
   /sbin/iptables -t nat -A POSTROUTING -m connmark --mark 2 -j SNAT --to 95.239.178.220
   /sbin/iptables -t nat -A POSTROUTING -m connmark --mark 3 -j SNAT --to 95.239.178.221
   ...nat table SNAT rules was done.
   Round robin balancer is turned on.
   Thank you for using this script written by Stanislav S. Osipov!

   root@h1:~# i=1; count=10; url="http://my.www.ru/ip.php"; while [  $i -lt $count ]; do GET "$url"; ((i++)); done

   95.239.178.214
   95.239.178.221
   95.239.178.220
   95.239.178.214
   95.239.178.221
   95.239.178.220
   95.239.178.214
   95.239.178.221
   95.239.178.220

   root@h1:~# ./balancer.sh off

   Cleaning old balancer iptables rules...
   Cleaning was done.

   root@h1:~# i=1; count=10; url="http://my.www.ru/ip.php"; while [ $i -lt $count ]; do GET "$url"; ((i++)); done

   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
   95.239.178.214
 
09.08.2010 , Автор: Stanislav S. Osipov , Источник: http://wiki.opennet.ru/Iptables/net...
Ключи: iptables, balance, netfilter
Раздел:    Корень / Администратору / Сетевая подсистема, маршрутизация / Пакетные фильтры и фаерволы / Пакетные фильтры в Linux: iptables, ipchains

Обсуждение [ Линейный режим | Показать все | RSS ]
  • 1.1, prapor (??), 23:09, 09/08/2010 [ответить] [﹢﹢﹢] [ · · · ]  
  • +/
    В результате регулярно начинают отваливаться некоторые сервисы, расчитанные на привязку к IP без keep-alive. Так что пользоваться осмотрительно.
     
  • 1.2, mma (?), 09:40, 10/08/2010 [ответить] [﹢﹢﹢] [ · · · ]  
  • +/
    а в чем приемущество данного решения против множественных таблиц маршрутизации и балансировки использую iproute2? Я так понимаю тут речь идет о round-robin NAT?
     
     
  • 2.6, artickl (?), 20:06, 10/08/2010 [^] [^^] [^^^] [ответить]  
  • +/
    насколько я помню, через iptables2 если уже был пакет на какой-то ip, то он всегда будет идти через тот же интерфейс... то есть балансировка не совсем равномерная, если скажем на один и тот же сайт постоянно заходят из подсети...

    если не прав - поправьте...

     
     
  • 3.9, mma (?), 10:59, 11/08/2010 [^] [^^] [^^^] [ответить]  
  • +/
    в любом случае round-robin NAT это разброс соединений на этапе их инициализации, когда оно установлено соединение работает через тот интерфейс через который было установлено. Иначе никак. Сами подумайте как принимающая сторона поймет от кого пришел пакет если вы будет каждый следующий пакет слать через отдельный интерфейс. Пока у вас не будет автономной системы никакой балансировки реальной вы не получите.

    А вообще iptables использовть для этого это в рядовом случае как вырезать аппендицит бензопилой, iproute2 вам в помощь

     

  • 1.4, im (??), 18:39, 10/08/2010 [ответить] [﹢﹢﹢] [ · · · ]  
  • +/
    Скрип "убивает" уже первыми строчками:
    myips=…
    myipscount=…
    Сама идея погребена в тонне кода.
    "Thank you for using this script written by" - да ну нафиг :)
    Да, изящностью тут и не пахнет :)
     
  • 1.5, artickl (?), 20:02, 10/08/2010 [ответить] [﹢﹢﹢] [ · · · ]  
  • +/
    Я бы еще exeption'ы для каждого IP бы сделал
    типа smtp пускать только через этот ip, на этот ip обращаться только с этого интерфейса и так далее... а так - возьму на заметку
     
  • 1.8, rxx_void (??), 09:51, 11/08/2010 [ответить] [﹢﹢﹢] [ · · · ]  
  • +/
    уже где то писал, но повторюсь : на что только не идут люди что бы не покупить циску :)
     
     
  • 2.10, mma (?), 11:01, 11/08/2010 [^] [^^] [^^^] [ответить]  
  • +/
    на что маркетологи циски только не идут чтобы люди покупали не только роутеры но и их мыльницы.


     
  • 2.11, Аноним (11), 21:11, 14/08/2010 [^] [^^] [^^^] [ответить]  
  • +/
    И на то у вас машина есть? (c)
     
  • 2.12, Аноним (11), 22:38, 14/08/2010 [^] [^^] [^^^] [ответить]  
  • +/
    >уже где то писал, но повторюсь : на что только не идут
    >люди что бы не покупить циску :)

    Что только цисководы не купят, чтоб мозгами не работать.

     
     
  • 3.13, ananaskin (?), 00:07, 17/08/2010 [^] [^^] [^^^] [ответить]  
  • +/
    там, это есть --random опция, что-бы раскидывать по дестинейшиенам через раун робин. И весь скрипт сводится к 1 правилу. Почитай рассылку, так они зыбыли это задокументировать.
     
     
  • 4.14, Аноним (11), 00:17, 18/08/2010 [^] [^^] [^^^] [ответить]  
  • +/
    таки верю, но циску не куплю - привык все делать линуксом :-b

    ключевое слово "все"

     

  • 1.15, Anonym (?), 16:30, 28/08/2010 [ответить] [﹢﹢﹢] [ · · · ]  
  • +/
    Использовать ifconfig не очень корректно, он может не отображать некоторые IP адреса. ip - наше всё, например как-нибудь так
    ip a | awk '/inet /&&!/ lo/{print $2}' | cut -d/ -f1
     
     
  • 2.16, demoflymail.ru (?), 13:05, 01/11/2010 [^] [^^] [^^^] [ответить]  
  • +/
    Вы абсолютно правы, спасибо!
     


     Добавить комментарий
    Имя:
    E-Mail:
    Заголовок:
    Текст:




    Партнёры:
    PostgresPro
    Inferno Solutions
    Hosting by Hoster.ru
    Хостинг:

    Закладки на сайте
    Проследить за страницей
    Created 1996-2024 by Maxim Chirkov
    Добавить, Поддержать, Вебмастеру