Fail2Ban на VPS: защита от bruteforce без лишней магии
VPS с открытым SSH-портом быстро замечается ботами. На сервере счётчик неудачных входов набирает сотни попыток в сутки, а на давно засвеченных адресах – тысячи. Боты работают автоматически и не делают перерывов. Настройка VPS без базовой защиты от перебора – прямое приглашение для таких сканеров.
Оценить масштаб можно без внешних сервисов: откройте журналы за сутки и посмотрите, сколько раз повторяются одни и те же адреса или подсети. У нового сервера первые попытки нередко появляются через несколько минут после выдачи публичного IP. Поэтому Fail2Ban лучше ставить сразу после настройки доступа, а не когда перебор уже попал в мониторинг.
Fail2Ban не заменяет SSH-ключи, отключение входа по паролю и аккуратный firewall, но хорошо снимает самый частый шум от bruteforce: видит повторяющиеся ошибки входа и отправляет подозрительные IP в бан. Ниже – рабочая настройка для Ubuntu 22.04/24.04, Debian 11/12, AlmaLinux 9 и CentOS Stream 9: установка, jail.local, защита SSH и проверка результата.
Что такое Fail2Ban и как он работает?
Fail2Ban работает довольно просто. Этот инструмент на Python читает лог-файлы или systemd journal и ищет строки, похожие на неудачную аутентификацию. Совпало регулярное выражение – счётчик для IP увеличился. Набралось maxretry ошибок за findtime – адрес уходит в firewall на время bantime. Когда срок заканчивается, блокировка снимается автоматически.
Отдельный сервис поднимать не нужно, Fail2Ban использует системный firewall: iptables, nftables или firewalld. Вся защита от bruteforce держится на понятной связке: лог, фильтр, порог срабатывания и действие блокировки.
В конфигурации чаще всего встречаются два термина:
Jail – правило для конкретного сервиса: какие события читать, какие строки считать нарушением и что делать после превышения лимита.
Filter – набор failregex, то есть регулярных выражений для поиска нужных строк в логе. Для SSH, nginx, postfix и других популярных сервисов такие фильтры уже лежат в пакете.
Подготовка VPS перед установкой
Правильная настройка VPS сервера начинается с доступа. Перед установкой нужно оставить себе путь назад: несколько действий занимают пару минут, зато помогают не попасть в классический сценарий, когда защита сработала, но заблокировала самого администратора.
Обновите систему:
# Ubuntu/Debian
sudo apt update && sudo apt upgrade -y
# AlmaLinux 9 / CentOS Stream 9
sudo dnf update -y
Узнайте свой текущий внешний IP. Его необходимо добавить в белый список:
curl -4 https://api.ipify.org
Проверьте, что на сервере есть пользователь с sudo. Работать от root не рекомендуется: ошибка в конфиге или случайная команда могут повлиять на весь сервер.
Чек-лист перед установкой
• SSH-доступ работает; запасная сессия открыта или есть KVM/VNC-консоль в панели провайдера
• Внешний IP известен: curl -4 https://api.ipify.org
• На сервере есть пользователь с sudo
• Если используется UFW на Ubuntu/Debian, проверен его статус: sudo ufw status
• На AlmaLinux 9 / CentOS Stream 9 проверен firewalld: sudo systemctl status firewalld
Установка Fail2Ban на Ubuntu/Debian и AlmaLinux/CentOS
На Ubuntu и Debian пакет есть в стандартном репозитории:
sudo apt install fail2ban -y
/var/log/auth.log может отсутствовать при использовании systemd-journald вместо rsyslog. Если auth.log отсутствует или jail [sshd] не считает попытки входа, задайте backend = systemd. При использовании backend = systemd может потребоваться пакет python3-systemd. На минимальных образах он не всегда установлен:
sudo apt install python3-systemd -y
Проблема с backend может выглядеть так: сервис запущен, jail [sshd] активен, но Currently failed остаётся 0 даже после заведомо ошибочных SSH-входов. В таком случае явно укажите backend = systemd и перезапустите инструмент.
В AlmaLinux 9 и CentOS Stream 9 Fail2Ban обычно ставят через EPEL. Для связки с firewalld понадобится дополнительный пакет fail2ban-firewalld:
sudo dnf install epel-release -y
sudo dnf install fail2ban fail2ban-firewalld -y
На современных системах Fail2Ban также может работать через nftables без fail2ban-firewalld, в зависимости от выбранного banaction.
Запуск и добавление в автозагрузку:
sudo systemctl enable --now fail2ban
Проверка статуса:
sudo systemctl status fail2ban
В статусе нужен Active: active (running). Если сервис упал, первым делом посмотрите последние сообщения unit:
journalctl -u fail2ban -n 50
Базовая конфигурация: jail.local без магии
/etc/fail2ban/jail.conf приходит вместе с пакетом и может измениться после обновления. Свои правила лучше держать в /etc/fail2ban/jail.local: он читается поверх jail.conf и обычно не перезаписывается при обновлениях.
Создаём файл:
sudo nano /etc/fail2ban/jail.local
Секция [DEFAULT] задаёт глобальные параметры для всех jail:
[DEFAULT]
# Адреса из этого списка никогда не блокируются
ignoreip = 127.0.0.1/8 ::1 Ваш_IP
# Время блокировки (s – секунды, m – минуты, h – часы, d – дни)
bantime = 1h
# Временное окно для подсчёта неудачных попыток
findtime = 10m
# Количество неудач до блокировки
maxretry = 5
# Бэкенд чтения логов: auto подходит для большинства систем
backend = auto
ignoreip заполните сразу, до тестов. Добавьте свой IP, а при статическом офисном адресе – ещё и офисную подсеть. Иначе одна серия ошибочных входов может закончиться блокировкой администратора.
bantime определяет срок бана. Десять минут часто слишком мало: бот успевает вернуться с тем же или соседним адресом. Для рабочей SSH-защиты обычно начинают с 1h, а затем повышают до 24h, если ложных срабатываний нет.
findtime и maxretry всегда смотрят вместе. При findtime = 10m и maxretry = 5 адрес блокируется после пяти ошибок за десять минут. Для SSH это нормальный старт: пользователь с опечаткой не страдает, а простой перебор быстро отсекается.
backend = auto автоматически выбирает способ чтения логов в зависимости от окружения. В большинстве случаев этого достаточно, но если SSH-события не обнаруживаются, необходимо указать backend = systemd в нужном jail.
Защита SSH: минимально рабочая конфигурация
Добавьте в jail.local секцию [sshd] для защиты входа по SSH. Обычная настройка fail2ban ssh выглядит так:
[sshd]
# Включаем jail
enabled = true
# Порт SSH (измените, если используете нестандартный)
port = ssh
# Фильтр из /etc/fail2ban/filter.d/sshd.conf
filter = sshd
# Переопределяем глобальные значения для SSH
maxretry = 5
bantime = 24h
Если SSH-события в Ubuntu 24.04 читаются через journal, добавьте в [sshd]:
backend = systemd
Для AlmaLinux 9 и CentOS Stream 9 задайте действие блокировки через firewalld в [DEFAULT] или [sshd]:
# На AlmaLinux / CentOS Stream 9 обычно используется firewalld
banaction = firewallcmd-rich-rules
После правок перезапустите сервис:
sudo systemctl restart fail2ban
Дополнительные jail: nginx, postfix, панели управления
Фильтры для nginx, postfix, dovecot и других сервисов лежат в /etc/fail2ban/filter.d/. Например, для basic auth в nginx можно завести отдельный jail:
[nginx-http-auth]
enabled = true
port = http,https
maxretry = 10
Для ISPmanager, cPanel, Plesk и других панелей универсального фильтра обычно нет. Правила лучше брать из документации панели или репозитория Fail2Ban, а затем прогонять у себя.
Проверка работы и мониторинг
Общий статус всех активных jail:
sudo fail2ban-client status
Статус jail [sshd] показывает, сколько раз правило сработало и какие IP сейчас в бане:
sudo fail2ban-client status sshd
Если sshd не появился в списке jail, чаще всего проблема в jail.local. Проверить конфиг можно без перезапуска:
sudo fail2ban-client -t
Разбанить конкретный IP:
sudo fail2ban-client set sshd unbanip 192.168.1.100
Основной лог – /var/log/fail2ban.log. По строкам Ban и Unban видно, кого заблокировали и когда блокировка закончилась:
sudo tail -50 /var/log/fail2ban.log
Если при реальных атаках строк Ban нет, а Currently failed держится на 0, Fail2Ban смотрит не туда. На системах, где SSH пишет в /var/log/auth.log, фильтр можно проверить так:
# Тест фильтра против реального лог-файла
sudo fail2ban-regex /var/log/auth.log /etc/fail2ban/filter.d/sshd.conf
Типичные ошибки и как их избежать
Самоблокировка при настройке. Две-три ошибки в пароле – и ваш IP уже в бане. Перед тестами держите открытой запасную сессию. Если доступ пропал, зайдите через KVM/VNC в панели провайдера и снимите блокировку:
sudo fail2ban-client set sshd unbanip Ваш_IP
Неверный backend при использовании systemd journal. Если auth.log отсутствует, а backend оставлен auto, jail может не видеть SSH-события. Итог: Currently failed остаётся 0 при реальных неудачных входах. Обычно помогает backend = systemd в [sshd]; на минимальных образах проверьте python3-systemd.
Конфликт с firewalld на AlmaLinux и CentOS. Без fail2ban-firewalld и banaction блокировки через firewalld баны могут появляться в fail2ban.log, но не попадать в реальные правила firewall. Проверьте rich rules:
sudo firewall-cmd --list-rich-rules
Конфликт с UFW на Ubuntu. Если Fail2Ban использует способ блокировки, который не совпадает с активным firewall, правила могут применяться некорректно. Проверьте выбранный banaction и используйте вариант, соответствующий вашему окружению: UFW, iptables, nftables или firewalld.
Слишком низкий maxretry. Значение 1–2 ловит не только ботов, но и людей с одной опечаткой при вводе пароля. Для SSH начинайте с 3–5 попыток; для веб-сервисов с живыми пользователями ставьте порог выше.
Ложные срабатывания. Если под бан попал легитимный пользователь или сервис, чаще всего виноваты слишком строгий maxretry или неподходящий failregex. На системах с /var/log/auth.log проверьте совпадения фильтра:
sudo fail2ban-regex /var/log/auth.log /etc/fail2ban/filter.d/sshd.conf
Если auth.log нет, смотрите SSH-события через journalctl и используйте backend = systemd. Адреса с постоянным административным доступом добавляйте в ignoreip.
Нет ignoreip для офисных адресов. При смене сети или работе из нескольких локаций риск заблокировать себя выше. Если у офиса статический IP, внесите в ignoreip всю офисную подсеть.
Итоговый чек-лист внедрения
1. Сервис стартует вместе с системой, а systemctl status fail2ban показывает active (running)
2. Пользовательские правила лежат в /etc/fail2ban/jail.local, минимум с секциями [DEFAULT] и [sshd]
3. В ignoreip внесены личный IP и административные подсети
4. bantime задан минимум на 1 час
5. Для систем с SSH-логами в systemd journal в [sshd] указан backend = systemd, а python3-systemd установлен или уже пришёл зависимостью
6. Для AlmaLinux 9 / CentOS Stream 9 установлен fail2ban-firewalld, а banaction работает через firewallcmd-rich-rules
7. fail2ban-client status sshd показывает активный jail и реальные счётчики при неудачных входах
Базовая настройка Fail2Ban обычно занимает 15–20 минут. После этого достаточно изредка проверять логи и whitelist, особенно при смене firewall, офиса или сети. Правильная настройка VPS сервера начинается с таких базовых вещей – ещё до деплоя приложения. Боты не ждут, пока вы закончите.



























