vps·web
PL

Proxmox Port Forwarding

Proxmox Port Forwarding na iptables — przekierowanie portów

Serwery · Proxmox Port Forwarding

Proxmox Port Forwarding na iptables — przekierowanie portów do VM krok po kroku

Proxmox Port Forwarding na iptables pozwala wystawić usługę działającą wewnątrz VM-ki lub kontenera LXC na publiczny internet przez jeden adres IP hosta. Schemat jest prosty — reguła PREROUTING z DNAT na vmbr0, pasująca reguła FORWARD, oraz POSTROUTING MASQUERADE dla prywatnej podsieci — ale zapomniany ip_forward = 1, brakujący moduł conntrack albo luka w hairpin NAT po cichu wszystko psują. Ten artykuł prowadzi przez pełną konfigurację: reguły, które każdy host Proxmox powinien mieć w /etc/iptables/rules.v4, błędy, na które się natkniesz gdy coś się rozjedzie, i pokazuje jak generator Proxmox Port Forwarding na vps-web.com napisze te reguły za Ciebie w prawidłowej kolejności.

Generator Proxmox Port Forwarding — co robi i komu się przyda

Generator na vps-web.com produkuje komplet reguł iptables do przekierowania publicznego portu hosta Proxmox na port VM-ki lub kontenera siedzącego na prywatnym moście (typu vmbr1). Wypełniasz protokół (TCP albo UDP), publiczny adres IP i port, lokalny adres IP i port, nazwy interfejsu publicznego i lokalnego, oraz kolejność reguły w łańcuchu IPTables. Output to cztery bloki: reguła PREROUTING z DNAT, reguła FORWARD z dopasowaniem conntrack, reguła POSTROUTING MASQUERADE dla hairpin NAT, oraz komendy utrwalające konfigurację (iptables-save plus instalacja iptables-persistent). Kopiujesz je do shella albo wkładasz w post-up w /etc/network/interfaces — gotowe.

Narzędzie jest dla admina prowadzącego Proxmox VE na jednym publicznym IP — dedyk z Hetznera, OVH, Scaleway, domowe laboratorium z jednym łączem, albo jakiekolwiek środowisko gdzie trzeba rozłożyć jeden publiczny adres na kilka wewnętrznych usług. Przydaje się też przy budowaniu sieci NAT-only za prywatnym mostem (vmbr1, 192.168.x.0/24 albo 10.x.0.0/24), w której SSH na porcie 2222 ma trafiać do VM-ki A, HTTP na 8080 do kontenera B, a serwer gry na UDP 27015 do VM-ki C — wszystko na jednym publicznym IP.

To, co generator faktycznie oszczędza, to czas. Reguły iptables są pozycyjne, różnica między -A (append, dołącz na koniec) a -I 1 (insert, wstaw na pozycję 1) ma znaczenie, a kolejność wpisów w łańcuchu NAT względem FORWARD decyduje o tym, czy pakiet w ogóle dotrze do VM-ki, czy padnie na domyślnym DROP gdzieś po drodze. Formularz zakodował tę kolejność za Ciebie.

Praktyka — przekierowanie portu z hosta Proxmox do VM-ki

Cel: host Proxmox VE 8.x i 9.x z jednym publicznym IP na vmbr0 i prywatnym mostem vmbr1 obsługującym podsieć 192.168.23.0/24. Pojedyncza VM-ka pod adresem 192.168.23.10 ma demona SSH na porcie 22 i chcemy ją wystawić na świat na porcie 5829, tak żeby ssh -p 5829 user@public-ip lądowało na VM-ce. Ten sam przepis działa identycznie dla serwerów WWW, pocztowych, gier i każdej innej usługi TCP albo UDP.

Krok 1 — sprawdzenie IP forwardingu i mostów

Jądro nie przerzuci pakietu między interfejsami, dopóki net.ipv4.ip_forward nie jest ustawione. Sprawdź to zanim napiszesz pierwszą regułę:

sysctl net.ipv4.ip_forward

Jeśli zwróci 0, włącz na stałe w /etc/sysctl.conf (albo w drop-inie pod /etc/sysctl.d/):

echo "net.ipv4.ip_forward = 1" >> /etc/sysctl.conf
sysctl -p

Potwierdź, że mosty są up. vmbr0 to most publiczny z IP hosta i bramą domyślną. vmbr1 to most wewnętrzny — bez bridge-ports, z adresem RFC 1918, do którego podpięta jest karta VM-ki. Minimalny /etc/network/interfaces wygląda tak:

# /etc/network/interfaces

auto vmbr0
iface vmbr0 inet static
    address 51.75.74.52/24
    gateway 51.75.74.1
    bridge-ports eno1
    bridge-stp off
    bridge-fd 0

auto vmbr1
iface vmbr1 inet static
    address 192.168.23.1/24
    bridge-ports none
    bridge-stp off
    bridge-fd 0

Host trzyma 192.168.23.1 na vmbr1. VM-ka używa tego adresu jako bramy domyślnej i bierze adres z tej samej /24 dla siebie.

Krok 2 — instalacja iptables-persistent

Proxmox dostarcza iptables, ale bez warstwy utrwalającej reguły. Bez iptables-persistent każdy reboot wywala wszystko co napisałeś. Zainstaluj teraz, żeby reguły przeżyły restart:

apt-get update
apt-get install -y iptables-persistent

Instalator zapyta, czy zapisać bieżące reguły do /etc/iptables/rules.v4 i rules.v6. Zatwierdź. Pakiet doda jednostkę systemd (netfilter-persistent.service), która przy bootowaniu wczytuje reguły z tych dwóch plików. To do tego mechanizmu podłącza się każde późniejsze iptables-save > /etc/iptables/rules.v4.

Krok 3 — NAT wyjściowy dla podsieci prywatnej

Zanim zaczniesz przekierowywać ruch wchodzący, VM-ki potrzebują wyjściowego internetu. To rola reguły MASQUERADE, która przepisuje źródłowy adres każdego pakietu wychodzącego przez vmbr0 z zakresu 192.168.23.0/24 na publiczny IP hosta:

iptables -t nat -A POSTROUTING -s '192.168.23.0/24' -o vmbr0 -j MASQUERADE

Po tej regule ping 1.1.1.1 z wnętrza VM-ki przechodzi przez host, dostaje przepisany adres źródłowy, a odpowiedź wraca poprawnie. Bez tej reguły VM-ka nie ma internetu w ogóle i nic dalszego w tym poradniku nie zadziała.

Krok 4 — DNAT ruchu wchodzącego do VM-ki

To serce port forwardingu. Pakiet przylatuje na publiczny interfejs, kierowany do hosta na TCP/5829. Reguła DNAT przepisuje cel pakietu na prywatny adres i port VM-ki:

iptables -t nat -I PREROUTING 1 -d 51.75.74.52 -p tcp --dport 5829 \
    -j DNAT --to-destination 192.168.23.10:22

Kilka dyrektyw, które warto zrozumieć:

  • -t nat — reguła ląduje w tabeli nat, gdzie odbywa się translacja adresów. Domyślna tabela filter służy do decyzji ACCEPT/DROP, nie do przepisywania.
  • -I PREROUTING 1 — wstaw na pozycję 1 w łańcuchu PREROUTING. DNAT musi zadziałać przed decyzją routingu jądra, inaczej pakiet poleci na lokalny stos hosta zamiast zostać przekierowany.
  • -d 51.75.74.52 — dopasuj tylko pakiety kierowane na publiczny IP. Bez tego dowolny pakiet przylatujący na host na TCP/5829 (w tym z wewnętrznej sieci) zostałby zNAT-owany, co psuje hairpin.
  • -p tcp --dport 5829 — dopasowanie protokołu i portu docelowego.
  • -j DNAT --to-destination 192.168.23.10:22 — akcja: przepisz cel na VM-kę. Zauważ, że port publiczny (5829) i lokalny (22) mogą się różnić — w tym cały sens, mapujesz zewnętrzny 5829 na wewnętrzny 22.

Krok 5 — reguła FORWARD z conntrack

DNAT przepisuje adres, ale pakiet wciąż potrzebuje zgody jądra na opuszczenie jednego interfejsu i wejście na drugi. Tym zajmuje się łańcuch FORWARD. Przy domyślnej polityce DROP w filter chain potrzeba jawnego ACCEPT:

iptables -I FORWARD 1 -i vmbr0 -o vmbr1 -d 192.168.23.10 -p tcp --dport 22 \
    -m conntrack --ctstate NEW,ESTABLISHED,RELATED -j ACCEPT

Dopasowanie conntrack gwarantuje, że przejdą tylko pakiety w prawidłowych stanach TCP. NEW przepuszcza SYN, ESTABLISHED obsługuje trwające połączenia, RELATED pokrywa rzeczy typu błędy ICMP związane z połączeniem. Bez conntrack musiałbyś pisać osobną regułę dla każdego kierunku ruchu; z nim jedna reguła pokrywa oba kierunki tego samego strumienia.

Krok 6 — hairpin NAT (opcjonalnie, ale często potrzebny)

Jeśli host z wnętrza 192.168.23.0/24 spróbuje sięgnąć na publiczny IP, port 5829, pakiet trafi w regułę DNAT, dostanie przepisany cel na 192.168.23.10:22, a VM-ka zobaczy w polu źródła oryginalny prywatny IP nadawcy. Odpowiedź pójdzie bezpośrednio z powrotem do nadawcy — omijając hosta — a stos TCP nadawcy odrzuci ją, bo wraca z innego adresu niż ten, do którego wysyłał. To klasyczny bug NAT hairpin / NAT loopback.

Lekarstwo to reguła POSTROUTING, która przepisuje źródło ruchu wewnątrz-wewnętrznego (idącego przez DNAT) na adres hosta z vmbr1:

iptables -t nat -I POSTROUTING 1 -s '192.168.23.0/24' -d 192.168.23.10/32 \
    -o vmbr1 -j MASQUERADE

Teraz VM-ka widzi w źródle adres hosta 192.168.23.1 i odpowiada przez hosta zgodnie z oczekiwaniem. Ta reguła jest potrzebna tylko jeśli faktycznie masz usługi w tej samej prywatnej sieci sięgające do siebie przez publiczny IP — w przeciwnym razie pomiń.

Krok 7 — utrwalenie reguł

Reguły zbudowałeś w pamięci jądra. Po reboocie znikną, chyba że je zapiszesz:

iptables-save > /etc/iptables/rules.v4

Sprawdź, że plik wygląda jak należy:

cat /etc/iptables/rules.v4

Powinieneś zobaczyć swoje wpisy PREROUTING, FORWARD i POSTROUTING plus to, co tam już było. Przy następnym bootowaniu netfilter-persistent je przywróci.

Jeśli wolisz starszy schemat — wrzucanie komend do /etc/network/interfaces jako post-up — też działa, ale iptables-persistent jest czystszy dla każdego zestawu reguł większego niż kilka linii. Oficjalna dokumentacja iptables na netfilter.org opisuje model w detalu, jeśli chcesz spojrzenia upstream.

Krok 8 — test z zewnątrz

Z maszyny, która nie jest w lokalnej sieci hosta, uruchom:

ssh -p 5829 user@51.75.74.52

Jeśli zobaczysz banner SSH VM-ki — gotowe. Jeśli Connection refused, demon sshd na VM-ce nie działa albo nie nasłuchuje na wszystkich interfejsach. Jeśli Connection timed out, blokuje gdzieś firewall (tabela filter na hoście, lokalny firewall VM-ki, firewall datacenter wyżej). Sekcja „Częste błędy" niżej rozbiera każdy przypadek.

Częste błędy i pułapki

net.ipv4.ip_forward = 0

Najczęstszy jednolinijkowy bug. Pakiety przylatują na publiczny interfejs, dostają zNAT-owane i… stoją, bo jądro nie przerzuci ich między interfejsami. Objaw: ssh -p 5829 wiesza się i timeoutuje, a w iptables -t nat -L -v -n liczniki pakietów na łańcuchu FORWARD nie rosną. Naprawa: sysctl -w net.ipv4.ip_forward=1 i utrwalenie w /etc/sysctl.conf.

Zła kolejność reguł — DNAT po FORWARD DROP

Jeśli masz domyślną politykę FORWARD ustawioną na DROP i reguła ACCEPT dla przekierowanego ruchu ląduje za ogólnym DROP, pakiet leci do śmietnika zanim dotrze do ACCEPT. Uruchom iptables -L FORWARD -v -n --line-numbers i obejrzyj kolejność. Naprawa: wstaw ACCEPT przez -I FORWARD 1, żeby siedziało na samej górze łańcucha.

Nie wyłączyłeś firewalla Proxmoxa

Własny pve-firewall w Proxmoxie przepisuje iptables na warstwie nad Twoimi regułami. Jeśli pve-firewall status pokazuje enabled, a po systemctl restart pve-firewall Twoje ręczne reguły znikają — to właśnie ten powód. Albo wyłącz firewall Proxmoxa (systemctl stop pve-firewall && systemctl disable pve-firewall) i jedź na czystym iptables, albo dodaj DNAT przez pliki konfiguracyjne firewalla Proxmoxa — ale nie mieszaj obu podejść w sposób doraźny.

iptables: No chain/target/match by that name

Pojawia się gdy moduł jądra nie jest załadowany — najczęściej nf_nat, nf_conntrack albo xt_conntrack. Uruchom modprobe nf_conntrack nf_nat i sprawdź lsmod | grep conntrack. Na okrojonych kernelach te moduły wymagają jawnego ładowania. Dorzuć je do /etc/modules-load.d/iptables.conf, żeby ładowały się przy boocie.

VM-ka nie ma bramy domyślnej wskazującej na hosta

VM-ka pod 192.168.23.10 musi mieć jako bramę domyślną 192.168.23.1 — adres hosta Proxmox na vmbr1. Jeśli wskazuje na własną kartę, na 8.8.8.8 albo nie ma bramy w ogóle, odpowiedzi z VM-ki nigdy nie wrócą przez hosta i z perspektywy klienta połączenie się wieszać. Na VM-ce z rodziny Debiana edytuj /etc/netplan/*.yaml albo /etc/network/interfaces. Zweryfikuj wewnątrz VM-ki przez ip route show.

MASQUERADE na złym interfejsie

Jeśli wpiszesz -o vmbr1 zamiast -o vmbr0 w regule wyjściowej MASQUERADE, pakiety wychodzące przez publiczny interfejs zachowają prywatny adres źródłowy, a brama upstream je odrzuci. Objaw: VM-ki nie mają internetu, ale ruch VM-VM i VM-host działa. Naprawa: zmień -o vmbr1 na -o vmbr0 w regule POSTROUTING.

Firewall datacenter blokuje port publiczny

Hetzner, OVH i kilka innych providerów ma upstreamowy firewall (typu „Robot", „vRack") filtrujący ruch zanim w ogóle dotrze do hosta. Twoje iptables mogą być idealne, a pakiet i tak nie przyleci. Objaw: tcpdump -i vmbr0 port 5829 na hoście pokazuje zero pakietów przy próbie połączenia z zewnątrz. Sprawdź panel providera pod kątem reguł firewalla na tym publicznym IP.

Hairpin NAT nie działa — wewnętrzne hosty nie sięgają do publicznego IP

Z zewnątrz SSH działa, ale z drugiej VM-ki w tym samym vmbr1 już nie. DNAT poprawnie przepisuje cel, ale odpowiedź VM-ki leci bezpośrednio do nadawcy z prywatnym adresem, omijając źródłowy NAT. Naprawa: dodaj regułę hairpin POSTROUTING MASQUERADE dla ruchu, w którym źródło i cel siedzą w tej samej prywatnej sieci — dokładnie tak, jak emituje to generator Proxmox Port Forwarding w bloku HAIPIN.

FAQ — najczęściej zadawane pytania

Czy mogę przekierować ten sam publiczny port do dwóch różnych VM-ek?

Nie. Pojedyncza reguła PREROUTING DNAT mapuje jedną kombinację publicznego IP + portu + protokołu na jeden cel prywatny. Jeśli potrzebujesz dwóch VM-ek odpowiadających na ten sam zewnętrzny port, masz dwie drogi: nadać im osobne publiczne IP i przekierować każdy niezależnie, albo postawić reverse proxy (nginx, HAProxy, Traefik) z przodu i niech ono routuje po nazwie hosta albo ścieżce.

Jak przekierować port UDP zamiast TCP?

Zmień -p tcp na -p udp zarówno w regule PREROUTING DNAT, jak i w regule FORWARD ACCEPT. UDP nie ma trójdrożnego handshake'u, ale dopasowanie conntrack działa tak samo — NEW dla pierwszego pakietu „flow", ESTABLISHED dla kolejnych. Typowe forwardowane porty UDP to WireGuard (51820), DNS (53) i serwery gier.

Jak przekierować zakres portów, np. 30000-30010?

Użyj --dport 30000:30010 w regule (uwaga: dwukropek, nie myślnik). Cel DNAT też przyjmuje zakres: --to-destination 192.168.23.10:30000-30010. Jeśli chcesz remapować na inny zakres, oba przedziały muszą mieć tyle samo portów — jądro dopasowuje offset.

Czy port forwarding działa też dla kontenerów Proxmoxa (LXC), czy tylko dla VM-ek?

Działa dla obu. Z perspektywy reguły iptables kontener to kolejny endpoint sieciowy na moście Proxmoxa. Dopóki LXC ma adres w vmbr1 i bramę domyślną wskazującą na hosta, te same reguły działają. Jedyna różnica: kontenery LXC można skonfigurować tak, żeby przepuszczały hostowe interfejsy bezpośrednio, co w ogóle omija NAT — ale to inny setup.

Jaka jest różnica między iptables -A i iptables -I 1?

-A dokłada na koniec łańcucha; -I 1 wstawia na pozycji 1 (samej górze). Kolejność ma znaczenie, bo reguły są ewaluowane z góry na dół i wygrywa pierwsze dopasowanie. Dla reguł DNAT i MASQUERADE kolejność w obrębie ich własnego łańcucha rzadko ma znaczenie (zwykle są tam same), ale dla reguł w łańcuchu FORWARD z polityką DROP, -A ACCEPT po DROP-ie to martwy kod. Gdy masz wątpliwości — używaj -I 1, żeby mieć pewność, że Twoja reguła jest sprawdzana jako pierwsza.

Jak usunąć regułę przekierowania, której już nie potrzebuję?

Tą samą komendą, ale z -D zamiast -I albo -A, z dokładnym dopasowaniem reguły:

iptables -t nat -D PREROUTING -d 51.75.74.52 -p tcp --dport 5829 \
    -j DNAT --to-destination 192.168.23.10:22

Albo przez numer linii po iptables -t nat -L PREROUTING --line-numbers:

iptables -t nat -D PREROUTING 1

Potem iptables-save > /etc/iptables/rules.v4, żeby utrwalić zmianę.

Dlaczego moje przekierowane połączenie chwilę działa, a potem się rozłącza?

Tabela conntrack jest pełna albo sesja wygasa. Sprawdź /proc/sys/net/netfilter/nf_conntrack_count względem nf_conntrack_max. Jeśli są blisko siebie, podnieś max (sysctl -w net.netfilter.nf_conntrack_max=262144). Dla długo żyjących bezczynnych połączeń (typu pool bazodanowy) typowym winowajcą są domyślne TCP keepalive — wpis w conntrack wygasa zanim przyleci kolejny pakiet i sesja niezauważenie staje się nieprawidłowa.

Mam używać firewalla Proxmoxa czy gołego iptables?

Oba działają, ale nie mieszaj na tym samym hoście. Firewall Proxmoxa (pve-firewall) jest wygodny do reguł per-VM w GUI, ale ma kruche miejsca z NAT — reguły DNAT powinny lądować w /etc/pve/firewall/cluster.fw albo bezpośrednio w iptables, nie rozproszone między oba. Dla scenariusza bramy NAT, jak w tym poradniku, goły iptables w /etc/iptables/rules.v4 jest prostszy i czysto przeżywa upgrade Proxmoxa.

Czy moje reguły iptables przeżyją upgrade Proxmoxa?

Tak, jeśli siedzą w /etc/iptables/rules.v4 i masz zainstalowane iptables-persistent. Upgrade Proxmoxa rusza konfigurację klastra i jądro, ale nie podmienia stanu netfilter-persistent. Po upgradzie zweryfikuj iptables -t nat -L -v -n — jeśli reguł nie ma, uruchom netfilter-persistent reload albo sprawdź, czy jednostka systemd jest włączona.

Jak zobaczyć ruch na żywo trafiający w moją regułę?

Liczniki i tcpdump:

iptables -t nat -L PREROUTING -v -n
tcpdump -i vmbr0 -n port 5829
tcpdump -i vmbr1 -n host 192.168.23.10 and port 22

Pierwsza komenda pokazuje liczniki pakietów na każdej regule NAT — przyrost znaczy, że reguła dopasowuje. Dwa wywołania tcpdump pozwalają zobaczyć pakiet po stronie publicznej i prywatnej; jeśli pojawia się na vmbr0 ale nie na vmbr1, Twój DNAT albo FORWARD jest zepsuty.

Następne kroki

Wygeneruj pełen zestaw reguł dla swojego konkretnego publicznego IP, portów i adresów VM w generatorze Proxmox Port Forwarding na vps-web.com — wypełnij formularz i wklej output do shella albo do /etc/iptables/rules.v4.

Tematy powiązane, które rozbudowują produkcyjny setup Proxmoxa:

Jeśli wolisz wideo, zajrzyj na mój kanał YouTube — praktyczna administracja Linuksem i Proxmoxem z demonstracjami na żywym sprzęcie.