Правила з пересиланням усіх портів можуть проковтнути ваш слухач WireGuard
Широке правило пересилання може проковтнути власні слухачі WireGuard і SSH шлюзу. Виберіть вузькі правила або окрему публічну адресу, а потім перевірте шлях керування.
Публічний шлюз уже запускає WireGuard на UDP 51820, SSH на 22 і один застосунок, який має бути доступним з інтернету. Спокусливе правило пересилає кожен порт пирові й оголошує справу зробленою. На шлюзі WireGuard таке правило може перехопити транспорт самого тунелю й замкнути вас поза машиною, яка його завершує. Публікація — це рішення про маршрутизацію з винятком для площини керування, а не один рядок DNAT.
Публічний вхід чи вхід через тунель: виберіть одне
Публікація сервісу створює нову точку входу в інтернеті. Це не те саме, що надати пирові членство у VPN, бо відвідувач ніколи не входить у тунель, а шлюз стає публічним обличчям бекенду. Ця відмінність визначає аудиторію правила та його сертифікат.
Адміністративні інтерфейси рідко доречні на цьому місці. Сторінка адміністрування, до якої доходять авторизовані клієнти VPN, тримає поверхню атаки всередині тунелю й уникає показу форми входу довільному скануванню. Публічним кінцевим точкам застосунку все одно потрібні власний сертифікат TLS, автентифікація й обмеження швидкості; зашифрована ділянка WireGuard не захищає шлях відвідувача до шлюзу.
Якщо сервіс справді має бути публічним, запишіть ім'я хоста, сертифікат, що його покриває, і діапазони відвідувачів, яким треба до нього дістатися. Ці три факти згодом визначають форму правила й політику фільтрації. Усе поза ними — розширення області на публічному слухачі.
Один порт усередину, один бекенд назовні
Використовуйте один публічний порт і один сервіс бекенду. У цьому прикладі eth0 несе публічну адресу 198.51.100.20, адреса тунелю шлюзу — 10.200.0.1, а пир запускає застосунок на 10.200.0.7. Публічний TCP 9443 відображається на TCP 8443 пира:
iptables -t nat -A PREROUTING -i eth0 -d 198.51.100.20 -p tcp --dport 9443 -j DNAT --to-destination 10.200.0.7:8443
iptables -t nat -A POSTROUTING -o wg0 -d 10.200.0.7 -p tcp --dport 8443 -m conntrack --ctorigdst 198.51.100.20 --ctorigdstport 9443 -j SNAT --to-source 10.200.0.1Правило SNAT збігається з трансляційним бекендом та початковим публічним призначенням, тому інше з'єднання до того самого сервісу бекенду лишається поза цим відображенням. Воно також приховує адресу відвідувача від пира, і це той компроміс, через який маршрутизований зворотний шлях зі збереженням джерела стає окремою схемою. Довідка з розширень iptables описує обидві цілі та їхні параметри зіставлення.
Пересилання все одно має бути ввімкнене, а ланцюжку фільтра потрібен дозвіл для трансляційного призначення й порту плюс встановлених відповідей. Ланцюжок FORWARD бачить трансляційне призначення після DNAT, тому правило, написане за публічною адресою, не збігається з пересиланим пакетом. Пишіть дозвіл за кортежем бекенду, а не за публічним.
Пир має приймати з'єднання сервісу з адреси тунелю шлюзу й надсилати відповідь назад через тунель. Його AllowedIPs має авторизувати джерело, яке він справді отримує, а за трансляції джерела це адреса тунелю шлюзу, і широкий запис 0.0.0.0/0 на кожному пирі для цієї схеми не потрібен. Зворотний трафік відкидає пир, у списку якого немає цієї адреси, або схема зі збереженням джерела, яка натомість пересилає адресу самого відвідувача, тож перевіряйте джерело, яке пир справді бачить, а не те, що у вашому правилі.
Тримайте власні слухачі шлюзу поза правилом
Замініть зіставлення порту правилом, що охоплює будь-яке призначення TCP і UDP, і власний сокет WireGuard шлюзу потрапить усередину. Трансляція призначення відбувається до того, як машина вирішить, що пакет локальний, тому UDP 51820 може опинитися в пира, а не в процесу, який тримає всі з'єднання пирів. Правило завантажується успішно, а тунель помирає, і це відмова, яку важко прочитати з боку пира.
SSH, агенти моніторингу та будь-який інший сервіс на шлюзі мають ту саму експозицію. Правило, що пересилає все, не відрізняє площину керування від опублікованого застосунку, і перший перезапуск після зміни — це момент, коли блокування стає очевидним. Правило, що захоплює все, не попереджає про сервіс, який воно тихо забирає. Ви дізнаєтеся про це, коли наступне з'єднання не проходить.
Якщо широке пересилання справді потрібне, зарезервуйте порти керування до правила, що захоплює все, або використайте окрему публічну адресу для публікації. Другий варіант чистіший, бо адреса керування зберігає власну політику, але провайдер має надати цю адресу; додавання запису DNS її не виділяє.
Широке пересилання TCP і UDP — це теж не всі протоколи. ICMP, IPv6, зворотний зв'язок path-MTU і зовнішній транспорт VPN потребують власної політики, а правило, що охоплює TCP і UDP, залишає ці випадки ланцюжку за замовчуванням.
Виберіть модель до того, як писати правила
Чотири форми охоплюють більшість публікацій зі шлюзу, і вибір залежить від того, скільки сервісів ви запускаєте й який ризик у площині керування ви терпите. Таблиця нижче впорядковує їх від найвужчої до найширшої.
| Model | What it protects | Cost | Use when |
|---|---|---|---|
| Narrow port forward | Every other listener, including the VPN | One rule per service | Few services, stable ports |
| Catch-all with reserved ports | Ports named in the exception list | Rule order becomes critical | Many services and disciplined review |
| Separate public address | Control address fully isolated | Provider must supply the address | High-value publication |
| VPN-only access | No public entry at all | Visitors need the tunnel | Admin interfaces and internal tools |
Почніть з вузької моделі, навіть якщо очікуєте більше сервісів пізніше. Її найлегше перевіряти, а перетворити набір вузьких правил на перевірене правило, що захоплює все, простіше, ніж з'ясувати, який слухач захопило широке правило. Яку б модель ви не обрали, тримайте правила у власника міжмережевого екрана. Застосування рядків iptables поряд із конфігурацією UFW або nftables, яка керує тими самими ланцюжками, дає політику, що змінюється залежно від порядку завантаження.
Доведіть і публікацію, і шлях керування
Перевіряйте з авторизованого зовнішнього клієнта, використовуючи схвалене ім'я хоста й дійсний для нього сертифікат. Підтвердьте, який бекенд відповів, потім перевірте, що не пов'язані публічні порти й далі закриті. Вимкнена перевірка сертифіката — це не пройдений тест HTTPS, а з'єднання, що потрапляє не на той бекенд, гірше за невдале.
Після цього перевірте сам шлюз: підключіть пир WireGuard, відкрийте сеанс SSH і переконайтеся, що моніторинг досі звітує. Опублікований сервіс може працювати, поки площина керування зламана, тому обидві перевірки належать до одного вікна змін. Перезавантажте один раз, щоб довести, що правила застосовуються знову в очікуваному порядку, потім зніміть публікацію й переконайтеся, що видалення справді відповідає додаванню. Великий набір додавань під час завантаження з неповним прибиранням — це те, як тимчасова перевірка стає постійною дірою.