К основному содержимому

Fail2ban: защита SSH и Nginx от подбора паролей

Безопасность · 20.04.2025 · 6 мин чтения
Иллюстрация к статье «Fail2ban: защита VPS от брутфорс-атак»

Каждый публичный VPS ежедневно подвергается тысячам попыток подбора паролей SSH. Fail2ban анализирует логи и автоматически блокирует атакующие IP-адреса.

Установка Fail2ban

sudo apt update
sudo apt install -y fail2ban

sudo systemctl enable fail2ban
sudo systemctl start fail2ban

Настройка защиты SSH

Создайте локальный конфиг (не редактируйте jail.conf — он перезатирается при обновлениях):

sudo nano /etc/fail2ban/jail.local
[DEFAULT]
bantime  = 3600
findtime = 600
maxretry = 5
ignoreip = 127.0.0.1/8 ВАШ_ДОМАШНИЙ_IP

[sshd]
enabled  = true
port     = ssh
filter   = sshd
logpath  = /var/log/auth.log
maxretry = 3
bantime  = 86400
sudo systemctl restart fail2ban

Что означает каждый параметр

ПараметрЗначение в примереСмысл
bantime3600 (для sshd — 86400)На сколько секунд блокируется IP после превышения лимита
findtime600Окно времени в секундах, за которое считаются неудачные попытки
maxretry5 (для sshd — 3)Сколько неудачных попыток допустимо в пределах findtime
ignoreip127.0.0.1/8 и ваш IPАдреса, которые никогда не блокируются

Секция [sshd] переопределяет maxretry и bantime из [DEFAULT] — для SSH их обычно делают строже (меньше попыток, дольше бан), чем общее значение по умолчанию для остальных сервисов.

Типичные ошибки настройки

Неверный logpath для дистрибутива

Путь /var/log/auth.log верен для Debian и Ubuntu. На CentOS, AlmaLinux и других RHEL-подобных дистрибутивах журнал аутентификации лежит в /var/log/secure — с неверным путём Fail2ban запускается без ошибки, но jail никогда не сработает, потому что просто не находит файл для чтения.

# Проверка, что jail реально читает файл логов:
sudo fail2ban-client status sshd
# Строка "File list" должна содержать реальный путь к логу с данными,
# а не путь к пустому или несуществующему файлу

ignoreip без собственного IP

Если не добавить свой рабочий IP в ignoreip, а порог maxretry стоит низким, случайные опечатки в пароле при обычном входе могут забанить вас самих на срок bantime. Особенно опасно при динамическом IP дома — стоит проверять текущий адрес после каждого переподключения провайдера.

На системах, где журнал аутентификации ведётся только через systemd journal без файла /var/log/auth.log или /var/log/secure (некоторые минимальные образы и контейнерные окружения), обычный logpath не сработает вовсе. Для этого случая в jail есть отдельный параметр backend, который читает записи напрямую из journal, а не из файла на диске:

[sshd]
enabled = true
backend = systemd
maxretry = 3

Основные команды

# Статус всех тюрем
sudo fail2ban-client status

# Статус SSH-тюрьмы
sudo fail2ban-client status sshd

# Разблокировать IP вручную
sudo fail2ban-client set sshd unbanip 203.0.113.42

# Посмотреть заблокированные IP
sudo iptables -L f2b-sshd -n --line-numbers

Защита Nginx от DDoS и сканирования

# Добавить в jail.local:
[nginx-http-auth]
enabled  = true
logpath  = /var/log/nginx/error.log

[nginx-botsearch]
enabled  = true
logpath  = /var/log/nginx/access.log
maxretry = 2
✅ Смените порт SSH с 22 на нестандартный (например, 2222) в /etc/ssh/sshd_config — это снизит количество атак на 95%.
⚠️ Перед сменой порта SSH обязательно откройте новый порт в UFW: sudo ufw allow 2222/tcp

Когда Fail2ban не спасёт

  • Распределённый перебор с тысяч разных IP по одной-две попытки с каждого — порог maxretry для отдельного адреса не срабатывает, потому что ни один IP его не превышает.
  • Атака через уязвимость в самом приложении, а не подбор пароля — Fail2ban реагирует на паттерны в логах неудачной аутентификации, а не на произвольные HTTP-запросы без совпадающей сигнатуры фильтра.
  • Вход по скомпрометированному, но действительному паролю или ключу с первой попытки — здесь нечего блокировать по признаку повторных неудач, нужны двухфакторная аутентификация и мониторинг подозрительных входов.

Проверка, что защита работает

  1. Выполните sudo fail2ban-client status sshd — в выводе должен быть корректный путь к логу и растущий счётчик Currently failed после неудачных попыток входа.
  2. С другого IP (не из ignoreip) намеренно введите неверный пароль SSH больше maxretry раз подряд — следующая попытка должна быть отклонена файрволом, а не формой входа.
  3. Проверьте бан в списке: sudo fail2ban-client status sshd должен показать этот IP в Banned IP list.
  4. Разбаньте тестовый IP командой fail2ban-client set sshd unbanip и убедитесь, что подключение снова проходит — это подтверждает, что бан снимается штатно, а не только руками через iptables.

Настройка файрвола, на котором Fail2ban расставляет правила блокировки, разобрана в статье UFW для Ubuntu и Debian, а вход по ключам вместо пароля вовсе убирает необходимость подбора — хардненинг SSH на сервере.

Установка

sudo apt update
sudo apt install fail2ban -y
sudo systemctl enable --now fail2ban

Создание конфига jail.local

Никогда не редактируйте jail.conf — он перезаписывается при обновлении. Создайте jail.local:

># /etc/fail2ban/jail.local
[DEFAULT]
# Время бана в секундах (3600 = 1 час, -1 = навсегда)
bantime  = 3600
# Время поиска попыток (10 минут)
findtime = 600
# Максимум попыток до бана
maxretry = 5
# Исключить свои IP из бана!
ignoreip = 127.0.0.1/8 YOUR.TRUSTED.IP

[sshd]
enabled  = true
port     = 22
logpath  = %(sshd_log)s
maxretry = 3

[nginx-http-auth]
enabled  = true
port     = http,https
logpath  = /var/log/nginx/error.log
maxretry = 5

[postfix-sasl]
enabled  = true
port     = smtp,submission
logpath  = /var/log/mail.log
maxretry = 5
sudo systemctl restart fail2ban

Управление и мониторинг

# Общий статус
sudo fail2ban-client status

# Статус конкретного jail
sudo fail2ban-client status sshd

# Ручной бан IP
sudo fail2ban-client set sshd banip 192.168.1.100

# Разбанить IP
sudo fail2ban-client set sshd unbanip 192.168.1.100

# Посмотреть забаненные IP в iptables
sudo iptables -L f2b-sshd -n -v

# Логи Fail2Ban
sudo journalctl -u fail2ban -f

Мониторинг атак в реальном времени

# Следить за банами SSH в реальном времени
sudo tail -f /var/log/auth.log | grep "Failed password"

# Топ атакующих IP
sudo grep "Failed password" /var/log/auth.log |     awk '{print $(NF-3)}' | sort | uniq -c | sort -rn | head -20
💡 ignoreip — ОБЯЗАТЕЛЬНО: Добавьте свой домашний/офисный IP в ignoreip ПЕРЕД первым запуском. Иначе рискуете забанить себя при отладке. Всегда проверяйте правило дважды.
⚠️ Fail2Ban ≠ полная защита: Брутфорс с тысяч разных IP (botnet) обойдёт Fail2Ban. Дополнительно ограничивайте доступ к SSH по белому списку IP через UFW, или используйте VPN для доступа к серверу.
Статья помогла?
← Назад в базу знаний Задать вопрос поддержке