Via tunela kontenero funkcias, docker compose exec vpn curl -s https://ifconfig.me respondas per la adreso de la provizanto, kaj tamen la retumilo sur via labortablo ankoraŭ eliras tra via ISP. Tiu breĉo estas atendita. Kontenero, kiu rulas VPN-klienton, tenas retan nomspacon, itinerojn kaj tunelan interfacon, kaj nenion, kio parolas HTTP aŭ SOCKS; publikigi pordon sur ĝi ne povas krei aŭskultanton, kiu neniam ekzistis.

Kie la kliento ruliĝas decidas la dezajnon. Najbara kontenero povas eniri la nomspacon de la tunelo, labortabla aplikaĵo ne povas, kaj enkursigilo bezonas itinerojn anstataŭ prokuran kampon. Se vi eraros pri la mapado, la simptomo estos la sama: konekto rifuzita, aŭ trafiko, kiu silente prenas la malnovan vojon.

Agordigu la aranĝon al la loko, kie la kliento ruliĝas

Demandu unu demandon antaŭ ol redakti Compose: ĉu la kliento povas starti ene de la reta nomspaco de la VPN-kontenero? Ĉio, kio jam ruliĝas kiel Linux-kontenero, povas. Retumilo, IDE aŭ CLI sur via labortablo ne povas, ĉar ĝia prokura agordo atendas protokolan servon, ne nomspacon.

ClientArrangementWhat must already exist
Another Compose serviceShares the vpn namespace via network_mode: service:vpnA working tunnel and correct start order
Host browser, IDE or CLIProxy listener inside the namespace, published to host loopbackA configured SOCKS or HTTP proxy and its access rules
Router, VM or phoneThe container as a layer-3 gatewayForwarding, NAT and a return route

Tiuj tri ne miksiĝas. HTTP-prokura kampo direktita al la ponto-adreso de la kontenero atingas nenion, se prokuro ne aŭskultas tie, kaj prokura aŭskultanto ne enkursigas la trafikon de enkursigilo. Unue decidu, poste sekvu la konforman sekcion.

Dividu la tunelan nomspacon kun najbara kontenero

Ĉi tio estas la plej malmultekosta opcio, ĉar neniu prokura protokolo partoprenas. La aplikaĵo aliĝas al la nomspaco de la vpn-servo kaj heredas ĝiajn interfacojn, itinerojn kaj pordan spacon:

services:
  vpn:
    image: your-vpn-client
    cap_add:
      - NET_ADMIN
    healthcheck:
      test: ["CMD-SHELL", "ip link show tun0 >/dev/null"]
      interval: 10s
      retries: 5
  app:
    image: your-app
    network_mode: service:vpn
    depends_on:
      vpn:
        condition: service_healthy

Tri limigoj sekvas el tio, ke la nomspaco apartenas al alia servo. La aplikaĵo ne ricevas propran networks-ŝlosilon, ĉar ĝi ne havas nomspacon al kiu alkroĉiĝi. Porda publikigo apartenas al vpn, ĉar tie loĝas la nomspaco. Kaj rekreado de vpn detruas la nomspacon, al kiu la aplikaĵo aliĝis, do docker compose up -d --force-recreate vpn lasas al vi rekrei ankaŭ app; simpla restarto ne ĉiam sufiĉas. La Compose-serva referenco kovras ĉi tiun aranĝon kaj ĝian limigon pri porda publikigo.

Ne supozu, ke la solvilo venas kun ĝi. /etc/resolv.conf estas dosiero por kontenero, ne parto de la reta nomspaco, do la aplikaĵo ankoraŭ povas demandi la solvilon de la gastiganto dum ĝiaj pakaĵoj eliras tra la tunelo. Legu ĝin ene de la kontenero kaj agordu dns: en la aplikaĵo, kiam privataj nomoj devas solviĝi tra la tunelo.

docker compose exec app ip route
docker compose exec app cat /etc/resolv.conf
docker compose exec app curl -s https://ifconfig.me

Se la itinera listo enhavas la tunelan interfacon kaj la adreso estas de la provizanto, la aplikaĵo estas ene de la tunelo. Se la interfaco mankas, app startis antaŭ ol vpn havis tunelon, do rekrei app post kiam vpn raportas sanon.

Metu veran prokuran aŭskultanton en la nomspacon por gastigantaj klientoj

Labortabla retumilo ne povas aliĝi al nomspaco, do la tunelo devas esti elmetita kiel servo. Rulu veran SOCKS aŭ HTTP-prokuron ene de la vpn-nomspaco kaj publikigu nur ĝian pordon:

services:
  vpn:
    ports:
      - "127.0.0.1:1080:1080"
  proxy:
    image: your-proxy
    network_mode: service:vpn
    command: ["--socks", "0.0.0.0:1080"]

La adreso sur la gastiganta flanko estas la grava duono de tiu mapado. 127.0.0.1:1080 maldekstre tenas la aŭskultanton ekster via LAN; nuda "1080:1080" publikigas malfermitan prokuron al ĉiu aparato, kiu povas atingi vian maŝinon.

La kontenera flanko havas sian propran kaptilon. Publikigitaj pordoj estas liverataj al la adreso de la kontenero sur la ponto, ne al ĝia loopback, do prokuro startita kun --socks 127.0.0.1:1080 ene de la nomspaco akceptas konektojn de najbaroj kaj rifuzas ĉion alvenantan tra la publikigita pordo. Ligu ĝin al 0.0.0.0 kaj fidu la loopback-ligon sur la gastiganta flanko por izoligo. La sama regulo validas por la aŭskulta adreso en prokura agorda dosiero.

Poste decidu, kie nomoj solviĝas. En curl --socks5 solvas la gastigan nomon loke kaj --socks5-hostname sendas la nomon al la prokuro; retumiloj montras la saman ŝaltilon sub alia etikedo. Loka solvado likas la peton eĉ kiam la paĝo ŝarĝiĝas tra la tunelo.

Traktu la konteneron kiel pordegon nur kun revena itinero

Enkursigiloj, VM-oj kaj telefonoj ne uzos HTTP-prokuran kampon, kaj iuj aplikaĵoj tute ignoras prokurajn variablojn. Enkursigi ilian trafikon signifas tavolon 3: la kontenero plusendas pakaĵojn kaj tradukas adresojn sur la tunela interfaco.

sysctl -w net.ipv4.ip_forward=1
iptables -t nat -A POSTROUTING -o tun0 -j MASQUERADE

Du aferojn oni facile preterlasas. La kliento bezonas itineron, kiu direktas sian defaŭltan pordegon al ĉi tiu gastiganto, kaj respondoj devas trovi la vojon reen, ĉu per statika itinero sur la supra enkursigilo, ĉu per NAT sur la interfaco al la klientoj. Sen unu el ili la tunelo portas la peton eksteren kaj la respondo malaperas.

Ĝi ankaŭ havas la plej larĝan efikradiuson. Gastiganto, kiu servas kiel pordego por la tuta LAN, sendas ĉiun misagorditan klienton tra via VPN-konto, kaj tunela falo aŭ nigrigas la LAN aŭ refalas al la ISP laŭ la kill switch.

Kontrolu la elirvojon, poste rulumu malantaŭen laŭvice

Kontrolu laŭ ĉi tiu ordo kaj haltu ĉe la unua fiasko: elira adreso ene de la nomspaco, elira adreso de la gastiganto tra la prokuro, poste nomsolvado por privata gastiganto.

docker compose exec vpn curl -s https://ifconfig.me
curl -s -x socks5h://127.0.0.1:1080 https://ifconfig.me
curl -s -x socks5h://127.0.0.1:1080 http://internal.example/health

La unuaj du adresoj devas kongrui kun la provizanto, kaj la tria devas solviĝi tra la prokuro anstataŭ fiaski per noma eraro. Kongrua unua linio kaj fiaska dua linio signifas, ke la aŭskultanto aŭ la publikigita pordo estas malĝustaj, ne la tunelo.

Rulumado malantaŭen estas la malo de la agordo. Forigu la prokurajn medio-variablojn el la ŝela profilo kaj el ajna systemd-unuo, poste mallevu la stakon, por ke la komuna nomspaco malaperu kun sia posedanto. Forigu la publikigitan pordon antaŭ ol forigi la prokuran servon, alie la gastiganto tenas loopback-aŭskultanton, kiun neniu legas.

Antaŭ ol daŭrigi, konfirmu kvar aferojn: la kliento, pri kiu vi zorgas, efektive atingas la tunelon, nur la posedanto de la nomspaco publikigas pordojn, privataj nomoj solviĝas tie, kie vi intencis, kaj nenio aŭskultas sur gastiganta adreso, kiu ne estas loopback. Ĉiu el ili silente fiaskas en produkto, kaj ĉiu estas unulinia kontrolo supre.

Rilataj artikoloj