Основы iptables
iptables — классический инструмент управления файрволом в Linux: он решает, какие пакеты пропустить, а какие отбросить, разбирая их по цепочкам правил. В этой статье вы разберётесь с цепочками и политиками, научитесь смотреть текущие правила, разрешите доступ по SSH и HTTP, закроете всё остальное политикой DROP по умолчанию и сделаете правила устойчивыми к перезагрузке сервера.
Что понадобится
- VPS ForestsNet Cloud на Ubuntu 22.04/24.04, Debian 11/12 или AlmaLinux/Rocky Linux 8/9.
- Доступ по SSH под
rootили пользователем сsudo.
Шаг 1. Проверьте, что iptables установлен
На Ubuntu и Debian команда iptables обычно уже есть в системе «из коробки» (как обёртка над nftables — iptables-nft, но с привычным синтаксисом). Проверьте версию:
iptables -VЕсли команда не найдена, установите пакет:
Ubuntu / Debian
sudo apt update
sudo apt install iptablesAlmaLinux / Rocky Linux
sudo dnf install iptables⚠️ Важно: AlmaLinux и Rocky Linux по умолчанию используют не iptables, а firewalld (поверх nftables) — проверить, активен ли он, можно командой systemctl status firewalld. Одновременно firewalld и iptables не работают — это два конфликтующих менеджера одного и того же netfilter. Начиная с версии 9 сами утилиты iptables на AlmaLinux/Rocky официально считаются устаревшими (deprecated). Понятия и синтаксис команд из этой статьи (шаги 2–5) верны для iptables на любом дистрибутиве, но как способ настроить файрвол на боевом сервере статья рассчитана на Ubuntu/Debian; на AlmaLinux/Rocky для этого используйте firewalld.
Шаг 2. Разберитесь с цепочками и политиками
iptables фильтрует трафик через таблицы, а внутри таблицы — через цепочки правил. Для файрвола нужна таблица filter (она используется по умолчанию, отдельно указывать её не нужно) с тремя встроенными цепочками:
- INPUT — пакеты, адресованные самому серверу: входящие подключения по SSH, HTTP и т. д.;
- OUTPUT — пакеты, которые генерирует сам сервер: исходящие запросы;
- FORWARD — пакеты, которые сервер пересылает транзитом. На обычном VPS (не роутере) через эту цепочку ничего не идёт.
У каждой встроенной цепочки есть политика по умолчанию — что делать с пакетом, если ни одно правило в цепочке не подошло. Политикой может быть только ACCEPT (пропустить) или DROP (молча отбросить) — REJECT как политику цепочки iptables не принимает, только как цель (target) отдельного правила.
Пока вы не настроили ни одного правила, политика всех трёх цепочек — ACCEPT, то есть разрешено абсолютно всё. Посмотреть текущие политики:
sudo iptables -L -nПервая строка каждой цепочки в выводе выглядит как Chain INPUT (policy ACCEPT) — это и есть текущая политика.
Шаг 3. Посмотрите текущие правила
Более подробный вывод — со счётчиками пакетов/байт и именами интерфейсов:
sudo iptables -L -v -n-L выводит правила (без аргумента — все цепочки таблицы filter), -v добавляет счётчики и интерфейсы, -n — не резолвит адреса и порты в имена (без этого флага вывод может быть заметно медленнее).
Чтобы увидеть номера строк — пригодится перед удалением конкретного правила:
sudo iptables -L -v -n --line-numbersПравило удаляется по номеру строки из этого вывода и имени цепочки: sudo iptables -D <цепочка> <номер> — например, sudo iptables -D INPUT 3 удалит третье правило цепочки INPUT.
А чтобы получить правила в виде готовых команд iptables (удобно скопировать или сравнить с тем, что вы собираетесь применить):
sudo iptables -SШаг 4. Разрешите SSH и HTTP
Прежде чем включать политику DROP (шаг 5), добавьте правила, которые разрешают нужный трафик, — иначе после DROP сервер станет недоступен вообще ни по чему, включая SSH.
Разрешите трафик на loopback-интерфейсе (lo) — им пользуются многие локальные службы:
sudo iptables -A INPUT -i lo -j ACCEPTРазрешите уже установленные и связанные с ними соединения — иначе будут обрываться ответы на исходящие запросы самого сервера (например, к DNS или репозиторию пакетов):
sudo iptables -A INPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPTТеперь разрешите сам SSH и HTTP:
sudo iptables -A INPUT -p tcp --dport 22 -j ACCEPT
sudo iptables -A INPUT -p tcp --dport 80 -j ACCEPTℹ️ Совет: если вы уже меняли порт SSH по умолчанию (см. статью «Усиление SSH»), подставьте вместо 22 свой порт. Если сервер также отдаёт HTTPS, добавьте порт 443 точно так же: sudo iptables -A INPUT -p tcp --dport 443 -j ACCEPT.
ℹ️ Совет: то же самое в ufw делается короче — ufw allow ssh и ufw allow 80/tcp. Если синтаксис iptables кажется избыточным, посмотрите статью «Настройка файрвола UFW»: это дружелюбная надстройка над тем же iptables/nftables, с более простыми командами и готовыми профилями приложений.
Проверьте, что правила добавились:
sudo iptables -L -v -nШаг 5. Включите политику DROP по умолчанию
⚠️ Важно: это самый рискованный шаг статьи — ошибка здесь может отрезать вас от сервера по SSH. Не закрывайте текущую SSH-сессию — откройте отдельное, второе подключение для проверки, и держите под рукой консоль VNC в VMmanager 6: через неё можно зайти на сервер и исправить правила, даже если SSH недоступен.
ℹ️ Совет: дополнительная подстраховка — пока вы не сохранили правила (шаг 6), перезагрузка сервера обычно возвращает политики обратно в ACCEPT. То есть даже полностью ошибочную настройку на этом шаге можно исправить перезагрузкой из VMmanager 6, без переустановки ОС.
Когда правила из шага 4 уже на месте, включите DROP по умолчанию для входящего трафика и транзита:
sudo iptables -P INPUT DROP
sudo iptables -P FORWARD DROPПолитику OUTPUT мы намеренно оставляем ACCEPT — фильтрация исходящего трафика (egress-фильтрация) полезна, но её легко настроить неправильно и сломать себе DNS, обновления пакетов и подобное; это отдельная, более продвинутая тема, которая в эту статью не входит.
Поскольку правило для ESTABLISHED,RELATED уже добавлено, ваша текущая SSH-сессия не оборвётся — политика DROP применяется только к новым соединениям, которые не подошли ни под одно правило. Тем не менее из второй, новой сессии проверьте, что подключение по SSH по-прежнему работает:
ssh [email protected]И посмотрите итоговое состояние:
sudo iptables -L -v -nВ выводе должно быть Chain INPUT (policy DROP) и Chain FORWARD (policy DROP), а выше — ACCEPT-правила для loopback, ESTABLISHED/RELATED, SSH и HTTP.
✅ Готово: новое SSH-подключение открывается, сайт на порту 80 отвечает, а всё остальное входящее — отбрасывается по умолчанию.
Шаг 6. Сохраните правила: iptables-persistent / netfilter-persistent
Правила и политики, которые вы настроили, живут только в памяти ядра — после перезагрузки сервера они слетят, и снова будут действовать политики ACCEPT по умолчанию. Чтобы правила переживали перезагрузку, на Ubuntu/Debian используется пакет iptables-persistent, который ставит системную службу netfilter-persistent:
sudo apt update
sudo apt install iptables-persistentВо время установки пакет дважды спросит, сохранить ли текущие правила — отдельно для IPv4 и отдельно для IPv6. Согласитесь в обоих случаях: IPv4-правила — это как раз то, что вы настроили в шагах 4–5, а пустой набор для IPv6 ничему не помешает, даже если вы им не пользуетесь.
Правила сохраняются в /etc/iptables/rules.v4 (и /etc/iptables/rules.v6 — для IPv6). Убедитесь, что служба, которая подхватывает их при загрузке, включена в автозапуск:
sudo systemctl enable --now netfilter-persistentЕсли после этого вы ещё раз поменяете правила (например, откроете дополнительный порт), не забудьте сохранить их заново — иначе после перезагрузки вернётся старый набор:
sudo netfilter-persistent saveПроверить, что сохранённые правила корректно загружаются, можно без перезагрузки сервера:
sudo netfilter-persistent reloadℹ️ Совет: команда sudo dpkg-reconfigure iptables-persistent в любой момент заново задаёт те же вопросы про сохранение текущих правил, что и при первой установке.
(Этот способ — про Ubuntu/Debian. На AlmaLinux/Rocky, как отмечено в шаге 1, файрволом по умолчанию управляет firewalld, а не iptables-persistent.)
Что дальше
Вы настроили базовый файрвол вручную: цепочки, политика DROP по умолчанию и нужные разрешения (SSH, HTTP) переживают перезагрузку. Тот же результат короче достигается через ufw — дружелюбную надстройку над тем же iptables/nftables. Дальше имеет смысл закрыть подбор пароля по SSH статьёй «Fail2ban», усилить сам SSH — «Усиление SSH», — и свериться с общим «Чек-листом безопасности сервера».