Скрипт контроля качества 3G Интернет’а на MikroTik

Автор: Андрей Торженов
Данный скрипт устарел и больше не обновляется. Новый скрипт находится в статье: MikroTik. Скрипт контроля мобильного Интернет’а

Обновление от 27/01/2018:

  • Исправлены ошибки проявившие себя в новой версии RouterOS (работа протестирована на ROS 6.41).
  • Убрал автоматическое определение интерфейса через который идёт интернет и который нужно контролировать (интерфейс USB модема). Теперь имя интерфейса необходимо указать вручную (переменная ifName). Данная функция не всегда удобна, по этому решил отказаться от неё.
  • Скрипт больше не поддерживается. Новый скрипт: MikroTik. Скрипт контроля мобильного Интернет’а

Обновление от 03/10/2015:

  • Добавлена возможность получения на email отчёта с 3G модема о уровне сигнала (RSSI), операторе мобильной связи, модели модема и т.д.
  • Проверка присутствия маршрута по умолчанию. Если нет, то перезагрузка. Стала возникать проблема, что PPP соединение поднимается, но иногда, в таблице маршрутизации не появляется маршрут по умолчанию (конечно «Add default route» включено).

Обновление от 09/05/2015:

  • Контроль наличия интерфейсов имя которых, начинается на «wlan» (у меня была проблема, когда данные интерфейсы исчезали и помогала только перезагрузка, похоже проблема была в конденсаторе, его перепояли, но на всякий случай, проверку оставил).
  • Контроль загрузки CPU в течении указанного времени. Если 100%, тогда перезагрузка Mikrotik.
  • ICMP пакеты для тестирования интернет, отправляются только в том случае, если в текущий момент, интернет трафик меньше 30 кбит/с (были проблемы, когда канал забивался на 100% и ICMP пакеты терялись, скрипт считал, что интернет лежит и перезапускал соединение).

Обновление от 26/09/2014:

  • Изменена информация по настройке SMTP. Использование SSL/TLS.

В деревне был налажен интернет и даже установлен офисный телефон, но возникла одна проблема, которая как мне кажется, часто встречается при использовании 3G USB модема.

PPP соединение установлено, но интернета нет или в большинстве случаев интернет есть но с 60-80% потерями пакетов. Иногда данная проблема возникает раз в день, иногда раз в неделю, а бывает и несколько раз за час. Проблему нужно было решать. Необходимо написать скрипт контроля соединения.

В MikroTik для написания скриптов используется язык Lua. Т.к. раньше с данным языком я ни когда не работал и изучил его основы за час-полтора то и скрипт получился простой и не претендующий на гениальность, но свои функции он выполняет.

Что делает скрипт

  • Контроль наличия wlan интерфейса (если нет, перезапуск Mikrotik);
  • Контроль загрузки CPU (если 100% загрузки за указанное время, перезапуск Mikrotik);
  • Контроль наличия маршрута по умолчанию (если нет, перезапуск Mikrotik);
  • Контроль наличия трафика на PPP интерфейсе;
  • Если трафика на PPP интерфейсе нет, то производится тестирование соединения используя ICMP протокол (ping). Если недоступны сразу ДВА хоста, PPP соединение перезапускается;
  • Информация об уровне сигнала 3G модема (RSSI), операторе сотовой связи и т.д.;
  • По всем описанным выше событиям, отправляется отчет на email.

Оборудование

Маршрутизатор MikroTik RB751U-2HnD, ver. 6.32.2

[admin@Saray] > /system resource print
                   uptime: 1h25m23s
                  version: 6.32.2
               build-time: Sep/17/2015 15:20:53
              free-memory: 7.2MiB
             total-memory: 32.0MiB
                      cpu: MIPS 24Kc V7.4
                cpu-count: 1
            cpu-frequency: 400MHz
                 cpu-load: 1%
           free-hdd-space: 109.4MiB
          total-hdd-space: 128.0MiB
  write-sect-since-reboot: 1031
         write-sect-total: 469431
               bad-blocks: 0%

3G USB модем Huawei E392

[admin@MikroTik] > /interface ppp-client info 0
       modem-status: call in progress
         pin-status: no password required
      functionality: full
       manufacturer: Huawei Technologies Co., Ltd.
              model: E392
           revision: 11.833.21.00.143
      serial-number: 861230311471111
   current-operator: Beeline (cellid unknown)
  access-technology: 3G
     signal-strengh: -79 dBm
   frame-error-rate: n/a

Настройка отправки почты через SMTP сервер

В данном случае у меня настроена отправка почты с отчётами через SMTP сервер Yandex’а. К сожалению в address нельзя указать fqdn (доменное имя), пришлось указать IP адрес сервера smtp.yandex.ru.

Судя по changelog, в версии RouterOS 6.32.2 появилась возможность указывать доменное имя (fqdn), а не IP:
What's new in 6.32.2 (2015-Sep-17 15:20):
...
*) email - resolve server address;

Но у меня это не работает, может какой то баг.

P.S. В Changelog на версию Release candidate 6.33rc16 появилось:

*) email - allow server to be specified as fqdn which is resolved on each send;

С 15ого сентября 2014 года, Yandex стал требовать в обязательном порядке  протокол шифрования SSL, в связи с этим, будем настраивать SMTP клиент в Mikrotik с поддержкой данного протокола.

[admin@MikroTik] > /tool e-mail set address=213.180.204.38 port=465 start-tls=tls-only  from=your-login@ya.ru user=your-login@ya.ru password=your-password
[admin@MikroTik] > /tool e-mail print
      address: 93.158.134.38
         port: 465
    start-tls: tls-only
         from: your-login@ya.ru
         user: your-login@ya.ru
     password: your-password
  last-status: succeeded

Проверим отправку почты, отправив тестовое письмо:

/tool e-mail send body=test to=email@your.address

Скрипт контроля качества 3G Интернет’а

Используются два скрипта:

  1. Test-3G-Link — сам скрипт контроля качества;
  2. modemStatus- скрипт получения информации с модема.
##########################
### НАЧАЛО - Настройки ###

# Интерфейс USB модема через который идёт интернет
:global ifName "ppp-out1";

# emailы на которые отправлять отчёты
:global mailAddrTo "user1@test.com";
:global mailAddrCopy "user2@test.ru";

# В течении какого времени (сек) анализируем загрузку CPU
:global sec 3;

# Количество посылаемый icmp пакетов
:local cnt 10;

# Ожидаемое количество вернувшихся пакетов
# В вашем случае, ожидается, что 10 пакетов отправлено и хотя бы 1 должен вернуться
:local cntOkRes 1;

# Первый тестируемый адрес в интернете
:local host1 "ya.ru";

# Второй тестируемый адрес в интернете
:local host2 "8.8.8.8";

### КОНЕЦ - Настройки ###
#########################

# Проверяем, есть ли маршрут по умолчанию
if ([/ip route find where dst-address=0.0.0.0/0] = "") do={
    :log warning "No default gateway. Mikrotik rebooted!";
    /system reboot;
}

# проверяем наличие интерфейсов с именем начинающимся на wlan
:if ( [/interface find name~"wlan"]="")  do={
    /tool e-mail send to=$mailAddrTo cc=$mailAddrCopy body="Wi-Fi interface not found. Mikrotik rebooted!" subject="$[/system identity get name]. Wi-Fi interface not found. $[/system clock get time] $[/system clock get date]"
    :delay 20;
    /system reboot;
}

:delay 1;

# Проверяем загрузку CPU
:global cpu100 0;
for x1 from=1 to=$sec do={
    :if ( [/system resource get cpu-load]="100") do={
        :global cpu100 ($cpu100+1);
    }
:delay 1;
}
:if ( $cpu100 = $sec ) do={
    /tool e-mail send to=$mailAddrTo cc=$mailAddrCopy body="Within $sec seconds, CPU load on Mikrotik: 100%. Mikrotik rebooted!" subject="$[/system identity get name]. CPU load on Mikrotik: 100%. $[/system clock get time] $[/system clock get date]"
    :delay 20;
    /system reboot;
}

# Проверяем имеется ли на сетевом интерфейсе шлюза по умолчанию трафик

# В течении 5 секунд следим за ИСХОДЯЩИМ и ВХОДЯЩИМ трафиком на сетевом интерфейсе
:global wanTrafTx "0";
:global wanTrafTxRes "0";
:global wanTrafRx "0";
:global wanTrafRxRes "0";
for x from=1 to=5 do={
    /interface monitor-traffic [/interface find name=$ifName] once do={
        :global wanTrafTx (tx-bits-per-second / 1024);
    }
    /interface monitor-traffic [/interface find name=$ifName] once do={
        :global wanTrafRx (rx-bits-per-second / 1024);
    }
    if ($wanTrafTx > $wanTrafTxRes) do={
        :global wanTrafTxRes $wanTrafTx;
    }
    if ($wanTrafRx > $wanTrafRxRes) do={
        :global wanTrafRxRes $wanTrafRx;
    }
    :delay 1;
}

# Если трафик на интерфейсе меньше 30кбит/с запускаем проверку ping'ами
if ($wanTrafTxRes < 30 and $wanTrafRxRes < 30) do={
    # Производим тестирование и результаты помещаем в переменные
    :local cntRes1 [/ping count=$cnt $host1];
    :local cntRes2 [/ping count=$cnt $host2];
    # Если из 10ти посланных пакетов вернулось меньше 1, то...
    if ($cntRes1 < $cntOkRes and $cntRes2 < $cntOkRes) do={
        # Делаем запись в log
        :local logmsg ("Internet connection fail! \n\nCPU Load: ".[/system resource get cpu-load]."% \nWAN speed RX: ".[:tonum $wanTrafRxRes]." kbit/s \nWAN speed TX: ".[:tonum $wanTrafTxRes]." kbit/s \nHost - ".[:tostr $host1]." lost ".[:tonum $cnt] - [:tonum $cntRes1]." packets of ".[:tostr $cnt]." \nHost - ".[:tostr $host2]." lost ".[:tonum $cnt] - [:tonum $cntRes2]." packets of ".[:tostr $cnt]."\n");
        :log info $logmsg;
        
        # Отключаем сетевой интерфейс через который идет маршрут по умолчанию
        /interface ppp-client disable [/interface ppp-client find name=$ifName];
        :delay 10;

        # Получаем состояние модема (Запускаем скрипт "modemStatus")
        execute "/system script run \"modemStatus\"";
        :delay 5s;
        :global modemStatus;

        # Включаем сетевой интерфейс
        /interface ppp-client enable [/interface ppp-client find name=$ifName];
        :delay 20;
        # Отправляем email с отчётом
        /tool e-mail send to=$mailAddrTo cc=$mailAddrCopy body="$logmsg$modemStatus" subject="$[/system identity get name]. Internet connection fails! $[/system clock get time] $[/system clock get date]"
    }
}

Из скрипта «Test-3G-Link» происходит вызов скрипта «modemStatus».

:global modemStatus;
:global ifName;
:global rssi;
:global operator;
:local i 0;
/interface ppp-client info $ifName do={
:set i ($i+1);
:if ($i=3) do={
:global rssi "\nSignal: $"signal-strengh"\n";
:global operator "Operator: $"current-operator"";

:set modemStatus "\nModem Status: $"modem-status"\nFunctionality: $"functionality"\nManufacturer: $"manufacturer"\nModel: $"model"\nRevision: $"revision"\nSerial Number: $"serial-number"\nCurrent Operator: $"current-operator"\nAccess Technology: $"access-technology"\nSignal Strength: $"signal-strengh"";

:log info $modemStatus;

:local stop {[:find $"signal-strengh" "dBm";]-1};
:local rssi1 {:tonum [:pick $"signal-strengh" 1 $stop]};

:log info $rssi1;

/system script job remove [find script=modemStatus ];
}}

 

Добавляем скрипты в системные скрипты MikroTik’а

Скрипт удобней добавлять через WinBox. Заходим в меню System > Scripts и нажимаем +. Имя скрипту даём «Test-3G-Link», в дальнейшем оно будет использоваться в настройках планировщика.

Так же поступаем и со скриптом «modemStatus».

Добавление скрипта в MikroTik

Добавление скрипта в MikroTik

Добавляем запуск скрипта в планировщик

Скрипт будет запускаться каждые две минуты.

[admin@MikroTik] > /system scheduler add name="Test-3G-link" interval=5m on-event="/system script run Test-3G-link"
[admin@MikroTik] > /system scheduler print
Flags: X - disabled
 #   NAME                          START-DATE  START-TIME                          INTERVAL             ON-EVENT                           RUN-COUNT
 0   Test-3G-Link                  may/10/2014 17:58:47                            5m                   /system script run Test-3G-link            2

Результаты

Проблемы с Интернет

В случае возникновения проблем будет перезапущенно PPP соединение и в логах MikroTik’а и на почту будут приходить похожие сообщения:

Internet connection fail!

CPU Load: 0%
WAN speed RX: 0 kbit/s
WAN speed TX: 0 kbit/s
Host - ya.ru lost 10 packets of 10
Host - 8.8.8.8 lost 10 packets of 10

Modem Status: ready
Functionality: full
Manufacturer: Huawei Technologies Co., Ltd.
Model: E392
Revision: 11.833.21.00.143
Serial Number: 861230311471111
Current Operator: Beeline (cellid unknown)
Access Technology: 3G
Signal Strength: -73 dBm

100% загрузка CPU

В случае 100% загрузки CPU в течении 3 сек, будет отправлено сообщение на email и перезагружен Mikrotik.

Within 3 seconds, CPU load on Mikrotik: 100%. Mikrotik rebooted!

 

Данный скрипт устарел и больше не обновляется. Новый скрипт находится в статье: MikroTik. Скрипт контроля мобильного Интернет’а
The following two tabs change content below.
В профессиональной сфере занимаюсь всем, что связанно с IT. Основная специализация - VoIP и сети передачи данных. Стараюсь не заниматься Windows серверами (но иногда приходится) и 1С.

Скрипт контроля качества 3G Интернет’а на MikroTik: 20 комментариев

  1. Уведомление: Продолжаем уходить на 2100 МГц | Жизнь радиолюбителей.

  2. eika-inc

    Андрей, спасибо за труды. Затея очень крутая. Будем пробовать ее в деле.

    1. Как тестировать скрипт? В смысле, имитировать проблемы с инетом? Кастрюля с крышкой нужного эффекта не приносят, -89 дбм хватает даже для 3G. Вынимать симку, кажется, тоже некорретно — роутер перестает видеть APN. Так как потестить? И особенно, чтобы был вызван modemStatus?

    2. В шедулере вы создаете таск в нижнем регистре (link). Потом же называете его Link. Вроде как в никсах это разные имена файлов.

    3. Не совсем понял как команда interface ppp-client info 0 прекрасно находит мой модем, хотя называется он ppp-out1. Видимо, после интерфейса указывается не имя, а что-то типа встроенной функции в ОС, и она уже ищет реальный интерфейс. Так что ли?

    Заранее спасибо за ответы и еще раз благодарю за большую проделанную работу.

  3. eika-inc

    И 4-ый пункт.

    К сожалению, на R951Ui-2nD ребут роутера не позволяет модему «почистить карму» (обнулить состояние). RouterOS ребуется, а модем продолжает не видеть сеть. К счастью, в этой модели роутера можно программно снимать питание с USB-порта:

    /system routerboard usb power-reset duration=15s

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

    Модем Huawei E392.

    1. Андрей Торженов Автор записи

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

      В моём случае использовался роутер 751ый (в статье написано об этом), у него нет функции управления питанием USB (http://wiki.mikrotik.com/wiki/Manual:USB_Features#RouterBoard_USB_port_table) по этому в скрипте и не реализована функция usb power-reset.

      1. eika-inc

        Андрей, спасибо.

        Именно так и есть, только причин зависания линка может быть много. И ребут роутера не спасает, что проверено как на Кинетике, так и на Микротике. А вот в 951-ый Микротике (дешевый hAP) эта функция к моему великому счастью есть. И она реально рулит! Я модем мурыжил и так и сяк, часами дергал, вынимал карту, давал ему работать в зеленом режиме и так далее. Из всех попыток только один раз модем не вышел в онлайн с первого раза, но вышел со второго.

        По моей версии вашего скрипта будут замечания? Я не кодер, сделал как понял и смог.

        1. Андрей Торженов Автор записи

          По вашей версии скрипта могу сказать следующее:

          1. У меня бывали случае, что пропадал маршрут по умолчанию и нужно было просто переподключить соединение (disable/enable) и он появлялся (но если не появится, можно дополнить логику работы скрипта, что в этом случае уже будет ресет модема по питанию).
          Каждый раз передёргивать модем по питанию, наверно не очень хорошо. Может и выйти из строя от частого выключения/включения питания, особенно если на морозе. Но если это не часто… то думаю проблем не будет.

          2. Есть ещё вторая часть скрипта, где у вас написано «# Comparing actual traffic with reference value (30 kbps). If less, ping hosts.».
          Там пингуется адрес в интернет и если не отвечает, то соединение тоже перезагружается.
          Туда вы не добавили ресет модема по питанию, хотя ситуация, что маршрут есть, а инет недоступен, т.к. повис модем, тоже может быть.

          Все мои замечания не критичны, если у вас всё работает так, как вам нужно!

          1. eika-inc

            Андрей, спасибо!

            1. В вашей версии скрипта disable/enable соединения при отсутствии дефолтного маршрута тоже нет. Вы ребутаете там Микротик как я помню.

            2. Согласен, что если трафик мелкий, то тоже можно ребутать модем по питани.. Хотя у меня была проблема полной потери линка, а не падения скорости. Но все же ребутать модем по питанию — лучший вариант. Ничего модему не будет от того, что его 2 раза в неделю ребутают. Их руками дергают по 8 раз в день и ничего. Но при ребуте мдема по питанию лечатся сразу все проблемы — запуск на другом (самом скоростном) стандарте сотовой связи, глюки биллинга (возобновление работы после финблокировки), глюки при общении с роутером, выемка симки и так далее. Про разрыв PPP куда менее эффективен и гарантированно не лечит половину из этих проблем.

  4. eika-inc

    Вот моя версия скрипта.

    Взял за основу труд Андрея, убрал проверку WLAN (мне он некритичен), заменил ребут роутера на снятие/подачу питания с USB-порта при пропаже маршрута по-умолчанию и сделал перевод кириллицы на английский, чтобы знаки вопроса в Микротике не раздражали.

    Скрипт по ссылке http://www.netfiles.ru/share/linked/MikroTik-USB-Modem-Script-V2.txt

    Теперь модем при отвале от сети (например, выемкой симки), прекрасно находит сеть опять. С оригинальным скриптом модем оставался в оффлайне навсегда (короткие зеленые моргания) и бесцельно ребутался в 5-минутном цикле.

  5. OpenIDUser

    Скрипт перестал работать на актуальной версии RouterOS. Результат вывода дебага понять не могу — в смысле, не пойму как именно дебаг указывает на проблемы. Кто сможет помочь?

      1. OpenIDUser

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

          1. OpenIDUser

            А скрин, который я привел выше, думаете не из консоли, а из Игр разума? Из того, что мне подсказали на другому форуме — в скрипте есть пробелы после do и отсутствующий знак =, что является нарушением современного синтаксиса. Признавайтесь, не вы писали?

          2. OpenIDUser

            Теперь синтаксис do пофиксен, но скрипт по-прежнему не работает. Вот исправленный код с убранными комментариями для компактности: http://www.netfiles.ru/share/linked/MikroTik-USB-Modem-Script-Vtest.txt

            Email в свойствах Микротика настроен верно, оттуда все ходит норм.

            Попробуйте, пожалуйста, у себя, и увидите, что он не работает (CPU Load и скорости на порту нарочно выставлены в невозможные значения).

Добавить комментарий