Имеем:
Основной провайдер — Prov1
Резервный провайдер — Prov2
Хотим:
чтобы оба канала работали одновременно — сам микротик и возможные сервисы за ним были доступны по двум каналом связи независимо друг от друга.
Пользователи выходят в сеть Интернет с основного канала, в случае неработоспособности — с резервного.
Теоретическая основа:
Нужно настроить маркировку входящего соединения, чтобы отслеживать — если запрос пришел с Prov1 то и ответ отправить через Prov1.
Два маршрута по умолчанию с разным «весом» (Distance). Скрипт переключения Distance в зависимости от состояния канала.
Не напутать с таблицами маршрутизации
Что делаем (вариант настройки из WinBox/Web интерфейса):
1
Два маршрута по умолчанию (Dst. Address 0.0.0.0/0) с Comment «Prov1» и «Prov2» соответственно (нужно для работы скрипта), а Distance выставляем для основного -1, для резервного — 2.
2. IP->Firewall->Mangle
добавляем в начало правила маркировки соединения:
General Chain: prerouting Dst. Address: [ip Prov1] In. Interface: [порт подключения Prov1] Action Action: mark_connection New Connection Mark: Prov1_c Passthrough: yes
General Chain: prerouting Dst. Address: [ip Prov2] In. Interface: [порт подключения Prov2] Action Action: mark_connection New Connection Mark: Prov2_c Passthrough: yes
Для всяких случаев продублируем эти правила в chain = input
3. IP->Routes
Добавляем два маршрута по умолчанию, так же как в п.1, только без Comment, а в Routing Mark пишем Prov1 для основного и Prov2 для резервного. Distance=1.
Эти маршруты будут работать только если мы завернем в них трафик создав соответствующие правило (см п.4).
4. IP->Routes->Rules
Создадим правила, заворачивающие помеченные соединения в соответствующие таблицы маршрутов:
Src. Address: [ip Prov1] Dst. Addess: 0.0.0.0/0 Routing Mark: Prov1_r Action: lookup only in table Table: Prov1
Src. Address: [ip Prov2] Dst. Addess: 0.0.0.0/0 Routing Mark: Prov2_r Action: lookup only in table Table: Prov2
И на всякие случаи не помеченные:
Src. Address: [ip Prov1] Dst. Addess: 0.0.0.0/0 Action: lookup Table: Prov1
Src. Address: [ip Prov2] Dst. Addess: 0.0.0.0/0 Action: lookup Table: Prov2
5. IP->Firewall->Mangle
Сразу после правил маркировки соединения пропишем правила маркировки маршрута:
General Chain: prerouting Connection Mark: Prov1_c Action Action: mark routing New Routing Mark: Prov1_r Passthrough: yes
General Chain: prerouting Connection Mark: Prov2_c Action Action: mark routing New Routing Mark: Prov2_r Passthrough: yes
Продублируем в chain=output:
General
Chain: output
Connection Mark: Prov1_c
Action.
Action: mark routing
New Routing Mark: Prov1_r
Passthrough: yes
General
Chain: output
Connection Mark: Prov2_c
Action.
Action: mark routing
New Routing Mark: Prov2_r
Passthrough: yes
6. IP->Firewall->NAT
Два правила маскарадинга для двух исходящих интерфейсов:
General
Chain: srcnat
Out. Interface: [порт подключения Prov1]
Action.
Action: masquerade
General
Chain: srcnat
Out. Interface: [порт подключения Prov2]
Action.
Action: masquerade
Если нужно — правила проброса портов на сервисы DMZ, в двух вариантах — для каждого провайдера, по примеру 5-го пункта этой статьи
После этих настроек у нас должны заработать — сам микротик и настроенные пробросы портов должны заработать независимо на двух каналах связи.
Если что-то не заработало, то скорей всего надо внимательно смотреть таблицы и правила маршрутизации. Правила mangle сами по себе только ставят метки,
а значит если что-то перестаёт работать при вкл/выкл правила в mangle, то виновато не само правило mangle, а то правило, которое использует поставленные метки (или его отсутствие)
Не забываем проверить включен ли Tracking соединений: IP->Firewall->Connections->Tracking
Осталось запилить механизм, который будет переключать основной маршрут в зависимости от состояния каналов.
Один из вариантов скрипта переключения основан на следующем:
- Есть по 3 ip на канал, которые мониторятся средствами ping
- Доступность канала определяется формулой:
MainIfInetOk (($PingResult1 + $PingResult2 + $PingResult3) >= (2 * $PingCount))
$PingCount = количество пинг запросов на хост. Другими словами — канал в порядке, если 2/3 запросов на проверочные хосты прошли.
- При наступлении события, соответственно переключаем Distance маршрута по умолчанию
- Не забываем от flush ить существующие NAT таблицы и IPSec SA (на данный момент существует одно стабильное средство — выкл/вкл интерфейс)
Чтобы ping запросы на проверочные хосты проходили через соответствующие интерфейсы (для основного канала (Prov1) через основные, для резервного (Prov2)- через резервный), нужно
добавить правила маршрутизации отдельно для проверочных хостов. Если вы дочитали до этого места, то уже понимаете как это сделать.
Если нужны скриншоты и/или какие-то пояснения — просьба отписать в комментариях.
Теперь у вас Mikrotik работает на двух провайдерах одновременно, сервисы за NAT доступны одновременно с двух каналов связи, а скрипт резервирования переключает пользовательский трафик на резервный канал в случае падения основного. О том, как сделать балансировку между двумя провайдерами будет отдельная история…
Скрипт резервирования:
#Main interface name :global MainIf ether1-Prov1 #Reserve interface name :global RsrvIf ether2-Prov2 :local PingCount 3 # :local PingTarget1 8.8.8.8 # :local PingTarget2 91.219.24.37 # :local PingTarget3 213.59.5.110 # :local PingTarget1R 194.87.0.50 # :local PingTarget2R 80.68.243.243 # :local PingTarget3R 8.8.4.4 #Check main internet connection :local MainIfInetOk false; :local PingResult1 [/ping $PingTarget1 count=$PingCount interface=$MainIf] :local PingResult2 [/ping $PingTarget2 count=$PingCount interface=$MainIf] :local PingResult3 [/ping $PingTarget3 count=$PingCount interface=$MainIf] :set MainIfInetOk (($PingResult1 + $PingResult2 + $PingResult3) >= (2 * $PingCount)) #Check reserved internet connection :local RsrvIfInetOk false; :local PingResult1 [/ping $PingTarget1R count=$PingCount interface=$RsrvIf] :local PingResult2 [/ping $PingTarget2R count=$PingCount interface=$RsrvIf] :local PingResult3 [/ping $PingTarget3R count=$PingCount interface=$RsrvIf] :set RsrvIfInetOk (($PingResult1 + $PingResult2 + $PingResult3) >= (2 * $PingCount)) :put "MainIfInetOk=$MainIfInetOk" :put "RsrvIfInetOk=$RsrvIfInetOk" if (!$MainIfInetOk) do={ /log error "Main internet connection error" } if (!$RsrvIfInetOk) do={ /log error "Reserve internet connection error" } :local MainGWDistance [/ip route get [find comment="Prov1"] distance] :local RsrvGWDistance [/ip route get [find comment="Prov2"] distance] :put "MainGWDistance=$MainGWDistance" :put "RsrvGWDistance=$RsrvGWDistance" #SetUp gateways if ($MainIfInetOk && ($MainGWDistance >= $RsrvGWDistance)) do={ /ip route set [find comment="Prov1"] distance=1 /ip route set [find comment="Prov2"] distance=2 /interface disable $RsrvIf /ip firewall connection tracking set enabled=no delay 5 /ip firewall connection tracking set enabled=yes /ip ipsec installed-sa flush sa-type=all /log warning "Switch to main internet connection" /interface enable $RsrvIf } if (!$MainIfInetOk && $RsrvIfInetOk && ($MainGWDistance <= $RsrvGWDistance)) do={ /ip route set [find comment="Prov1"] distance=2 /ip route set [find comment="Prov2"] distance=1 /interface disable $MainIf /ip firewall connection tracking set enabled=no delay 5 /ip firewall connection tracking set enabled=yes /ip ipsec installed-sa flush sa-type=all /log warning "Switch to reserve internet connection" /interface enable $MainIf }
А по mikritik балансировке между каналами что-нибудь есть? Это вообще реализуемо между двумя разными провайдерами? А то за два канала платим а работает только один, начальство дало задание: сделать балансировку/распределение между двумя провайдерами именно на микротике …
Да, есть разные варианты по балансировке на микротике, разные алгоритмы. Попробую описать в ближайшем будущем, следите за обновлениями. Например в твиттере
Вы как Азаров: не Mikrotik, а Mikritik.
Извините за оффтоп.
Здравствуйте.
Подскажите как можно реализовать следующую схему подключения на МИкроТике?
Порт 1 — WAN1 — Провайдер №1 — получает адрес от провайдера по DHCP
Порт 2 — WAN2 — Провайдер №2 — получает адрес от провайдера по DHCP
Порт 3 — LAN1 — сеть с адресами 192.168.0.Х — static
Порт 4 — LAN2 — сеть с адресами 192.168.1.Х — static
Порт 5 — LAN3 — сеть с адресами 192.168.2.Х — раздает DHCP
Для LAN1 — основной провайдер WAN1, в случае потери связи переключение на WAN2 (после восстановления связи с провайдером — обратно на WAN1)
Для LAN2 и LAN3 — основной провайдер WAN2, в случае потери связи переключение на WAN1 (после восстановления связи с провайдером — обратно на WAN2)
Если из сети LAN1, LAN3, идет запрос на внешний адрес (на пример) 10.10.10.10 по портам от 1234 до 2345, то пакеты перенаправлять на LAN2 (адрес 192.168.1.5)
И если есть подключения из вне (на адреса WAN1 и WAN2), то также перенаправлять на LAN2 (на пример на адрес 192.168.1.5).
Заранее благодарен!!!
Владимир, это очень интересная задача, но я не готов сейчас разложить ее по полочкам и выдать готовое решение. Можно сказать, что это вполне реализуемо.
Копать нужно в сторону маркировки соединений или пакетов. Создать правила маркировки в IP->Firewall->Mangle, после чего использовать эти отметки в других правилах заворачивая трафик куда нужно, не забывая менять в IP->Firewall->NAT адреса источника и назначения, если это требуется. Скрипт резервирования в этом случае будет сложней, могут быть сложности с тем, что WAN подключается по DHCP, но думаю решение найти можно, поскольку микротик достаточно гибок, а то, что не удается решить предлагаемым интерфейсом можно заскриптовать
вообще-то для правильной работы одновременно по двум провайдерам (имеется ввиду apache за натом) нужно правила в ветке mangle :
сначала марк роутинг
а уж потом марк коннект
кусочек конфига:
/ip firewall mangle
add action=mark-routing chain=prerouting connection-mark=inWAN1 dst-address-list=!local_net log-prefix=skymr new-routing-mark=1WAN src-address-list=local_net
add action=mark-routing chain=prerouting connection-mark=inWAN2 dst-address-list=!local_net log-prefix=tktmr new-routing-mark=2WAN src-address-list=local_net
add action=mark-connection chain=prerouting dst-address=IP_WAN1 in-interface=ether1_wan1 new-connection-mark=inWAN1
add action=mark-connection chain=prerouting dst-address=IP_WAN2 in-interface=ether2-wan2 new-connection-mark=inWAN2
/ip firewall address-list
add address=192.168.1.0/24 list=local_net
add address=192.168.2.0/25 list=local_net
add address=192.168.88.0/24 list=local_net
add address=10.0.1.0/24 list=local_net
Хорошая статья, можно ли все-таки для полноты подкорректировать ее и дописать правила которые нужно «добавить правила маршрутизации отдельно для проверочных хостов.» или отправить на E-Mail.
Тут ничего сложного, просто статические маршруты для проверочных хостов. Например, если проверочный хост 8.8.8.8 для Prov1 то добавить маршрут в main таблицу, где в Distance указывается 8.8.8.8 а next hop — шлюз Prov1
Не могли бы вы написать пример для ввода через окно терминала а то не могу найти где там nexthop задается и с какой версией прошивки вы это настраивали, то есть минимальная достаточная версия для Mikrotik?
/ip route add dst-address=8.8.8.8 gateway=[Prov1 gateway IP]
и далее по всем хостам, выбранных для проверки
Надеюсь понятно, если нет:
http://wiki.mikrotik.com/wiki/Simple_Static_Routes_Example
Теперь понятно, спасибо, а по второму вопросу — на какой версии прошивки у вас это работало?
Версии точно не скажу. На 5.x и 6.x работало
Пытаюсь настроить по вашей конфигурации с двумя ISP 1)Etehrnet static IP, 2)USB 3G modem DHCP IP ppp-out1. При попытке прописать правило Mangle для ppp-out1 что указывать в Dst-address тк если указываешь ppp-out1 ругается, требует IP но IP каждый раз другой?
Понятно в случае динамического белого IP на 3G надо будет для удобства DDNS использовать, чтобы попасть снаружи на него после очередной смены, в случае динамического серого IP снаружи не попасть вовсе, но изнутри в Интернет в любом случае пользователи смогут без проблем ходить, поэтому вопрос остается актуальным — какой писать IP для ppp-out1 в случае динамического?
Андрей, задача у вас интересная, но эта статья Ваш случай не рассматривает. В mangle можно не указывать Ip в distance, указать только интерфейс. Вообще, в случае динамического IP, теоретически два варианта: либо вы указываете только интерфейс, либо, если не везде можно обойтись без явного указания IP, нужен скрипт который будет этот IP определять и создавать нужные правила. Не проще ли запросить у провайдера статический IP? Ведь есть такая услуга даже на обычных тарифах.
В общем то вы правы, однобоко будет без статики — снаружи все равно не зайти будет по резервному каналу, спасибо вам за оперативные ответы на комментарии, тема в статье затронута очень актуальная. Еще бы придумать как 3G не держать постоянно включенным а поднимать только на время сбоя основного канала и выключать потом обратно при восстановлении. А то все эти USB 3G любят подвисать когда долго включенные стоят или очередной костыль делать чтобы питание передергивать периодически.
Настроил, все работает в режиме ETTH static IP + USB 3G static IP.
Компьютеры за роутером работают нормально, запускаю на самом Mikrotik — Check updates — пишет could not resolve address upgrade.mikrotik.com. Запускаю Tools-Ping upgrade.mikrotik.com нормально идет через оба WAN. Вопрос, почему ругается check updates на разрешение имени?
Конечно же я не проверяю доступность самого http сервера upgrade.mikrotik.com с помощью ping а использую этот адрес чтобы сработало разрешение имени и оно работает без проблем.
Сделал в netwatch проверку хоста upgrade.mikrotik.com, резолвится без проблем.
Тут можно посоветовать сохранить текущую конфигурацию, сбросить настройки в заводские, настроить wan обычным образом и проверить check updates. Если ситуация повторяется — можно обратиться к разработчикам, а можно проапдейтить вручную.
Если не повторяется, значит конфигурация как-то мешает этой функции и нужно разбираться детально. Лично я бы не стал тратить на это время — то, что нужно работает, а обновиться можно и вручную.
Конфигурацию уже пробовал сбрасывать, даже делал полную перепрошивку через netinstall без сохранения конфигурации.
IMHO это как то связано с разной логикой разрешения DNS для check updates.
В текущей конфигурации с резервированием DNS для ETTH и 3G интерфейсов не определены, для клиентов DHCP сервера назначаются DNS1 Prov1 и DNS2 8.8.8.8. В таком окружении все встроенные утилиты ping, netwatch могут штатно отрезолвить имя upgrade.mikrotik.com, а check updates как то по другому резолвит. И как всегда вы правы, поскольку этот косяк не критичен для самого резервирования и у клиентов за роутером проблем нет, то как вы и сказали можно забить на него и при необходимости обновляться вручную.
Похоже вы давно занимаетесь администрированием, видно у вас разумную и обоснованную лень 🙂
Еще может подскажете что лучше использовать в качестве хостов для проверки работоспособности каналов. Скажем есть некая удаленная точка (назовем Y) которая цепляется к офису (X). Для проверки наличия доступности канала со стороны Y в сторону X с использованием Prov1 я определил IP gateway X + IP DNS1,2 Prov1 при проверке которых также косвенно проверяется gateway Y. Сам IP X в качестве проверяемого не стал использовать тк если сервер в офисе к которому организовано подключение удаленной точки перегружается или недоступен то и соединяться Y не с кем, поэтому Y перескачет на резервный канал. А в качестве проверочных хостов для 3G (Prov2) использую IP DNS Yandex и Google.
У меня возникает желание использовать что-то другое вместо проверки 2 шт DNS Prov1 тк в принципе один из них может не работать и это допустимо в некоторых случаях.
А скрипт если я правильно понял логику заточен на то чтобы доходило хотя бы 2 из 3 пингов с каждого из 3х хостов? Если по одному из DNS Prov1 может отключать то уже будет похоже на проблемы канала Prov1 и скрипт переключится на Prov2. Вот и хотелось бы может какой трасе запустить из Y в сторону X и по пути какие узлы есть использовать, но маршрут короткий получается типа Y -> gateway Y — X тк провайдер у Х,Y один и тот же.
Что можете посоветовать?
В данном случае это элемент вашего творчества. Можно взять DNS Google и Yandex, но с IP отличными от проверок для Prov2. Можно изменить формулу определения доступности канала, можно изменить количество хостов и/или количество запросов к каждому хосту. И так далее. В статье приведены проверочные хосты, которые на момент применения работали в десятках мест с различными провайдерами и проблем с определением доступности зафиксировано не было.
Добрый день! Небольшое добавление к
«Не забываем от flush ить существующие NAT таблицы и IPSec SA (на данный момент существует одно стабильное средство — выкл/вкл интерфейс)»
Если IPsec демон запущен не на передёргиваемом интерфейсе, SA останутся живыми. Более точный способ flushнуть SA — выкл./вкл. IPsec пира.
Для flush NAT так же можно использовать выкл./вкл. conntrack с задержкой:
ip firewall connection tracking set enabled=no;
delay 1
ip firewall connection tracking set enabled=yes;
Спасибо за дополнение, Илья. Вполне возможно что сейчас, на новых прошивках, работают предложенные вами методы, но на момент написания статьи корректные способы отфлешить NAT не работали. А вот передергивание интерфейса работает стабильно. Думаю, что для надежности можно использовать все способы разом )
Кстати в скрипте так и реализовано:
———————————————
/interface disable $MainIf
/ip firewall connection tracking set enabled=no
delay 5
/ip firewall connection tracking set enabled=yes
/ip ipsec installed-sa flush sa-type=all
/log warning «Switch to reserve internet connection»
/interface enable $MainIf
————————————————————-
Здравствуйте, хотелось бы внести изменения в данный скрипт, чтобы получать уведомления о переключениях каналов с помощью /tool -email через smtp.gmail.com , но есть ограничение. Prov1-основной провайдер и имеет выход только в городскую сеть. Prov2-имеет выход во внешку в тч до smtp.gmail.com. Как бы допилить скрипт, чтобы команда /tool e-mail server=[:resolve smtp.gmail.com] отправляла почту всегда только через Prov2 независимо от состояния основного и резервного канала. Натолкните на истинный путь или может черкнете пару строк как пример.
Разобрался сам — достаточно проверять перед отправкой E-Mail список [:resolve smtp.gmail.com] и добавлять их в routes:
ip route add dst-address=173.194.222.108 gateway=Prov2
ip route add dst-address=173.194.222.109 gateway=Prov2
и т.д.
Но готов посмотреть еще альтернативные решения если кто поделится…
Здравствуйте, вы написали в статье «Если нужно – правила проброса портов на сервисы DMZ, в двух вариантах – для каждого провайдера. После этих настроек у нас должны заработать – сам микротик и настроенные пробросы портов должны заработать независимо на двух каналах связи.»
Не могли бы вы привести пример проброса какого-нибудь одного порта через каждого провайдера чтобы сервис был доступен при заходе с любого из провайдеров.
В ходе настройки вашего решения встретился со странной проблемой. Скрипт просто не выполняется хотя счетчик выполнений растёт. даже поставив в начало скрипта /log error «test» в логах ничего не пишется. Можете подсказать как с этим бороться?
устройство hap AC lite
делает ли
/ip firewall connection tracking set enabled=no
тоже самое что и
foreach i in=[/ip firewall connection find] do={/ip firewall connection remove $i}
это рекомендует volink для правильной работы asterisk при переключении. Без этой строчки ломается связь.
Здравствуйте, вы написали в статье “Если нужно – правила проброса портов на сервисы DMZ, в двух вариантах – для каждого провайдера. После этих настроек у нас должны заработать – сам микротик и настроенные пробросы портов должны заработать независимо на двух каналах связи.”
Не могли бы вы привести пример проброса какого-нибудь одного порта через каждого провайдера чтобы сервис был доступен при заходе с любого из провайдеров.
Andrey, попробую ответить как только появится возможность
Вот новая статья по этому вопросу: http://www.adminhelp.pro/how-to/how-to-mikrotik/1055/
Олег, нет, это не то же самое. Первый вариант работает гораздо надежней и был выбран после тестов второго варианта, который не всегда срабатывал.
Только если я правильно помню нужно так же делать выкл/вкл интерфейса.
Суть действий — отчистить текущие коннекты и разные таблицы, что бы после переключения трафик гарантированно шёл по новым маршрутам, а если в таблицах остаются старые данные — соответствующие коннекты и пакеты будут пытаться идти по старому
не понял, как будет скрипт переключения срабатывать? он же должен переодически запускатьсясам или как?
и как мониторить логи скрипта, т.е. вручную запустил, а рехультат не видно.
Вам просто нужно настроить system => scheduler и там создаете правило с запуском скрипта с определенным интервалом
Добрый день, спасибо большое за статью! За подробное объяснение.
Но возникла одна проблема, когда оба провайдера в рабочем состоянии, и все пользователи идут через основного провайдера, отсутствует доступ к ресурсам сети второго провайдера. Т.е. получается работают они не одновременно, инструкцию перепроверил несколько раз. Причём запрос на второго провайдера приходит (это видно в статистике) но дальше роутера не идёт, либо идёт но через другой шлюз (первого провайдера). Если Вам не сложно, могли бы вы меня натолкнуть что не правильно в настройках. Спасибо.
Прошу расписать инструкцию по «Осталось запилить механизм, который будет переключать основной маршрут в зависимости от состояния каналов.», чтобы не сделать ошибку.
Добрый день, почему то скрипт не отрабатывает хотя статические маршруты указаны на проверочные хосты и даже фаерволом заблокировал пинг на проверочные хосты с разных провайдеров.
Версия 6.38.1
Один из вариантов отладки: вставлять в скрипте строчки вывода в системный лог. Место вставки определяет та часть логики скрипта, отработку которой нужно проверить.
да в скрипте были синтаксические ошибки, видимо связанные с разными версиями ОС /ip ipsec installed-sa flush этого достаточно и sa-type=all указывать не нужно! В дальнейшем я отказался вообще от использования скрипта, настроив резервирование на основе рекурсивных маршрутов с разными значениями distance для основного и резервных каналов. Всё взлетело.
вот пример моего конфига с 6 маршрутами
/ip route
add distance=1 gateway=xxx.xxx.xxx.xxx routing-mark=Prov1
add distance=2 gateway=xxx.xxx.xxx.xxx routing-mark=Prov2
add distance=1 gateway=8.8.8.8
add distance=2 gateway=8.8.4.4
add check-gateway=ping comment=Prov2 distance=2 dst-address=8.8.4.4/32 gateway=xxx.xxx.xxx.xxx scope=10
add check-gateway=ping comment=Prov1 distance=1 dst-address=8.8.8.8/32 gateway=xxx.xxx.xxx.xxx scope=10
Евгений, не могли бы вы привести полный вариант скрипта с проверкой через рекурсивные маршруты?
а сколько занимает время переключения с основного на резервный и происходит ли обрыв сессии? и возможно ли к данному примеру прикрутить тонели ip-to-ip c резервировинием .спасибо
Время будет зависит от того как часто Вы поставите выполнятся скрипт проверки.
Сам скрипт отрабатывает достаточно быстро: 6-10 секунд
Сессия обрывается и не может не обрываться при такой схеме (ведь для внешнего ресурса меняется IP источника). Более того, скрипт это делает нарочно:
/interface disable $MainIf
/ip firewall connection tracking set enabled=no
delay 5
/ip firewall connection tracking set enabled=yes
/ip ipsec installed-sa flush sa-type=all
чтобы переключение на новый канал произошло быстрее (не дожидаясь таймаутов сессии).
Туннели будут восстанавливаться при такой схеме резервирования, если инициатор соединения микротик, а принимающая сторона не привязывается к IP инициатора.
Можно придумать различные схемы резервирования для разных случаев. Но это выходит за рамки статьи.
Ях