[{"data":1,"prerenderedAt":3748},["ShallowReactive",2],{"content-index":3,"doc-de-docker":80},{"en":4,"de":54,"es":67},{"paths":5,"docs":29},[6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28],"\u002Fdocs\u002Fgetting-started","\u002Fdocs\u002Flinux","\u002Fdocs\u002Fmacos","\u002Fdocs\u002Fwindows","\u002Fdocs\u002Fdocker","\u002Fdocs\u002Fcreate-api-key","\u002Fguides\u002Ffind-your-public-ip-address\u002Ffind-your-ip-address-on-linux","\u002Fguides\u002Ffind-your-public-ip-address\u002Ffind-your-ip-address-on-mac","\u002Fguides\u002Ffind-your-public-ip-address\u002Ffind-your-ip-address-on-windows","\u002Fguides\u002Ffind-your-public-ip-address","\u002Fguides\u002Fself-hosting\u002Fdocker-desktop-mac-client-ip","\u002Fguides\u002Fself-hosting\u002Fexpose-docker-containers-to-the-internet","\u002Fguides\u002Fself-hosting\u002Fexpose-home-server-to-internet","\u002Fguides\u002Fself-hosting\u002Fgetpublicip-vs-cloudflare-tunnel-vs-tailscale","\u002Fguides\u002Fself-hosting\u002Fmac-mini-home-server","\u002Fguides\u002Fself-hosting\u002Fport-forwarding-not-working","\u002Fguides\u002Fself-hosting\u002Fself-hosting-behind-carrier-grade-nat-cgnat","\u002Fguides\u002Fself-hosting\u002Fwireguard-simple-watchdog-script","\u002Fguides\u002Fstatic-public-ip-address\u002Fhow-to-get-a-public-ip-address","\u002Fguides\u002Fstatic-public-ip-address\u002Fhow-to-get-a-static-ip-address","\u002Fguides\u002Fstatic-public-ip-address","\u002Fguides\u002Fuse-cases\u002Fhome-server","\u002Fguides\u002Fuse-cases\u002Foffice-server",[30,34,38,42,46,50],{"path":6,"title":31,"icon":32,"stem":33},"Getting Started","mdi-file-document-outline","docs\u002F1.getting-started",{"path":7,"title":35,"icon":36,"stem":37},"Linux","mdi-linux","docs\u002F2.linux",{"path":8,"title":39,"icon":40,"stem":41},"macOS","mdi-apple","docs\u002F3.macos",{"path":9,"title":43,"icon":44,"stem":45},"Windows","mdi-microsoft-windows","docs\u002F3.windows",{"path":10,"title":47,"icon":48,"stem":49},"Docker","mdi-docker","docs\u002F4.docker",{"path":11,"title":51,"icon":52,"stem":53},"Create API Key","mdi-key","docs\u002F5.create-api-key",{"paths":55,"docs":58},[6,7,8,9,10,11,12,14,15,56,17,18,57,19,21,22,24,25,26,27,28],"\u002Fguides\u002Fself-hosting\u002Fdyndns-hinter-cgnat","\u002Fguides\u002Fself-hosting\u002Ffritzbox-portfreigabe-ds-lite",[59,61,62,63,64,65],{"path":6,"title":60,"icon":32,"stem":33},"Erste Schritte",{"path":7,"title":35,"icon":36,"stem":37},{"path":8,"title":39,"icon":40,"stem":41},{"path":9,"title":43,"icon":44,"stem":45},{"path":10,"title":47,"icon":48,"stem":49},{"path":11,"title":66,"icon":52,"stem":53},"API-Schlüssel erstellen",{"paths":68,"docs":71},[6,7,8,9,10,11,12,14,15,69,70,17,18,19,21,22,24,25,26,27,28],"\u002Fguides\u002Fself-hosting\u002Fcomo-saber-si-tengo-cgnat","\u002Fguides\u002Fself-hosting\u002Fddns-detras-de-cgnat",[72,74,75,76,77,78],{"path":6,"title":73,"icon":32,"stem":33},"Primeros pasos",{"path":7,"title":35,"icon":36,"stem":37},{"path":8,"title":39,"icon":40,"stem":41},{"path":9,"title":43,"icon":44,"stem":45},{"path":10,"title":47,"icon":48,"stem":49},{"path":11,"title":79,"icon":52,"stem":53},"Crear clave API",{"id":81,"title":82,"body":83,"createdAt":3716,"description":3717,"extension":3718,"faq":3719,"meta":3742,"navigation":3743,"path":10,"seo":3745,"stem":49,"updatedAt":3746,"__hash__":3747},"content_de\u002Fdocs\u002F4.docker.md","Öffentliche IP mit Docker einrichten",{"type":84,"value":85,"toc":3678},"minimark",[86,90,99,102,107,180,193,208,212,222,248,262,266,269,434,445,458,463,470,661,664,683,690,708,712,722,730,841,919,929,932,935,939,942,948,954,969,979,983,993,1003,1068,1081,1091,1104,1108,1111,1125,1129,1132,1135,1139,1142,1176,1180,1183,1187,1194,1244,1276,1288,1292,1299,1405,1412,1416,1446,1453,1456,1462,1477,1481,1488,1491,1510,1513,1516,1519,1530,1536,1539,1542,1549,1555,1564,1571,1574,1578,1581,1586,1592,1596,1602,1605,1608,1612,1615,1619,2009,2013,2027,2443,2446,2459,2469,2492,2502,2521,2528,2540,2544,2547,2586,2592,2595,2602,2606,2616,2619,2660,2664,2671,2674,2813,2821,2824,2846,2849,2853,2859,2886,2889,2893,2899,2905,2911,2947,2951,3018,3021,3028,3031,3034,3041,3044,3050,3060,3077,3080,3087,3096,3099,3103,3109,3113,3119,3122,3125,3129,3135,3425,3428,3487,3491,3509,3524,3537,3551,3560,3585,3598,3611,3622,3634,3647,3656,3659,3674],[87,88,47],"h1",{"id":89},"docker",[91,92,93,94,98],"p",{},"Wenn Ihre Dienste mit Docker Compose laufen, fügen Sie dem Projekt unseren Container hinzu, und\nsie sind über Ihre eigene öffentliche IPv4-Adresse aus dem Internet erreichbar, ohne dass Sie an\nden Diensten selbst etwas ändern. Eingehender Verkehr kommt über den Tunnel an statt über einen\nveröffentlichten Port. Sie fügen also keine ",[95,96,97],"code",{},"ports:","-Einträge hinzu, Sie brauchen keine routbare\nAdresse von Ihrem Internetanbieter, und weder an Ihrem Router noch an Ihrer Host-Firewall muss\netwas geöffnet werden.",[100,101],"docs-toc",{},[103,104,106],"h2",{"id":105},"bevor-sie-beginnen","Bevor Sie beginnen",[108,109,110,125,142,155],"ul",{},[111,112,113,114,118,119],"li",{},"Eine GetPublicIP-IP-Adresse und ihr ",[115,116,117],"strong",{},"API-Schlüssel",". Siehe\n",[120,121,66],"a",{"className":122,"href":124},[123],"link","\u002Fde\u002Fdocs\u002Fcreate-api-key",[111,126,127,130,131,134,135,138,139],{},[115,128,129],{},"Linux:"," Docker Engine und ",[115,132,133],{},"Compose v2",", also ",[95,136,137],{},"docker compose"," statt des älteren\nSkripts ",[95,140,141],{},"docker-compose",[111,143,144,147,148,154],{},[115,145,146],{},"macOS:"," ",[120,149,153],{"className":150,"href":151,"target":152},[123],"https:\u002F\u002Fwww.docker.com\u002Fproducts\u002Fdocker-desktop\u002F","_blank","Docker Desktop",", auf Intel oder Apple Silicon",[111,156,157,147,160,163,164,167,168,171,172,175,176,179],{},[115,158,159],{},"Windows:",[120,161,153],{"className":162,"href":151,"target":152},[123]," im Modus für ",[115,165,166],{},"Linux-Container",", mit einem ",[115,169,170],{},"WSL2-Kernel 6.6",". Prüfen\nSie das mit ",[95,173,174],{},"wsl --version"," und führen Sie ",[95,177,178],{},"wsl --update"," aus, falls eine ältere Version\nangezeigt wird, denn Kernels vor 6.6 fehlt ein Netfilter-Modul, das der Tunnel benötigt",[91,181,182,183,187,188,192],{},"Alles auf dieser Seite funktioniert unverändert unter Windows und macOS mit Docker Desktop,\nohne dass Sie außer Docker Desktop selbst etwas installieren müssen. Docker Desktop ist\nkostenlos für die private Nutzung, für Bildung, für nicht kommerzielle Open-Source-Projekte\nund für kleine Unternehmen mit weniger als 250 Beschäftigten und unter 10 Mio. USD\nJahresumsatz; größere Organisationen brauchen ein kostenpflichtiges Abonnement von Docker.\nDetails zu den einzelnen Systemen finden Sie unter ",[120,184,39],{"className":185,"href":186},[123],"#macos"," und\n",[120,189,43],{"className":190,"href":191},[123],"#windows",".",[91,194,195,196,199,200,203,204,207],{},"Das Image wird für ",[95,197,198],{},"linux\u002Famd64"," und ",[95,201,202],{},"linux\u002Farm64"," unter\n",[95,205,206],{},"ghcr.io\u002Fgetpublicip\u002Fgetpublicip"," veröffentlicht.",[103,209,211],{"id":210},"api-schlüssel-in-eine-env-datei-eintragen","API-Schlüssel in eine .env-Datei eintragen",[91,213,214,215,218,219,192],{},"Legen Sie neben Ihrer Compose-Datei eine Datei ",[95,216,217],{},".env"," an. Weitere Informationen finden Sie\nunter ",[120,220,66],{"className":221,"href":124},[123],[223,224,229],"pre",{"className":225,"code":226,"language":227,"meta":228,"style":228},"language-bash shiki shiki-themes monokai","GETPUBLICIP_API_KEY=your-api-key-from-the-dashboard\n","bash","",[95,230,231],{"__ignoreMap":228},[232,233,236,240,244],"span",{"class":234,"line":235},"line",1,[232,237,239],{"class":238},"sCdxs","GETPUBLICIP_API_KEY",[232,241,243],{"class":242},"s8I7P","=",[232,245,247],{"class":246},"s_Ekj","your-api-key-from-the-dashboard\n",[91,249,250,251,254,255,257,258,261],{},"Compose liest die .env-Datei automatisch. Deshalb verweisen die Compose-Dateien unten auf\n",[95,252,253],{},"${GETPUBLICIP_API_KEY}",", statt den Schlüssel selbst zu enthalten. Tragen Sie ",[95,256,217],{}," in Ihre\n",[95,259,260],{},".gitignore"," ein.",[103,263,265],{"id":264},"zur-docker-compose-datei-hinzufügen","Zur Docker-Compose-Datei hinzufügen",[91,267,268],{},"Fügen Sie diesen Dienst neben den Containern hinzu, die Sie bereits betreiben:",[223,270,274],{"className":271,"code":272,"language":273,"meta":228,"style":228},"language-yaml shiki shiki-themes monokai","services:\n  getpublicip:\n    image: ghcr.io\u002Fgetpublicip\u002Fgetpublicip:latest\n    restart: unless-stopped\n    environment:\n      GETPUBLICIP_API_KEY: \"${GETPUBLICIP_API_KEY}\"\n      GETPUBLICIP_MAPPINGS: \"8080\u002Ftcp->web:80; 443\u002Ftcp->web:443\"\n    cap_add:\n      - NET_ADMIN\n    devices:\n      - \u002Fdev\u002Fnet\u002Ftun\n    sysctls:\n      net.ipv4.ip_forward: 1\n      net.ipv4.conf.all.src_valid_mark: 1\n      net.ipv6.conf.all.forwarding: 1\n    networks:\n      - appnet\n","yaml",[95,275,276,284,292,304,315,323,334,345,353,362,370,378,386,398,408,418,426],{"__ignoreMap":228},[232,277,278,281],{"class":234,"line":235},[232,279,280],{"class":242},"services",[232,282,283],{"class":238},":\n",[232,285,287,290],{"class":234,"line":286},2,[232,288,289],{"class":242},"  getpublicip",[232,291,283],{"class":238},[232,293,295,298,301],{"class":234,"line":294},3,[232,296,297],{"class":242},"    image",[232,299,300],{"class":238},": ",[232,302,303],{"class":246},"ghcr.io\u002Fgetpublicip\u002Fgetpublicip:latest\n",[232,305,307,310,312],{"class":234,"line":306},4,[232,308,309],{"class":242},"    restart",[232,311,300],{"class":238},[232,313,314],{"class":246},"unless-stopped\n",[232,316,318,321],{"class":234,"line":317},5,[232,319,320],{"class":242},"    environment",[232,322,283],{"class":238},[232,324,326,329,331],{"class":234,"line":325},6,[232,327,328],{"class":242},"      GETPUBLICIP_API_KEY",[232,330,300],{"class":238},[232,332,333],{"class":246},"\"${GETPUBLICIP_API_KEY}\"\n",[232,335,337,340,342],{"class":234,"line":336},7,[232,338,339],{"class":242},"      GETPUBLICIP_MAPPINGS",[232,341,300],{"class":238},[232,343,344],{"class":246},"\"8080\u002Ftcp->web:80; 443\u002Ftcp->web:443\"\n",[232,346,348,351],{"class":234,"line":347},8,[232,349,350],{"class":242},"    cap_add",[232,352,283],{"class":238},[232,354,356,359],{"class":234,"line":355},9,[232,357,358],{"class":238},"      - ",[232,360,361],{"class":246},"NET_ADMIN\n",[232,363,365,368],{"class":234,"line":364},10,[232,366,367],{"class":242},"    devices",[232,369,283],{"class":238},[232,371,373,375],{"class":234,"line":372},11,[232,374,358],{"class":238},[232,376,377],{"class":246},"\u002Fdev\u002Fnet\u002Ftun\n",[232,379,381,384],{"class":234,"line":380},12,[232,382,383],{"class":242},"    sysctls",[232,385,283],{"class":238},[232,387,389,392,394],{"class":234,"line":388},13,[232,390,391],{"class":242},"      net.ipv4.ip_forward",[232,393,300],{"class":238},[232,395,397],{"class":396},"s7s5_","1\n",[232,399,401,404,406],{"class":234,"line":400},14,[232,402,403],{"class":242},"      net.ipv4.conf.all.src_valid_mark",[232,405,300],{"class":238},[232,407,397],{"class":396},[232,409,411,414,416],{"class":234,"line":410},15,[232,412,413],{"class":242},"      net.ipv6.conf.all.forwarding",[232,415,300],{"class":238},[232,417,397],{"class":396},[232,419,421,424],{"class":234,"line":420},16,[232,422,423],{"class":242},"    networks",[232,425,283],{"class":238},[232,427,429,431],{"class":234,"line":428},17,[232,430,358],{"class":238},[232,432,433],{"class":246},"appnet\n",[91,435,436,437,440,441,444],{},"Ersetzen Sie ",[95,438,439],{},"appnet"," durch das Netzwerk, in dem Ihre Dienste bereits laufen, und ",[95,442,443],{},"web"," durch\ndie Namen Ihrer eigenen Dienste. Alles andere kann bleiben, wie es ist.",[91,446,447,448,451,452,457],{},"Behalten Sie ",[95,449,450],{},"restart: unless-stopped"," bei. Darüber erholt sich der Agent von Fehlern, die er\nnicht an Ort und Stelle beheben kann, wie unter\n",[120,453,456],{"className":454,"href":455},[123],"#verbindungsabbrüche","Verbindungsabbrüche"," beschrieben.",[459,460,462],"h3",{"id":461},"ein-vollständiges-funktionierendes-beispiel","Ein vollständiges, funktionierendes Beispiel",[91,464,465,466,469],{},"Wenn Sie noch kein Compose-Projekt haben, ist diese Datei ein komplettes Setup: ein Webserver\nauf Ihrer eigenen öffentlichen IP-Adresse, von überall erreichbar. Speichern Sie sie als\n",[95,467,468],{},"compose.yaml",":",[223,471,473],{"className":271,"code":472,"language":273,"meta":228,"style":228},"services:\n  web:\n    image: nginx:alpine\n    restart: unless-stopped\n    networks:\n      - appnet\n\n  getpublicip:\n    image: ghcr.io\u002Fgetpublicip\u002Fgetpublicip:latest\n    restart: unless-stopped\n    environment:\n      GETPUBLICIP_API_KEY: \"${GETPUBLICIP_API_KEY}\"\n      GETPUBLICIP_MAPPINGS: \"80\u002Ftcp->web:80\"\n    cap_add:\n      - NET_ADMIN\n    devices:\n      - \u002Fdev\u002Fnet\u002Ftun\n    sysctls:\n      net.ipv4.ip_forward: 1\n      net.ipv4.conf.all.src_valid_mark: 1\n      net.ipv6.conf.all.forwarding: 1\n    networks:\n      - appnet\n\nnetworks:\n  appnet:\n",[95,474,475,481,488,497,505,511,517,523,529,537,545,551,559,568,574,580,586,592,599,608,617,626,633,640,645,653],{"__ignoreMap":228},[232,476,477,479],{"class":234,"line":235},[232,478,280],{"class":242},[232,480,283],{"class":238},[232,482,483,486],{"class":234,"line":286},[232,484,485],{"class":242},"  web",[232,487,283],{"class":238},[232,489,490,492,494],{"class":234,"line":294},[232,491,297],{"class":242},[232,493,300],{"class":238},[232,495,496],{"class":246},"nginx:alpine\n",[232,498,499,501,503],{"class":234,"line":306},[232,500,309],{"class":242},[232,502,300],{"class":238},[232,504,314],{"class":246},[232,506,507,509],{"class":234,"line":317},[232,508,423],{"class":242},[232,510,283],{"class":238},[232,512,513,515],{"class":234,"line":325},[232,514,358],{"class":238},[232,516,433],{"class":246},[232,518,519],{"class":234,"line":336},[232,520,522],{"emptyLinePlaceholder":521},true,"\n",[232,524,525,527],{"class":234,"line":347},[232,526,289],{"class":242},[232,528,283],{"class":238},[232,530,531,533,535],{"class":234,"line":355},[232,532,297],{"class":242},[232,534,300],{"class":238},[232,536,303],{"class":246},[232,538,539,541,543],{"class":234,"line":364},[232,540,309],{"class":242},[232,542,300],{"class":238},[232,544,314],{"class":246},[232,546,547,549],{"class":234,"line":372},[232,548,320],{"class":242},[232,550,283],{"class":238},[232,552,553,555,557],{"class":234,"line":380},[232,554,328],{"class":242},[232,556,300],{"class":238},[232,558,333],{"class":246},[232,560,561,563,565],{"class":234,"line":388},[232,562,339],{"class":242},[232,564,300],{"class":238},[232,566,567],{"class":246},"\"80\u002Ftcp->web:80\"\n",[232,569,570,572],{"class":234,"line":400},[232,571,350],{"class":242},[232,573,283],{"class":238},[232,575,576,578],{"class":234,"line":410},[232,577,358],{"class":238},[232,579,361],{"class":246},[232,581,582,584],{"class":234,"line":420},[232,583,367],{"class":242},[232,585,283],{"class":238},[232,587,588,590],{"class":234,"line":428},[232,589,358],{"class":238},[232,591,377],{"class":246},[232,593,595,597],{"class":234,"line":594},18,[232,596,383],{"class":242},[232,598,283],{"class":238},[232,600,602,604,606],{"class":234,"line":601},19,[232,603,391],{"class":242},[232,605,300],{"class":238},[232,607,397],{"class":396},[232,609,611,613,615],{"class":234,"line":610},20,[232,612,403],{"class":242},[232,614,300],{"class":238},[232,616,397],{"class":396},[232,618,620,622,624],{"class":234,"line":619},21,[232,621,413],{"class":242},[232,623,300],{"class":238},[232,625,397],{"class":396},[232,627,629,631],{"class":234,"line":628},22,[232,630,423],{"class":242},[232,632,283],{"class":238},[232,634,636,638],{"class":234,"line":635},23,[232,637,358],{"class":238},[232,639,433],{"class":246},[232,641,643],{"class":234,"line":642},24,[232,644,522],{"emptyLinePlaceholder":521},[232,646,648,651],{"class":234,"line":647},25,[232,649,650],{"class":242},"networks",[232,652,283],{"class":238},[232,654,656,659],{"class":234,"line":655},26,[232,657,658],{"class":242},"  appnet",[232,660,283],{"class":238},[91,662,663],{},"Starten Sie es dann:",[223,665,667],{"className":225,"code":666,"language":227,"meta":228,"style":228},"docker compose up -d\n",[95,668,669],{"__ignoreMap":228},[232,670,671,674,677,680],{"class":234,"line":235},[232,672,89],{"class":673},"sHkqI",[232,675,676],{"class":246}," compose",[232,678,679],{"class":246}," up",[232,681,682],{"class":396}," -d\n",[91,684,685,686,689],{},"Warten Sie etwa 30 bis 60 Sekunden und öffnen Sie ",[95,687,688],{},"http:\u002F\u002F{YOUR IP ADDRESS}"," aus einem\nbeliebigen Netzwerk oder mit Ihrem Smartphone über mobile Daten. Sehen Sie die\nWillkommensseite von nginx, hat eine Anfrage aus dem Internet Ihren Container erreicht.",[91,691,692,694,695,697,698,700,701,703,704,707],{},[95,693,443],{}," hat keinen ",[95,696,97],{},"-Eintrag. Der Agent erreicht nginx über das interne Netzwerk\n",[95,699,439],{},", und beide Dienste sind Mitglied davon, weil der Agent ",[95,702,443],{}," über den Dienstnamen\nauflöst, was nur in einem Netzwerk funktioniert, das beide gemeinsam nutzen. Würden Sie die\n",[95,705,706],{},"networks:","-Blöcke weglassen, legte Compose beide in das Standardnetzwerk des Projekts, und das\nfunktioniert genauso gut. Ein benanntes Netzwerk macht die Voraussetzung aber sichtbar.",[103,709,711],{"id":710},"ports-zuordnen","Ports zuordnen",[91,713,714,717,718,721],{},[95,715,716],{},"GETPUBLICIP_MAPPINGS"," legt fest, welche Ports Ihrer öffentlichen IP-Adresse an welchen Ihrer\nContainer gehen. Trennen Sie Einträge mit ",[95,719,720],{},";"," oder Zeilenumbrüchen:",[223,723,728],{"className":724,"code":726,"language":727},[725],"language-text","publicPort[\u002Fproto[,proto]][\u002Fstack[,stack]]->service[:internalPort]\n","text",[95,729,726],{"__ignoreMap":228},[731,732,733,749],"table",{},[734,735,736],"thead",{},[737,738,739,743,746],"tr",{},[740,741,742],"th",{},"Teil",[740,744,745],{},"Standard",[740,747,748],{},"Hinweise",[750,751,752,769,790,810,826],"tbody",{},[737,753,754,760,763],{},[755,756,757],"td",{},[95,758,759],{},"publicPort",[755,761,762],{},"keiner",[755,764,765,766],{},"ein einzelner Port oder ein Bereich wie ",[95,767,768],{},"60000-60099",[737,770,771,776,781],{},[755,772,773],{},[95,774,775],{},"proto",[755,777,778],{},[95,779,780],{},"tcp",[755,782,783,785,786,789],{},[95,784,780],{}," oder ",[95,787,788],{},"udp","; für beide durch Komma trennen",[737,791,792,797,802],{},[755,793,794],{},[95,795,796],{},"stack",[755,798,799],{},[95,800,801],{},"ipv4",[755,803,804,785,806,809],{},[95,805,801],{},[95,807,808],{},"ipv6","; für Dual-Stack durch Komma trennen",[737,811,812,817,819],{},[755,813,814],{},[95,815,816],{},"service",[755,818,762],{},[755,820,821,822,825],{},"das Ziel, zur Laufzeit aufgelöst: ein Compose-",[115,823,824],{},"Dienstname",", ein beliebiger auflösbarer Hostname oder eine feste IPv4-Adresse",[737,827,828,833,838],{},[755,829,830],{},[95,831,832],{},"internalPort",[755,834,835,836],{},"wie ",[95,837,759],{},[755,839,840],{},"der Port am Ziel; bei einem Bereich weglassen oder denselben Bereich wiederholen",[731,842,843,853],{},[734,844,845],{},[737,846,847,850],{},[740,848,849],{},"Beispiel",[740,851,852],{},"Bedeutung",[750,854,855,868,881,895,905],{},[737,856,857,862],{},[755,858,859],{},[95,860,861],{},"8080\u002Ftcp->web:80",[755,863,864,865,867],{},"TCP 8080 auf Ihrer öffentlichen IP-Adresse geht an ",[95,866,443],{}," auf Port 80",[737,869,870,875],{},[755,871,872],{},[95,873,874],{},"443\u002Ftcp,udp->web:443",[755,876,877,878,880],{},"TCP und UDP 443 gehen an ",[95,879,443],{}," auf Port 443",[737,882,883,888],{},[755,884,885],{},[95,886,887],{},"53\u002Fudp->dns:53",[755,889,890,891,894],{},"UDP 53 geht an ",[95,892,893],{},"dns"," auf Port 53",[737,896,897,902],{},[755,898,899],{},[95,900,901],{},"9000\u002Ftcp\u002Fipv4,ipv6->api",[755,903,904],{},"Dual-Stack; der interne Port ist standardmäßig 9000",[737,906,907,912],{},[755,908,909],{},[95,910,911],{},"60000-60099\u002Fudp->turn",[755,913,914,915,918],{},"UDP 60000 bis 60099 gehen an ",[95,916,917],{},"turn"," auf dieselben Ports",[91,920,921,922,199,925,928],{},"Die Segmente nach dem Port werden anhand von Schlüsselwörtern erkannt, ihre Reihenfolge spielt\nalso keine Rolle. ",[95,923,924],{},"8080\u002Ftcp\u002Fipv4",[95,926,927],{},"8080\u002Fipv4\u002Ftcp"," bedeuten dasselbe.",[91,930,931],{},"Sprechen Sie Ihre Container über den Dienstnamen an, niemals über die IP-Adresse. Compose\nvergibt Container-IPs dynamisch. Der Agent löst die Namen deshalb selbst auf und prüft sie alle\n30 Sekunden erneut. Startet ein Container mit einer anderen IP-Adresse neu, passt der Agent die\nWeiterleitungsregeln an.",[91,933,934],{},"Ein Ziel kann auch ein beliebiger auflösbarer Hostname oder eine feste IPv4-Adresse sein, und\nalle drei Varianten verhalten sich gleich. Eine feste IPv6-Adresse wird nicht akzeptiert;\nverwenden Sie stattdessen einen Hostnamen mit einem AAAA-Eintrag.",[459,936,938],{"id":937},"portbereiche","Portbereiche",[91,940,941],{},"Manche Dienste brauchen statt eines einzelnen Ports einen ganzen Block: ein TURN-Server für\nSprach- und Videoanrufe, FTP im passiven Modus oder alles, was RTP-Medien überträgt. Geben Sie\nden öffentlichen Port als Bereich an, und jeder Port darin wird an denselben Port Ihres\nContainers weitergeleitet:",[223,943,946],{"className":944,"code":945,"language":727},[725],"GETPUBLICIP_MAPPINGS: \"3478\u002Ftcp,udp->turn; 60000-60099\u002Fudp->turn\"\n",[95,947,945],{"__ignoreMap":228},[91,949,950,951,953],{},"Port 60042 auf Ihrer öffentlichen IP-Adresse kommt immer an Port 60042 von ",[95,952,917],{}," an. Diese\nDienste teilen der Gegenseite mit, welchen Port sie verwenden soll, und ein Port, der sich auf\ndem Weg hinein geändert hat, würde die Verbindung ohne jede Fehlermeldung unterbrechen.",[91,955,956,957,960,961,964,965,968],{},"Aus demselben Grund kann ein Bereich nur an denselben Bereich gehen. Sie können den internen\nPort weglassen, wie oben, oder den Bereich exakt wiederholen\n(",[95,958,959],{},"60000-60099\u002Fudp->turn:60000-60099","). Eine Weiterleitung an andere Ports, etwa\n",[95,962,963],{},"->turn:61000-61099",", wird beim Start des Containers mit\n",[95,966,967],{},"a port range must forward to the same range"," abgelehnt. Ein Bereich darf außerdem nicht\nPort 51820 enthalten, den der Tunnel selbst verwendet.",[91,970,971,972],{},"Öffnen Sie nur so viele Ports, wie Ihr Dienst nutzen soll. Bei einem TURN-Server ist\ndas der Relay-Bereich, aus dem er laut Konfiguration Ports vergibt, und nicht alles oberhalb\nvon 49152. ",[115,973,974,975,978],{},"Dafür ist das Image ",[95,976,977],{},"1.3.1"," oder neuer erforderlich.",[459,980,982],{"id":981},"ipv6-weiterleiten","IPv6 weiterleiten",[91,984,985,986,988,989,992],{},"Zuordnungen gelten nur für IPv4, sofern Sie nichts anderes angeben. Fügen Sie also den Stack\n",[95,987,808],{}," hinzu, um Ihre öffentliche IPv6-Adresse weiterzuleiten, oder ",[95,990,991],{},"ipv4,ipv6",", um beide\nweiterzuleiten. Damit das funktioniert, müssen zwei Dinge zusammenpassen.",[91,994,995,998,999,1002],{},[115,996,997],{},"In Ihrem Compose-Netzwerk muss IPv6 aktiviert sein."," Docker-Bridge-Netzwerke sind\nstandardmäßig reine IPv4-Netzwerke, ein Container darin hat also keine IPv6-Adresse, an die der\nAgent weiterleiten könnte. Geben Sie dem Netzwerk ",[95,1000,1001],{},"enable_ipv6: true"," und ein IPv6-Subnetz:",[223,1004,1006],{"className":271,"code":1005,"language":273,"meta":228,"style":228},"networks:\n  appnet:\n    enable_ipv6: true\n    ipam:\n      config:\n        - subnet: 172.29.7.0\u002F24\n        - subnet: fd00:dead:beef::\u002F64\n",[95,1007,1008,1014,1020,1030,1037,1044,1057],{"__ignoreMap":228},[232,1009,1010,1012],{"class":234,"line":235},[232,1011,650],{"class":242},[232,1013,283],{"class":238},[232,1015,1016,1018],{"class":234,"line":286},[232,1017,658],{"class":242},[232,1019,283],{"class":238},[232,1021,1022,1025,1027],{"class":234,"line":294},[232,1023,1024],{"class":242},"    enable_ipv6",[232,1026,300],{"class":238},[232,1028,1029],{"class":396},"true\n",[232,1031,1032,1035],{"class":234,"line":306},[232,1033,1034],{"class":242},"    ipam",[232,1036,283],{"class":238},[232,1038,1039,1042],{"class":234,"line":317},[232,1040,1041],{"class":242},"      config",[232,1043,283],{"class":238},[232,1045,1046,1049,1052,1054],{"class":234,"line":325},[232,1047,1048],{"class":238},"        - ",[232,1050,1051],{"class":242},"subnet",[232,1053,300],{"class":238},[232,1055,1056],{"class":246},"172.29.7.0\u002F24\n",[232,1058,1059,1061,1063,1065],{"class":234,"line":336},[232,1060,1048],{"class":238},[232,1062,1051],{"class":242},[232,1064,300],{"class":238},[232,1066,1067],{"class":246},"fd00:dead:beef::\u002F64\n",[91,1069,1070,1073,1074,1077,1078,1080],{},[115,1071,1072],{},"Der Stack gilt für das Ziel ebenso wie für den öffentlichen Port."," Die Weiterleitungsregeln\nkönnen nicht zwischen den beiden Adressfamilien übersetzen, eine IPv6-Anfrage muss Ihren\nContainer also über IPv6 erreichen. ",[95,1075,1076],{},"8080\u002Ftcp\u002Fipv4,ipv6->web:80"," setzt daher voraus, dass ",[95,1079,443],{},"\nsowohl eine IPv4- als auch eine IPv6-Adresse hat, und genau die liefert das Netzwerk oben.",[91,1082,447,1083,1086,1087,1090],{},[95,1084,1085],{},"net.ipv6.conf.all.forwarding: 1"," im ",[95,1088,1089],{},"sysctls","-Block des Agenten bei. Es steht\nbereits in den Beispielen auf dieser Seite und wird nur benötigt, wenn Sie IPv6 weiterleiten.",[91,1092,1093,1094,1097,1098,1100,1101,192],{},"Fehlt etwas, nennt Ihnen der Agent mit\n",[95,1095,1096],{},"no destination resolved in the family its mapping asked for",", welches Ziel und welche\nAdressfamilie betroffen sind. Erscheint diese Zeile bei einer ",[95,1099,808],{},"-Zuordnung in einem\nansonsten gesunden Setup, fehlt dem Netzwerk fast immer ",[95,1102,1103],{},"enable_ipv6",[103,1105,1107],{"id":1106},"ssl-tls","SSL \u002F TLS",[91,1109,1110],{},"GetPublicIP arbeitet auf Paketebene. Es leitet TCP und UDP an Ihre Container weiter, und\nVerschlüsselung und Zertifikate bleiben bei Ihnen: Wenn Sie HTTPS anbieten, terminiert Ihr\neigener Dienst die TLS-Verbindung. Ordnen Sie Port 443 dem Container zu, der Ihr Zertifikat\nbereits hat, und Ihr TLS-Setup bleibt, wie es ist:",[223,1112,1114],{"className":271,"code":1113,"language":273,"meta":228,"style":228},"GETPUBLICIP_MAPPINGS: \"443\u002Ftcp->web:443; 80\u002Ftcp->web:80\"\n",[95,1115,1116],{"__ignoreMap":228},[232,1117,1118,1120,1122],{"class":234,"line":235},[232,1119,716],{"class":242},[232,1121,300],{"class":238},[232,1123,1124],{"class":246},"\"443\u002Ftcp->web:443; 80\u002Ftcp->web:80\"\n",[459,1126,1128],{"id":1127},"wir-entschlüsseln-ihren-datenverkehr-nicht","Wir entschlüsseln Ihren Datenverkehr nicht",[91,1130,1131],{},"Ihre öffentliche IP-Adresse ist kein TLS-Proxy. Sie besitzt keines Ihrer Zertifikate oder\nprivaten Schlüssel und hat daher nichts, womit sie entschlüsseln könnte. Die TLS-Sitzung wird\ndirekt zwischen dem Browser Ihres Besuchers und Ihrem eigenen Dienst ausgehandelt und bleibt\nauf dem gesamten Weg verschlüsselt: aus dem Browser hinaus, über das Internet zu Ihrer\nöffentlichen IP-Adresse, durch den WireGuard-Tunnel und in Ihren Container, wo sie zum ersten\nMal entschlüsselt wird.",[91,1133,1134],{},"Der Tunnel fügt zwischen unserem Netzwerk und Ihrem Rechner eine zweite, äußere\nVerschlüsselungsschicht hinzu, und darin wird derselbe TLS-Chiffretext transportiert, den Ihr\nBesucher gesendet hat. Ihre Zertifikate und privaten Schlüssel verlassen niemals Ihren Rechner,\nund Ihr Datenverkehr wird unterwegs nie entschlüsselt und neu verschlüsselt. Wir entschlüsseln\nkeinen TLS-Datenverkehr und haben das auch nicht vor.",[459,1136,1138],{"id":1137},"ihr-dienst-braucht-ein-gültiges-zertifikat","Ihr Dienst braucht ein gültiges Zertifikat",[91,1140,1141],{},"Da das Zertifikat bei dem Dienst liegt, der die Verbindung terminiert, braucht dieser Dienst\nein gültiges Zertifikat, genau wie auf jedem anderen öffentlichen Host.",[108,1143,1144,1158,1164,1170],{},[111,1145,1146,1149,1150,1153,1154,1157],{},[115,1147,1148],{},"Richten Sie eine Domain auf Ihre öffentliche IP-Adresse."," Legen Sie einen ",[95,1151,1152],{},"A","-Eintrag für\nIhre IPv4-Adresse an und einen ",[95,1155,1156],{},"AAAA","-Eintrag, wenn Sie auch IPv6 anbieten.\nZertifizierungsstellen stellen Zertifikate für Domainnamen aus, eine nackte IP-Adresse reicht\nalso nicht.",[111,1159,1160,1163],{},[115,1161,1162],{},"Holen Sie sich das Zertifikat von Let's Encrypt."," Das ist kostenlos und automatisiert.\nCaddy und Traefik beantragen und erneuern es für Sie, ohne dass Sie mehr als Ihren\nDomainnamen konfigurieren müssen; nginx und Apache kombinieren Sie mit certbot.",[111,1165,1166,1169],{},[115,1167,1168],{},"Wenn Sie eine HTTP-01-Challenge verwenden, ordnen Sie neben Port 443 auch Port 80"," demselben\nDienst zu. Let's Encrypt verbindet sich mit Port 80 Ihrer öffentlichen IP-Adresse, um die\nChallenge zu prüfen, und scheitert, wenn nur 443 zugeordnet ist. Eine DNS-01-Challenge\nbraucht Port 80 nicht.",[111,1171,1172,1175],{},[115,1173,1174],{},"Lassen Sie diese Ports zugeordnet."," Die Erneuerung wiederholt dieselbe Challenge etwa alle\n60 Tage und schlägt ohne Hinweis fehl, wenn die Zuordnung verschwunden ist.",[459,1177,1179],{"id":1178},"unverschlüsseltes-http-bleibt-unverschlüsselt","Unverschlüsseltes HTTP bleibt unverschlüsselt",[91,1181,1182],{},"Eine Zuordnung auf Port 80, über die unverschlüsseltes HTTP ausgeliefert wird, ist zwischen\nIhrem Besucher und Ihrer öffentlichen IP-Adresse unverschlüsselt, genau wie überall sonst im\nInternet. Der WireGuard-Tunnel deckt nur die Strecke zwischen unserem Netzwerk und Ihrem\nRechner ab. Wenn die Inhalte wichtig sind, aktivieren Sie TLS.",[103,1184,1186],{"id":1185},"weiterleitung-an-einen-dienst-auf-dem-host","Weiterleitung an einen Dienst auf dem Host",[91,1188,1189,1190,1193],{},"Um einen Dienst, der direkt auf dem Docker-Host läuft, öffentlich zu machen, lassen Sie eine\nZuordnung auf ",[95,1191,1192],{},"host.docker.internal"," zeigen:",[223,1195,1197],{"className":271,"code":1196,"language":273,"meta":228,"style":228},"services:\n  getpublicip:\n    environment:\n      GETPUBLICIP_MAPPINGS: \"8081\u002Ftcp->host.docker.internal:8081\"\n    extra_hosts:\n      - \"host.docker.internal:host-gateway\"   # needed on Linux; built in on Docker Desktop\n",[95,1198,1199,1205,1211,1217,1226,1233],{"__ignoreMap":228},[232,1200,1201,1203],{"class":234,"line":235},[232,1202,280],{"class":242},[232,1204,283],{"class":238},[232,1206,1207,1209],{"class":234,"line":286},[232,1208,289],{"class":242},[232,1210,283],{"class":238},[232,1212,1213,1215],{"class":234,"line":294},[232,1214,320],{"class":242},[232,1216,283],{"class":238},[232,1218,1219,1221,1223],{"class":234,"line":306},[232,1220,339],{"class":242},[232,1222,300],{"class":238},[232,1224,1225],{"class":246},"\"8081\u002Ftcp->host.docker.internal:8081\"\n",[232,1227,1228,1231],{"class":234,"line":317},[232,1229,1230],{"class":242},"    extra_hosts",[232,1232,283],{"class":238},[232,1234,1235,1237,1240],{"class":234,"line":325},[232,1236,358],{"class":238},[232,1238,1239],{"class":246},"\"host.docker.internal:host-gateway\"",[232,1241,1243],{"class":1242},"snpHw","   # needed on Linux; built in on Docker Desktop\n",[108,1245,1246,1262],{},[111,1247,1248,1258,1259,192],{},[115,1249,1250,1251,1254,1255,192],{},"Der Dienst auf dem Host muss auf ",[95,1252,1253],{},"0.0.0.0"," lauschen, nicht auf ",[95,1256,1257],{},"127.0.0.1"," Ein Dienst,\nder an Loopback gebunden ist, lehnt die Verbindung aus dem Container ab. Prüfen Sie das mit\n",[95,1260,1261],{},"ss -lntp",[111,1263,1264,1267,1268,1271,1272,1275],{},[115,1265,1266],{},"Eine Host-Firewall verwirft den Verkehr stillschweigend",", sofern Sie das Bridge-Subnetz\nnicht eingehend auf ",[95,1269,1270],{},"docker0"," bzw. der ",[95,1273,1274],{},"br-*","-Schnittstelle erlauben.",[91,1277,1278,1279,1281,1282,1287],{},"Ziele auf dem Host und in Containern lassen sich in einem einzigen ",[95,1280,716],{},"\nbeliebig mischen, außer mit\n",[120,1283,1286],{"className":1284,"href":1285},[123],"#die-echte-client-ip-adresse-sehen","Die echte Client-IP-Adresse sehen",",\ndenn damit funktionieren Ziele auf dem Host nicht.",[103,1289,1291],{"id":1290},"docker-compose-netzwerke","Docker-Compose-Netzwerke",[91,1293,1294,1295,1298],{},"Da Ziele über den Dienstnamen aufgelöst werden, muss der Container ",[95,1296,1297],{},"getpublicip"," im selben\nDocker-Netzwerk sein wie die Container, an die er weiterleitet.",[108,1300,1301,1307,1321],{},[111,1302,1303,1306],{},[115,1304,1305],{},"Ein Standardnetzwerk."," Es funktioniert so, wie es ist.",[111,1308,1309,1312,1313,1315,1316,1320],{},[115,1310,1311],{},"Mehrere Netzwerke."," Tragen Sie ",[95,1314,1297],{}," in ",[1317,1318,1319],"em",{},"jedes"," Netzwerk ein, in dem ein Dienst\nliegt, an den er weiterleitet.",[111,1322,1323,1326,1327,1345,1348,1349],{},[115,1324,1325],{},"Ziele in einem anderen Compose-Projekt."," Beide Projekte müssen einem gemeinsamen externen\nNetzwerk beitreten:",[223,1328,1330],{"className":225,"code":1329,"language":227,"meta":228,"style":228},"docker network create shared\n",[95,1331,1332],{"__ignoreMap":228},[232,1333,1334,1336,1339,1342],{"class":234,"line":235},[232,1335,89],{"class":673},[232,1337,1338],{"class":246}," network",[232,1340,1341],{"class":246}," create",[232,1343,1344],{"class":246}," shared\n",[1346,1347],"br",{},"Dann in jeder Compose-Datei:",[223,1350,1352],{"className":271,"code":1351,"language":273,"meta":228,"style":228},"services:\n  getpublicip:\n    networks:\n      - shared\n\nnetworks:\n  shared:\n    external: true\n",[95,1353,1354,1360,1366,1372,1379,1383,1389,1396],{"__ignoreMap":228},[232,1355,1356,1358],{"class":234,"line":235},[232,1357,280],{"class":242},[232,1359,283],{"class":238},[232,1361,1362,1364],{"class":234,"line":286},[232,1363,289],{"class":242},[232,1365,283],{"class":238},[232,1367,1368,1370],{"class":234,"line":294},[232,1369,423],{"class":242},[232,1371,283],{"class":238},[232,1373,1374,1376],{"class":234,"line":306},[232,1375,358],{"class":238},[232,1377,1378],{"class":246},"shared\n",[232,1380,1381],{"class":234,"line":317},[232,1382,522],{"emptyLinePlaceholder":521},[232,1384,1385,1387],{"class":234,"line":325},[232,1386,650],{"class":242},[232,1388,283],{"class":238},[232,1390,1391,1394],{"class":234,"line":336},[232,1392,1393],{"class":242},"  shared",[232,1395,283],{"class":238},[232,1397,1398,1401,1403],{"class":234,"line":347},[232,1399,1400],{"class":242},"    external",[232,1402,300],{"class":238},[232,1404,1029],{"class":396},[91,1406,1407,1408,1411],{},"Stimmt hier etwas nicht, wiederholen die Logs ",[95,1409,1410],{},"waiting for destinations to resolve",", und der\nAgent versucht es weiter, statt sofort abzubrechen.",[103,1413,1415],{"id":1414},"logs-prüfen","Logs prüfen",[223,1417,1419],{"className":225,"code":1418,"language":227,"meta":228,"style":228},"docker compose up -d\ndocker compose logs -f getpublicip\n",[95,1420,1421,1431],{"__ignoreMap":228},[232,1422,1423,1425,1427,1429],{"class":234,"line":235},[232,1424,89],{"class":673},[232,1426,676],{"class":246},[232,1428,679],{"class":246},[232,1430,682],{"class":396},[232,1432,1433,1435,1437,1440,1443],{"class":234,"line":286},[232,1434,89],{"class":673},[232,1436,676],{"class":246},[232,1438,1439],{"class":246}," logs",[232,1441,1442],{"class":396}," -f",[232,1444,1445],{"class":246}," getpublicip\n",[91,1447,1448,1449,1452],{},"Bei einem gesunden Start baut der Agent den Tunnel auf der Schnittstelle ",[95,1450,1451],{},"pi0"," auf, löst Ihre\nZiele auf, installiert die Weiterleitungsregeln und überträgt die Zuordnungen an GetPublicIP.\nDanach läuft der Agent weiter und prüft die Ziele und den Tunnel selbst alle 30 Sekunden.",[91,1454,1455],{},"Ein gesunder Tunnel schreibt eine Zeile wie diese ins Log. Merken Sie sie sich als Vergleich,\nfalls der Tunnel später Probleme macht:",[223,1457,1460],{"className":1458,"code":1459,"language":727},[725],"tunnel status up=true interfaces=1 peers=1 healthy=true handshakeAge=31s rxDelta=0\n",[95,1461,1459],{"__ignoreMap":228},[91,1463,1464,1465,1468,1469,1472,1473,1476],{},"Achten Sie auf ",[95,1466,1467],{},"healthy=true",". ",[95,1470,1471],{},"up=true"," bedeutet nur, dass die Schnittstelle existiert, und\nbleibt auch bei einem Tunnel ",[95,1474,1475],{},"true",", der keinen Verkehr mehr durchlässt.",[103,1478,1480],{"id":1479},"testen","Testen",[91,1482,1483,1484,1487],{},"Warten Sie vor dem Testen etwa 30 bis 60 Sekunden. Wenn neue Zuordnungen übertragen werden,\nwechselt Ihre IP-Adresse in den Zustand ",[95,1485,1486],{},"updating",", während wir sie anwenden, und Anfragen in\ndiesem Zeitraum schlagen fehl. Zwei oder drei Fehlschläge, gefolgt von Erfolg, sind normal.",[91,1489,1490],{},"Testen Sie aus einem Netzwerk, das nicht Ihr eigenes ist. Am einfachsten geht das über mobile\nDaten:",[223,1492,1494],{"className":225,"code":1493,"language":227,"meta":228,"style":228},"curl http:\u002F\u002F{YOUR IP ADDRESS}\n",[95,1495,1496],{"__ignoreMap":228},[232,1497,1498,1501,1504,1507],{"class":234,"line":235},[232,1499,1500],{"class":673},"curl",[232,1502,1503],{"class":246}," http:\u002F\u002F{YOUR",[232,1505,1506],{"class":246}," IP",[232,1508,1509],{"class":246}," ADDRESS}\n",[103,1511,456],{"id":1512},"verbindungsabbrüche",[91,1514,1515],{},"Der Tunnel baut sich nach einem Verbindungsabbruch, einem Neustart des Routers oder einer neuen\nAdresse von Ihrem Internetanbieter von selbst wieder auf, ohne dass Sie etwas neu starten oder\nkonfigurieren müssen.",[91,1517,1518],{},"Meistens repariert er sich, ohne dass der Agent etwas tun muss. Der Tunnel ist eine ausgehende\nVerbindung, die alle 25 Sekunden durch einen Keepalive offen gehalten wird, und unser Server\nlernt Ihre Adresse aus jedem Paket neu, das der Agent sendet. Verwirft Ihr Router also die\nZuordnung oder weist Ihnen einen neuen Port zu, stellt der nächste Keepalive sie wieder her.",[91,1520,1521,1522,1525,1526,1529],{},"Bei den selteneren Fehlern, die ein Keepalive nicht beheben kann, beendet sich der Agent, statt\nden Tunnel an Ort und Stelle zu reparieren, und Docker startet ihn mit einer frischen\nVerbindung neu. Im Log sehen Sie zuerst ",[95,1523,1524],{},"tunnel appears broken",", sobald er das Problem bemerkt,\nund dann ",[95,1527,1528],{},"exiting so the container is restarted",", wenn es über mehrere Prüfungen hinweg\nbestehen bleibt. Beide Zeilen gehören zur normalen Wiederherstellung.",[91,1531,1532,1533,1535],{},"Die Wiederherstellung hängt von Ihrer Restart-Policy ab, behalten Sie also\n",[95,1534,450],{}," für den Dienst bei. Ohne sie stoppt der Container und bleibt gestoppt.",[91,1537,1538],{},"Solange die Internetverbindung Ihres Hosts ausgefallen ist, sind auch Ihre Dienste nicht\nerreichbar. Der Tunnel baut sich wieder auf, sobald eine Verbindung verfügbar ist.",[103,1540,1286],{"id":1541},"die-echte-client-ip-adresse-sehen",[91,1543,1544,1545,1548],{},"Standardmäßig sehen Ihre Container nicht die IP-Adresse des Besuchers. Der GetPublicIP-Container\nschreibt beim Weiterleiten die Quelladresse des eingehenden Verkehrs um, und jeder Besucher\nerscheint in Ihren Access-Logs daher mit derselben lokalen IP-Adresse. Geolokalisierung, Rate\nLimiting pro Client, Missbrauchssperren und ",[95,1546,1547],{},"fail2ban"," sehen alle nur eine IP-Adresse.",[91,1550,1551,1554],{},[95,1552,1553],{},"GETPUBLICIP_PRESERVE_CLIENT_IP"," schaltet das Umschreiben ab, und Ihre Container sehen dann die\nechte IP-Adresse des Clients.",[91,1556,1557,1560,1561,1563],{},[115,1558,1559],{},"Dafür muss jeder Dienst geändert werden, an den Sie weiterleiten. Lesen Sie deshalb diesen\nAbschnitt, bevor Sie es aktivieren.","\nSolange die Quelladresse auf eine im Compose-Netzwerk umgeschrieben wird, antworten Ihre Dienste\nautomatisch über den GetPublicIP-Container. Ist ",[95,1562,1553],{}," aktiv, muss die\nStandardroute jedes Dienstes auf den GetPublicIP-Container zeigen, damit seine Antworten über\nIhre öffentliche IP-Adresse zum Client zurückgelangen. Ohne diese Route gehen die Antworten über\nIhren normalen Internetanschluss hinaus, und der Client verwirft sie.",[91,1565,1566],{},[115,1567,974,1568,978],{},[95,1569,1570],{},"1.1.0",[91,1572,1573],{},"Die Einstellung gilt für den ganzen Agenten und nicht für eine einzelne Zuordnung, sie wirkt\nsich also auf jeden Dienst aus, an den dieser Agent weiterleitet.",[459,1575,1577],{"id":1576},"warum-sich-die-standardroute-ändern-muss","Warum sich die Standardroute ändern muss",[91,1579,1580],{},"Alles Weitere in diesem Abschnitt folgt daraus, was mit einer eingehenden Anfrage und ihrer\nausgehenden Antwort geschieht:",[1582,1583,1585],"h4",{"id":1584},"ablauf-im-standardmodus","Ablauf im Standardmodus",[223,1587,1590],{"className":1588,"code":1589,"language":727},[725],"visitor 203.0.113.9 → your public IP → tunnel → agent \nagent rewrites the source to its own address, 172.29.7.2\nweb replies to 172.29.7.2, which is on its own subnet\nagent puts the real address back, reply leaves through the tunnel\n",[95,1591,1589],{"__ignoreMap":228},[1582,1593,1595],{"id":1594},"ablauf-mit-erhaltener-client-ip","Ablauf mit erhaltener Client-IP",[223,1597,1600],{"className":1598,"code":1599,"language":727},[725],"visitor 203.0.113.9 → your public IP → tunnel → agent\nweb sees 203.0.113.9 and then send replies to 203.0.113.9\nthe web container reply will follow the default route \n",[95,1601,1599],{"__ignoreMap":228},[91,1603,1604],{},"Ein Container entscheidet, wohin er eine Antwort schickt, indem er zuerst sein eigenes Subnetz\nund dann seine Standardroute betrachtet. Solange die Quelladresse umgeschrieben wird, ist jede\nAntwort an etwas im lokalen Subnetz adressiert, und die Standardroute kommt nie ins Spiel. Ist\ndie Erhaltung der Client-IP aktiv, ist jede Antwort an ein Ziel irgendwo im Internet\nadressiert, also entscheidet die Standardroute über alle. Die Lösung ist daher eine Route, die\nin jedem Dienst gesetzt wird, und keine Einstellung am Agenten kann sie ersetzen.",[91,1606,1607],{},"Docker bietet dafür keine eingebaute Möglichkeit. Die Beispiele unten setzen die Standardroute\njedes Dienst-Containers deshalb mit einem kleinen Sidecar-Container.",[459,1609,1611],{"id":1610},"beispielprojekt","Beispielprojekt",[91,1613,1614],{},"Es gibt zwei Versionen desselben Projekts. Beginnen Sie mit der reinen IPv4-Variante, sofern\nSie nicht auch Ihre öffentliche IPv6-Adresse weiterleiten. Jede IPv6-Zeile unten muss zusätzlich\nstimmen, und ein halb fertiges IPv6-Setup ergibt einen Dienst, der über IPv4 funktioniert und\nüber IPv6 hängt.",[1582,1616,1618],{"id":1617},"nur-ipv4","Nur IPv4",[223,1620,1622],{"className":271,"code":1621,"language":273,"meta":228,"style":228},"services:\n  getpublicip:\n    image: ghcr.io\u002Fgetpublicip\u002Fgetpublicip:latest\n    restart: unless-stopped\n    environment:\n      GETPUBLICIP_API_KEY: \"${GETPUBLICIP_API_KEY}\"\n      GETPUBLICIP_MAPPINGS: \"80\u002Ftcp->web:80\"\n      GETPUBLICIP_PRESERVE_CLIENT_IP: \"true\"\n    cap_add:\n      - NET_ADMIN\n    devices:\n      - \u002Fdev\u002Fnet\u002Ftun\n    sysctls:\n      net.ipv4.ip_forward: 1\n      net.ipv4.conf.all.src_valid_mark: 1\n    networks:\n      appnet:\n        ipv4_address: 172.29.7.2      # fixed, because the sidecar routes to it\n\n  web:\n    image: nginx:alpine\n    restart: unless-stopped\n    networks:\n      appnet:\n        ipv4_address: 172.29.7.3      # give every service a fixed address, not just the agent\n\n  # Points web's default route at the agent, from inside web's own network\n  # namespace. Runs once and exits.\n  web-route:\n    image: alpine:3.20\n    network_mode: \"service:web\"\n    cap_add:\n      - NET_ADMIN\n    restart: \"no\"\n    command: sh -c 'ip route replace default via 172.29.7.2'\n    depends_on:\n      web:\n        condition: service_started\n        restart: true               # re-run this sidecar whenever web restarts\n      getpublicip:\n        condition: service_started\n\nnetworks:\n  appnet:\n    driver: bridge\n    ipam:\n      config:\n        - subnet: 172.29.7.0\u002F24\n          gateway: 172.29.7.1\n",[95,1623,1624,1630,1636,1644,1652,1658,1666,1674,1684,1690,1696,1702,1708,1714,1722,1730,1736,1743,1756,1760,1766,1774,1782,1788,1794,1806,1810,1816,1822,1830,1840,1851,1858,1865,1875,1886,1894,1902,1913,1926,1934,1943,1948,1955,1962,1973,1980,1987,1998],{"__ignoreMap":228},[232,1625,1626,1628],{"class":234,"line":235},[232,1627,280],{"class":242},[232,1629,283],{"class":238},[232,1631,1632,1634],{"class":234,"line":286},[232,1633,289],{"class":242},[232,1635,283],{"class":238},[232,1637,1638,1640,1642],{"class":234,"line":294},[232,1639,297],{"class":242},[232,1641,300],{"class":238},[232,1643,303],{"class":246},[232,1645,1646,1648,1650],{"class":234,"line":306},[232,1647,309],{"class":242},[232,1649,300],{"class":238},[232,1651,314],{"class":246},[232,1653,1654,1656],{"class":234,"line":317},[232,1655,320],{"class":242},[232,1657,283],{"class":238},[232,1659,1660,1662,1664],{"class":234,"line":325},[232,1661,328],{"class":242},[232,1663,300],{"class":238},[232,1665,333],{"class":246},[232,1667,1668,1670,1672],{"class":234,"line":336},[232,1669,339],{"class":242},[232,1671,300],{"class":238},[232,1673,567],{"class":246},[232,1675,1676,1679,1681],{"class":234,"line":347},[232,1677,1678],{"class":242},"      GETPUBLICIP_PRESERVE_CLIENT_IP",[232,1680,300],{"class":238},[232,1682,1683],{"class":246},"\"true\"\n",[232,1685,1686,1688],{"class":234,"line":355},[232,1687,350],{"class":242},[232,1689,283],{"class":238},[232,1691,1692,1694],{"class":234,"line":364},[232,1693,358],{"class":238},[232,1695,361],{"class":246},[232,1697,1698,1700],{"class":234,"line":372},[232,1699,367],{"class":242},[232,1701,283],{"class":238},[232,1703,1704,1706],{"class":234,"line":380},[232,1705,358],{"class":238},[232,1707,377],{"class":246},[232,1709,1710,1712],{"class":234,"line":388},[232,1711,383],{"class":242},[232,1713,283],{"class":238},[232,1715,1716,1718,1720],{"class":234,"line":400},[232,1717,391],{"class":242},[232,1719,300],{"class":238},[232,1721,397],{"class":396},[232,1723,1724,1726,1728],{"class":234,"line":410},[232,1725,403],{"class":242},[232,1727,300],{"class":238},[232,1729,397],{"class":396},[232,1731,1732,1734],{"class":234,"line":420},[232,1733,423],{"class":242},[232,1735,283],{"class":238},[232,1737,1738,1741],{"class":234,"line":428},[232,1739,1740],{"class":242},"      appnet",[232,1742,283],{"class":238},[232,1744,1745,1748,1750,1753],{"class":234,"line":594},[232,1746,1747],{"class":242},"        ipv4_address",[232,1749,300],{"class":238},[232,1751,1752],{"class":396},"172.29.7.2",[232,1754,1755],{"class":1242},"      # fixed, because the sidecar routes to it\n",[232,1757,1758],{"class":234,"line":601},[232,1759,522],{"emptyLinePlaceholder":521},[232,1761,1762,1764],{"class":234,"line":610},[232,1763,485],{"class":242},[232,1765,283],{"class":238},[232,1767,1768,1770,1772],{"class":234,"line":619},[232,1769,297],{"class":242},[232,1771,300],{"class":238},[232,1773,496],{"class":246},[232,1775,1776,1778,1780],{"class":234,"line":628},[232,1777,309],{"class":242},[232,1779,300],{"class":238},[232,1781,314],{"class":246},[232,1783,1784,1786],{"class":234,"line":635},[232,1785,423],{"class":242},[232,1787,283],{"class":238},[232,1789,1790,1792],{"class":234,"line":642},[232,1791,1740],{"class":242},[232,1793,283],{"class":238},[232,1795,1796,1798,1800,1803],{"class":234,"line":647},[232,1797,1747],{"class":242},[232,1799,300],{"class":238},[232,1801,1802],{"class":396},"172.29.7.3",[232,1804,1805],{"class":1242},"      # give every service a fixed address, not just the agent\n",[232,1807,1808],{"class":234,"line":655},[232,1809,522],{"emptyLinePlaceholder":521},[232,1811,1813],{"class":234,"line":1812},27,[232,1814,1815],{"class":1242},"  # Points web's default route at the agent, from inside web's own network\n",[232,1817,1819],{"class":234,"line":1818},28,[232,1820,1821],{"class":1242},"  # namespace. Runs once and exits.\n",[232,1823,1825,1828],{"class":234,"line":1824},29,[232,1826,1827],{"class":242},"  web-route",[232,1829,283],{"class":238},[232,1831,1833,1835,1837],{"class":234,"line":1832},30,[232,1834,297],{"class":242},[232,1836,300],{"class":238},[232,1838,1839],{"class":246},"alpine:3.20\n",[232,1841,1843,1846,1848],{"class":234,"line":1842},31,[232,1844,1845],{"class":242},"    network_mode",[232,1847,300],{"class":238},[232,1849,1850],{"class":246},"\"service:web\"\n",[232,1852,1854,1856],{"class":234,"line":1853},32,[232,1855,350],{"class":242},[232,1857,283],{"class":238},[232,1859,1861,1863],{"class":234,"line":1860},33,[232,1862,358],{"class":238},[232,1864,361],{"class":246},[232,1866,1868,1870,1872],{"class":234,"line":1867},34,[232,1869,309],{"class":242},[232,1871,300],{"class":238},[232,1873,1874],{"class":246},"\"no\"\n",[232,1876,1878,1881,1883],{"class":234,"line":1877},35,[232,1879,1880],{"class":242},"    command",[232,1882,300],{"class":238},[232,1884,1885],{"class":246},"sh -c 'ip route replace default via 172.29.7.2'\n",[232,1887,1889,1892],{"class":234,"line":1888},36,[232,1890,1891],{"class":242},"    depends_on",[232,1893,283],{"class":238},[232,1895,1897,1900],{"class":234,"line":1896},37,[232,1898,1899],{"class":242},"      web",[232,1901,283],{"class":238},[232,1903,1905,1908,1910],{"class":234,"line":1904},38,[232,1906,1907],{"class":242},"        condition",[232,1909,300],{"class":238},[232,1911,1912],{"class":246},"service_started\n",[232,1914,1916,1919,1921,1923],{"class":234,"line":1915},39,[232,1917,1918],{"class":242},"        restart",[232,1920,300],{"class":238},[232,1922,1475],{"class":396},[232,1924,1925],{"class":1242},"               # re-run this sidecar whenever web restarts\n",[232,1927,1929,1932],{"class":234,"line":1928},40,[232,1930,1931],{"class":242},"      getpublicip",[232,1933,283],{"class":238},[232,1935,1937,1939,1941],{"class":234,"line":1936},41,[232,1938,1907],{"class":242},[232,1940,300],{"class":238},[232,1942,1912],{"class":246},[232,1944,1946],{"class":234,"line":1945},42,[232,1947,522],{"emptyLinePlaceholder":521},[232,1949,1951,1953],{"class":234,"line":1950},43,[232,1952,650],{"class":242},[232,1954,283],{"class":238},[232,1956,1958,1960],{"class":234,"line":1957},44,[232,1959,658],{"class":242},[232,1961,283],{"class":238},[232,1963,1965,1968,1970],{"class":234,"line":1964},45,[232,1966,1967],{"class":242},"    driver",[232,1969,300],{"class":238},[232,1971,1972],{"class":246},"bridge\n",[232,1974,1976,1978],{"class":234,"line":1975},46,[232,1977,1034],{"class":242},[232,1979,283],{"class":238},[232,1981,1983,1985],{"class":234,"line":1982},47,[232,1984,1041],{"class":242},[232,1986,283],{"class":238},[232,1988,1990,1992,1994,1996],{"class":234,"line":1989},48,[232,1991,1048],{"class":238},[232,1993,1051],{"class":242},[232,1995,300],{"class":238},[232,1997,1056],{"class":246},[232,1999,2001,2004,2006],{"class":234,"line":2000},49,[232,2002,2003],{"class":242},"          gateway",[232,2005,300],{"class":238},[232,2007,2008],{"class":396},"172.29.7.1\n",[1582,2010,2012],{"id":2011},"ipv4-und-ipv6","IPv4 und IPv6",[91,2014,2015,2016,2018,2019,2022,2023,2026],{},"Dasselbe Projekt mit der IPv6-Hälfte. Vier Dinge ändern sich: Das Netzwerk erhält\n",[95,2017,1001],{}," und ein IPv6-Subnetz, jeder Dienst erhält eine feste ",[95,2020,2021],{},"ipv6_address",", der\nAgent erhält den sysctl ",[95,2024,2025],{},"net.ipv6.conf.all.forwarding",", und der Sidecar setzt eine zweite\nStandardroute.",[223,2028,2030],{"className":271,"code":2029,"language":273,"meta":228,"style":228},"services:\n  getpublicip:\n    image: ghcr.io\u002Fgetpublicip\u002Fgetpublicip:latest\n    restart: unless-stopped\n    environment:\n      GETPUBLICIP_API_KEY: \"${GETPUBLICIP_API_KEY}\"\n      GETPUBLICIP_MAPPINGS: \"80\u002Ftcp\u002Fipv4,ipv6->web:80\"\n      GETPUBLICIP_PRESERVE_CLIENT_IP: \"true\"\n    cap_add:\n      - NET_ADMIN\n    devices:\n      - \u002Fdev\u002Fnet\u002Ftun\n    sysctls:\n      net.ipv4.ip_forward: 1\n      net.ipv4.conf.all.src_valid_mark: 1\n      net.ipv6.conf.all.forwarding: 1\n    networks:\n      appnet:\n        ipv4_address: 172.29.7.2      # fixed, because the sidecar routes to it\n        ipv6_address: fd00:c0de:7::2\n\n  web:\n    image: nginx:alpine\n    restart: unless-stopped\n    networks:\n      appnet:\n        ipv4_address: 172.29.7.3      # give every service a fixed address, not just the agent\n        ipv6_address: fd00:c0de:7::3\n\n  # Points web's default routes at the agent, from inside web's own network\n  # namespace. Runs once and exits. Both families need their own route.\n  web-route:\n    image: alpine:3.20\n    network_mode: \"service:web\"\n    cap_add:\n      - NET_ADMIN\n    restart: \"no\"\n    command: >\n      sh -c 'ip route replace default via 172.29.7.2;\n      ip -6 route replace default via fd00:c0de:7::2'\n    depends_on:\n      web:\n        condition: service_started\n        restart: true               # re-run this sidecar whenever web restarts\n      getpublicip:\n        condition: service_started\n\nnetworks:\n  appnet:\n    driver: bridge\n    enable_ipv6: true\n    ipam:\n      config:\n        - subnet: 172.29.7.0\u002F24\n          gateway: 172.29.7.1\n        - subnet: fd00:c0de:7::\u002F64\n          gateway: fd00:c0de:7::1\n",[95,2031,2032,2038,2044,2052,2060,2066,2074,2083,2091,2097,2103,2109,2115,2121,2129,2137,2145,2151,2157,2167,2177,2181,2187,2195,2203,2209,2215,2225,2234,2238,2243,2248,2254,2262,2270,2276,2282,2290,2299,2304,2309,2315,2321,2329,2339,2345,2353,2357,2363,2369,2378,2387,2394,2401,2412,2421,2433],{"__ignoreMap":228},[232,2033,2034,2036],{"class":234,"line":235},[232,2035,280],{"class":242},[232,2037,283],{"class":238},[232,2039,2040,2042],{"class":234,"line":286},[232,2041,289],{"class":242},[232,2043,283],{"class":238},[232,2045,2046,2048,2050],{"class":234,"line":294},[232,2047,297],{"class":242},[232,2049,300],{"class":238},[232,2051,303],{"class":246},[232,2053,2054,2056,2058],{"class":234,"line":306},[232,2055,309],{"class":242},[232,2057,300],{"class":238},[232,2059,314],{"class":246},[232,2061,2062,2064],{"class":234,"line":317},[232,2063,320],{"class":242},[232,2065,283],{"class":238},[232,2067,2068,2070,2072],{"class":234,"line":325},[232,2069,328],{"class":242},[232,2071,300],{"class":238},[232,2073,333],{"class":246},[232,2075,2076,2078,2080],{"class":234,"line":336},[232,2077,339],{"class":242},[232,2079,300],{"class":238},[232,2081,2082],{"class":246},"\"80\u002Ftcp\u002Fipv4,ipv6->web:80\"\n",[232,2084,2085,2087,2089],{"class":234,"line":347},[232,2086,1678],{"class":242},[232,2088,300],{"class":238},[232,2090,1683],{"class":246},[232,2092,2093,2095],{"class":234,"line":355},[232,2094,350],{"class":242},[232,2096,283],{"class":238},[232,2098,2099,2101],{"class":234,"line":364},[232,2100,358],{"class":238},[232,2102,361],{"class":246},[232,2104,2105,2107],{"class":234,"line":372},[232,2106,367],{"class":242},[232,2108,283],{"class":238},[232,2110,2111,2113],{"class":234,"line":380},[232,2112,358],{"class":238},[232,2114,377],{"class":246},[232,2116,2117,2119],{"class":234,"line":388},[232,2118,383],{"class":242},[232,2120,283],{"class":238},[232,2122,2123,2125,2127],{"class":234,"line":400},[232,2124,391],{"class":242},[232,2126,300],{"class":238},[232,2128,397],{"class":396},[232,2130,2131,2133,2135],{"class":234,"line":410},[232,2132,403],{"class":242},[232,2134,300],{"class":238},[232,2136,397],{"class":396},[232,2138,2139,2141,2143],{"class":234,"line":420},[232,2140,413],{"class":242},[232,2142,300],{"class":238},[232,2144,397],{"class":396},[232,2146,2147,2149],{"class":234,"line":428},[232,2148,423],{"class":242},[232,2150,283],{"class":238},[232,2152,2153,2155],{"class":234,"line":594},[232,2154,1740],{"class":242},[232,2156,283],{"class":238},[232,2158,2159,2161,2163,2165],{"class":234,"line":601},[232,2160,1747],{"class":242},[232,2162,300],{"class":238},[232,2164,1752],{"class":396},[232,2166,1755],{"class":1242},[232,2168,2169,2172,2174],{"class":234,"line":610},[232,2170,2171],{"class":242},"        ipv6_address",[232,2173,300],{"class":238},[232,2175,2176],{"class":246},"fd00:c0de:7::2\n",[232,2178,2179],{"class":234,"line":619},[232,2180,522],{"emptyLinePlaceholder":521},[232,2182,2183,2185],{"class":234,"line":628},[232,2184,485],{"class":242},[232,2186,283],{"class":238},[232,2188,2189,2191,2193],{"class":234,"line":635},[232,2190,297],{"class":242},[232,2192,300],{"class":238},[232,2194,496],{"class":246},[232,2196,2197,2199,2201],{"class":234,"line":642},[232,2198,309],{"class":242},[232,2200,300],{"class":238},[232,2202,314],{"class":246},[232,2204,2205,2207],{"class":234,"line":647},[232,2206,423],{"class":242},[232,2208,283],{"class":238},[232,2210,2211,2213],{"class":234,"line":655},[232,2212,1740],{"class":242},[232,2214,283],{"class":238},[232,2216,2217,2219,2221,2223],{"class":234,"line":1812},[232,2218,1747],{"class":242},[232,2220,300],{"class":238},[232,2222,1802],{"class":396},[232,2224,1805],{"class":1242},[232,2226,2227,2229,2231],{"class":234,"line":1818},[232,2228,2171],{"class":242},[232,2230,300],{"class":238},[232,2232,2233],{"class":246},"fd00:c0de:7::3\n",[232,2235,2236],{"class":234,"line":1824},[232,2237,522],{"emptyLinePlaceholder":521},[232,2239,2240],{"class":234,"line":1832},[232,2241,2242],{"class":1242},"  # Points web's default routes at the agent, from inside web's own network\n",[232,2244,2245],{"class":234,"line":1842},[232,2246,2247],{"class":1242},"  # namespace. Runs once and exits. Both families need their own route.\n",[232,2249,2250,2252],{"class":234,"line":1853},[232,2251,1827],{"class":242},[232,2253,283],{"class":238},[232,2255,2256,2258,2260],{"class":234,"line":1860},[232,2257,297],{"class":242},[232,2259,300],{"class":238},[232,2261,1839],{"class":246},[232,2263,2264,2266,2268],{"class":234,"line":1867},[232,2265,1845],{"class":242},[232,2267,300],{"class":238},[232,2269,1850],{"class":246},[232,2271,2272,2274],{"class":234,"line":1877},[232,2273,350],{"class":242},[232,2275,283],{"class":238},[232,2277,2278,2280],{"class":234,"line":1888},[232,2279,358],{"class":238},[232,2281,361],{"class":246},[232,2283,2284,2286,2288],{"class":234,"line":1896},[232,2285,309],{"class":242},[232,2287,300],{"class":238},[232,2289,1874],{"class":246},[232,2291,2292,2294,2296],{"class":234,"line":1904},[232,2293,1880],{"class":242},[232,2295,300],{"class":238},[232,2297,2298],{"class":242},">\n",[232,2300,2301],{"class":234,"line":1915},[232,2302,2303],{"class":246},"      sh -c 'ip route replace default via 172.29.7.2;\n",[232,2305,2306],{"class":234,"line":1928},[232,2307,2308],{"class":246},"      ip -6 route replace default via fd00:c0de:7::2'\n",[232,2310,2311,2313],{"class":234,"line":1936},[232,2312,1891],{"class":242},[232,2314,283],{"class":238},[232,2316,2317,2319],{"class":234,"line":1945},[232,2318,1899],{"class":242},[232,2320,283],{"class":238},[232,2322,2323,2325,2327],{"class":234,"line":1950},[232,2324,1907],{"class":242},[232,2326,300],{"class":238},[232,2328,1912],{"class":246},[232,2330,2331,2333,2335,2337],{"class":234,"line":1957},[232,2332,1918],{"class":242},[232,2334,300],{"class":238},[232,2336,1475],{"class":396},[232,2338,1925],{"class":1242},[232,2340,2341,2343],{"class":234,"line":1964},[232,2342,1931],{"class":242},[232,2344,283],{"class":238},[232,2346,2347,2349,2351],{"class":234,"line":1975},[232,2348,1907],{"class":242},[232,2350,300],{"class":238},[232,2352,1912],{"class":246},[232,2354,2355],{"class":234,"line":1982},[232,2356,522],{"emptyLinePlaceholder":521},[232,2358,2359,2361],{"class":234,"line":1989},[232,2360,650],{"class":242},[232,2362,283],{"class":238},[232,2364,2365,2367],{"class":234,"line":2000},[232,2366,658],{"class":242},[232,2368,283],{"class":238},[232,2370,2372,2374,2376],{"class":234,"line":2371},50,[232,2373,1967],{"class":242},[232,2375,300],{"class":238},[232,2377,1972],{"class":246},[232,2379,2381,2383,2385],{"class":234,"line":2380},51,[232,2382,1024],{"class":242},[232,2384,300],{"class":238},[232,2386,1029],{"class":396},[232,2388,2390,2392],{"class":234,"line":2389},52,[232,2391,1034],{"class":242},[232,2393,283],{"class":238},[232,2395,2397,2399],{"class":234,"line":2396},53,[232,2398,1041],{"class":242},[232,2400,283],{"class":238},[232,2402,2404,2406,2408,2410],{"class":234,"line":2403},54,[232,2405,1048],{"class":238},[232,2407,1051],{"class":242},[232,2409,300],{"class":238},[232,2411,1056],{"class":246},[232,2413,2415,2417,2419],{"class":234,"line":2414},55,[232,2416,2003],{"class":242},[232,2418,300],{"class":238},[232,2420,2008],{"class":396},[232,2422,2424,2426,2428,2430],{"class":234,"line":2423},56,[232,2425,1048],{"class":238},[232,2427,1051],{"class":242},[232,2429,300],{"class":238},[232,2431,2432],{"class":246},"fd00:c0de:7::\u002F64\n",[232,2434,2436,2438,2440],{"class":234,"line":2435},57,[232,2437,2003],{"class":242},[232,2439,300],{"class":238},[232,2441,2442],{"class":246},"fd00:c0de:7::1\n",[91,2444,2445],{},"Egal, mit welcher Variante Sie beginnen: Wiederholen Sie den Sidecar für jeden Dienst, an den\nSie weiterleiten, und prüfen Sie die vier folgenden Punkte. Ist einer davon falsch, hängt der\nDienst, ohne einen Fehler zu melden.",[91,2447,2448,2451,2452,2455,2456,192],{},[115,2449,2450],{},"Geben Sie jedem Dienst im Netzwerk eine feste Adresse, nicht nur dem Agenten."," Ein Dienst\nohne feste Adresse nimmt die niedrigste freie Adresse, und das ist die, die Sie für den Agenten\nreserviert haben. Wegen ",[95,2453,2454],{},"depends_on"," startet er oft zuerst und belegt sie. Der Agent startet\ndann überhaupt nicht und meldet ",[95,2457,2458],{},"Address already in use",[91,2460,2461,2464,2465,2468],{},[115,2462,2463],{},"Wenn Sie IPv6 weiterleiten, setzen Sie beide Routen."," Die IPv6-Standardroute ist unabhängig\nvon der IPv4-Route. Ein Sidecar, der nur die IPv4-Route setzt, lässt IPv6-Antworten also über\ndie Bridge hinausgehen, und diese Verbindungen hängen, während IPv4 funktioniert. Die zweite\nZeile ",[95,2466,2467],{},"ip -6 route replace"," im Dual-Stack-Beispiel setzt sie. Fehlt sie, ist das der häufigste\nGrund, warum diese Variante schiefgeht, denn alles, was Sie über IPv4 testen, funktioniert.",[91,2470,2471,2474,2475,2477,2478,2481,2482,2484,2485,199,2488,2491],{},[115,2472,2473],{},"Die Route überlebt keinen Neustart Ihres Dienstes."," Docker baut einen neuen\nNetzwerk-Namespace mit leerer Routingtabelle auf. Die Route ist also weg, und eingehender\nVerkehr stoppt, bis der Sidecar wieder läuft. Darum kümmert sich das ",[95,2476,2454],{}," oben:\n",[95,2479,2480],{},"restart: true"," weist Compose an, den Sidecar bei jedem Neustart von ",[95,2483,443],{}," erneut auszuführen.\n",[95,2486,2487],{},"docker compose restart web",[95,2489,2490],{},"docker compose up -d"," reparieren die Route also beide von\nselbst.",[91,2493,2494,2495,2497,2498,2501],{},"Nicht abgedeckt ist ein Neustart Ihres Dienstes, den Docker ohne Sie auslöst. Stürzt ",[95,2496,443],{}," ab\noder wird es vom Out-of-Memory-Killer beendet, holt seine eigene ",[95,2499,2500],{},"restart:","-Policy es zurück,\nohne dass Compose beteiligt ist, und niemand führt den Sidecar erneut aus. Die Route fehlt,\neingehender Verkehr stoppt, und kein Problem wird gemeldet. Stellen Sie sie wieder her mit:",[223,2503,2505],{"className":225,"code":2504,"language":227,"meta":228,"style":228},"docker compose up -d web-route\n",[95,2506,2507],{"__ignoreMap":228},[232,2508,2509,2511,2513,2515,2518],{"class":234,"line":235},[232,2510,89],{"class":673},[232,2512,676],{"class":246},[232,2514,679],{"class":246},[232,2516,2517],{"class":396}," -d",[232,2519,2520],{"class":246}," web-route\n",[91,2522,2523,2524,2527],{},"Wir empfehlen, die Standardroute im Dockerfile des Dienstes zu setzen, damit sie solche\nNeustarts übersteht. Andernfalls prüfen Sie die Routen mit ",[95,2525,2526],{},"docker exec web ip route"," und setzen\ndie Standardroute erneut, sobald sie fehlt.",[91,2529,2530,2533,2534,2539],{},[115,2531,2532],{},"Ziele auf dem Host funktionieren in diesem Modus nicht."," Die Weiterleitung an\n",[120,2535,2538],{"className":2536,"href":2537},[123],"#weiterleitung-an-einen-dienst-auf-dem-host","einen Dienst auf dem Docker-Host","\nsetzt ebenfalls voraus, dass die Antwort über den Agenten zurückkommt, und dafür müsste die\nStandardroute des Hosts selbst geändert werden.",[459,2541,2543],{"id":2542},"prüfen-ob-es-funktioniert","Prüfen, ob es funktioniert",[91,2545,2546],{},"Senden Sie eine Anfrage an Ihre IP-Adresse:",[223,2548,2550],{"className":225,"code":2549,"language":227,"meta":228,"style":228},"curl http:\u002F\u002F{YOUR IP ADDRESS}              # one request through your public IP\ndocker compose logs --tail 10 web           # what your container recorded\n",[95,2551,2552,2566],{"__ignoreMap":228},[232,2553,2554,2556,2558,2560,2563],{"class":234,"line":235},[232,2555,1500],{"class":673},[232,2557,1503],{"class":246},[232,2559,1506],{"class":246},[232,2561,2562],{"class":246}," ADDRESS}",[232,2564,2565],{"class":1242},"              # one request through your public IP\n",[232,2567,2568,2570,2572,2574,2577,2580,2583],{"class":234,"line":286},[232,2569,89],{"class":673},[232,2571,676],{"class":246},[232,2573,1439],{"class":246},[232,2575,2576],{"class":396}," --tail",[232,2578,2579],{"class":396}," 10",[232,2581,2582],{"class":246}," web",[232,2584,2585],{"class":1242},"           # what your container recorded\n",[91,2587,2588,2589,2591],{},"Das Log sollte die echte IP-Adresse des Clients zeigen. Zeigt es ",[95,2590,1752],{},", ist die\nErhaltung der Client-IP nicht aktiv, und Sie sehen das Standardverhalten.",[91,2593,2594],{},"Ein Test vom Docker-Host selbst ist in Ordnung. Die Anfrage geht trotzdem hinaus an Ihre\nöffentliche IP-Adresse, erreicht unser Netzwerk und kommt durch den Tunnel zurück. Ihr\nContainer zeichnet also die öffentliche Adresse Ihres Internetanschlusses auf, die sich leicht\nvon der Bridge-Adresse unterscheiden lässt, die das Umschreiben dort eingetragen hätte.",[91,2596,2597,2598,2601],{},"Wenn Sie IPv6 weiterleiten, prüfen Sie es separat mit ",[95,2599,2600],{},"curl -6",". Die beiden Adressfamilien\nhaben getrennte Standardrouten, eine kann also funktionieren, während die andere defekt ist.",[459,2603,2605],{"id":2604},"wenn-es-nicht-funktioniert","Wenn es nicht funktioniert",[91,2607,2608,2609,2611,2612,2615],{},"Eine falsche Standardroute erzeugt keine Fehlermeldung. Verbindungen hängen, der Tunnel bleibt\naktiv und schreibt weiterhin ",[95,2610,1467],{}," ins Log, die Weiterleitungsregeln bleiben korrekt,\nund nichts in ",[95,2613,2614],{},"docker compose logs getpublicip"," meldet ein Problem, denn aus Sicht des Agenten\ngibt es keines. Die Antworten Ihres Containers gehen auf dem falschen Weg hinaus statt über Ihre\nöffentliche IP-Adresse.",[91,2617,2618],{},"Prüfen Sie die Routingtabelle im Dienst:",[223,2620,2622],{"className":225,"code":2621,"language":227,"meta":228,"style":228},"docker exec web ip route      # default must be via the agent's address\ndocker exec web ip -6 route   # and this one too, if you forward IPv6\n",[95,2623,2624,2642],{"__ignoreMap":228},[232,2625,2626,2628,2631,2633,2636,2639],{"class":234,"line":235},[232,2627,89],{"class":673},[232,2629,2630],{"class":246}," exec",[232,2632,2582],{"class":246},[232,2634,2635],{"class":246}," ip",[232,2637,2638],{"class":246}," route",[232,2640,2641],{"class":1242},"      # default must be via the agent's address\n",[232,2643,2644,2646,2648,2650,2652,2655,2657],{"class":234,"line":286},[232,2645,89],{"class":673},[232,2647,2630],{"class":246},[232,2649,2582],{"class":246},[232,2651,2635],{"class":246},[232,2653,2654],{"class":396}," -6",[232,2656,2638],{"class":246},[232,2658,2659],{"class":1242},"   # and this one too, if you forward IPv6\n",[103,2661,2663],{"id":2662},"ausgehenden-datenverkehr-über-ihre-ip-adresse-senden","Ausgehenden Datenverkehr über Ihre IP-Adresse senden",[91,2665,2666,2667,2670],{},"Die Abschnitte oben behandeln eingehenden Verkehr. ",[95,2668,2669],{},"GETPUBLICIP_OUTBOUND"," betrifft die andere\nRichtung: Ihre Container erreichen das Internet über Ihre öffentliche IP-Adresse statt über die\nAdresse Ihres Internetanbieters. Das hilft, wenn ein Dienst, mit dem Sie sich verbinden, nur\nbekannte Adressen zulässt, oder wenn Ihr ausgehender Verkehr von derselben Adresse kommen soll\nwie Ihr eingehender.",[91,2672,2673],{},"Es erfordert dieselbe Änderung der Standardroute wie die Erhaltung der Client-IP, aus demselben\nGrund: Die Antwort muss über den Agenten zurückkommen. Haben Sie den Sidecar dafür bereits\neingerichtet, müssen Sie nur noch die Einstellung hinzufügen.",[223,2675,2677],{"className":271,"code":2676,"language":273,"meta":228,"style":228},"services:\n  getpublicip:\n    image: ghcr.io\u002Fgetpublicip\u002Fgetpublicip:latest\n    restart: unless-stopped\n    environment:\n      GETPUBLICIP_API_KEY: \"${GETPUBLICIP_API_KEY}\"\n      GETPUBLICIP_MAPPINGS: \"80\u002Ftcp->web:80\"\n      GETPUBLICIP_OUTBOUND: \"true\"\n    cap_add:\n      - NET_ADMIN\n    devices:\n      - \u002Fdev\u002Fnet\u002Ftun\n    sysctls:\n      net.ipv4.ip_forward: 1\n      net.ipv4.conf.all.src_valid_mark: 1\n      net.ipv6.conf.all.forwarding: 1\n    networks:\n      appnet:\n        ipv4_address: 172.29.7.2\n",[95,2678,2679,2685,2691,2699,2707,2713,2721,2729,2738,2744,2750,2756,2762,2768,2776,2784,2792,2798,2804],{"__ignoreMap":228},[232,2680,2681,2683],{"class":234,"line":235},[232,2682,280],{"class":242},[232,2684,283],{"class":238},[232,2686,2687,2689],{"class":234,"line":286},[232,2688,289],{"class":242},[232,2690,283],{"class":238},[232,2692,2693,2695,2697],{"class":234,"line":294},[232,2694,297],{"class":242},[232,2696,300],{"class":238},[232,2698,303],{"class":246},[232,2700,2701,2703,2705],{"class":234,"line":306},[232,2702,309],{"class":242},[232,2704,300],{"class":238},[232,2706,314],{"class":246},[232,2708,2709,2711],{"class":234,"line":317},[232,2710,320],{"class":242},[232,2712,283],{"class":238},[232,2714,2715,2717,2719],{"class":234,"line":325},[232,2716,328],{"class":242},[232,2718,300],{"class":238},[232,2720,333],{"class":246},[232,2722,2723,2725,2727],{"class":234,"line":336},[232,2724,339],{"class":242},[232,2726,300],{"class":238},[232,2728,567],{"class":246},[232,2730,2731,2734,2736],{"class":234,"line":347},[232,2732,2733],{"class":242},"      GETPUBLICIP_OUTBOUND",[232,2735,300],{"class":238},[232,2737,1683],{"class":246},[232,2739,2740,2742],{"class":234,"line":355},[232,2741,350],{"class":242},[232,2743,283],{"class":238},[232,2745,2746,2748],{"class":234,"line":364},[232,2747,358],{"class":238},[232,2749,361],{"class":246},[232,2751,2752,2754],{"class":234,"line":372},[232,2753,367],{"class":242},[232,2755,283],{"class":238},[232,2757,2758,2760],{"class":234,"line":380},[232,2759,358],{"class":238},[232,2761,377],{"class":246},[232,2763,2764,2766],{"class":234,"line":388},[232,2765,383],{"class":242},[232,2767,283],{"class":238},[232,2769,2770,2772,2774],{"class":234,"line":400},[232,2771,391],{"class":242},[232,2773,300],{"class":238},[232,2775,397],{"class":396},[232,2777,2778,2780,2782],{"class":234,"line":410},[232,2779,403],{"class":242},[232,2781,300],{"class":238},[232,2783,397],{"class":396},[232,2785,2786,2788,2790],{"class":234,"line":420},[232,2787,413],{"class":242},[232,2789,300],{"class":238},[232,2791,397],{"class":396},[232,2793,2794,2796],{"class":234,"line":428},[232,2795,423],{"class":242},[232,2797,283],{"class":238},[232,2799,2800,2802],{"class":234,"line":594},[232,2801,1740],{"class":242},[232,2803,283],{"class":238},[232,2805,2806,2808,2810],{"class":234,"line":601},[232,2807,1747],{"class":242},[232,2809,300],{"class":238},[232,2811,2812],{"class":396},"172.29.7.2\n",[91,2814,2815,2816,2820],{},"Lassen Sie dann jeden Container, der das nutzen soll, auf den Agenten zeigen, genau wie im\n",[120,2817,1611],{"className":2818,"href":2819},[123],"#beispielprojekt"," oben. Ein Container, dessen Route\nSie unverändert lassen, nutzt weiterhin die normale Docker-Bridge. Sie können die Dienste also\neinzeln umstellen.",[91,2822,2823],{},"Prüfen Sie es aus einem Container heraus, den Sie umgeleitet haben:",[223,2825,2827],{"className":225,"code":2826,"language":227,"meta":228,"style":228},"docker exec web curl -s https:\u002F\u002Fapi.getpublicip.com\u002Fip\n",[95,2828,2829],{"__ignoreMap":228},[232,2830,2831,2833,2835,2837,2840,2843],{"class":234,"line":235},[232,2832,89],{"class":673},[232,2834,2630],{"class":246},[232,2836,2582],{"class":246},[232,2838,2839],{"class":246}," curl",[232,2841,2842],{"class":396}," -s",[232,2844,2845],{"class":246}," https:\u002F\u002Fapi.getpublicip.com\u002Fip\n",[91,2847,2848],{},"Es sollte Ihre GetPublicIP-Adresse angezeigt werden, nicht die Ihres Zuhauses oder Büros.",[459,2850,2852],{"id":2851},"nur-ausgehend-ohne-portfreigaben","Nur ausgehend, ohne Portfreigaben",[91,2854,2855,2856,2858],{},"Wenn Sie nur die ausgehende Richtung brauchen, ist ",[95,2857,716],{}," optional:",[223,2860,2862],{"className":271,"code":2861,"language":273,"meta":228,"style":228},"    environment:\n      GETPUBLICIP_API_KEY: \"${GETPUBLICIP_API_KEY}\"\n      GETPUBLICIP_OUTBOUND: \"true\"\n",[95,2863,2864,2870,2878],{"__ignoreMap":228},[232,2865,2866,2868],{"class":234,"line":235},[232,2867,320],{"class":242},[232,2869,283],{"class":238},[232,2871,2872,2874,2876],{"class":234,"line":286},[232,2873,328],{"class":242},[232,2875,300],{"class":238},[232,2877,333],{"class":246},[232,2879,2880,2882,2884],{"class":234,"line":294},[232,2881,2733],{"class":242},[232,2883,300],{"class":238},[232,2885,1683],{"class":246},[91,2887,2888],{},"Ein so gestarteter Agent lässt die Portfreigaben Ihrer IP-Adresse, wie sie sind, auch die, die\nSie im Dashboard eingerichtet haben.",[459,2890,2892],{"id":2891},"was-sie-vor-dem-aktivieren-wissen-sollten","Was Sie vor dem Aktivieren wissen sollten",[91,2894,2895,2898],{},[115,2896,2897],{},"Ihre Container teilen sich eine Adresse."," Alles hinter dem Agenten verlässt das Netz mit\nderselben öffentlichen IPv4- und derselben öffentlichen IPv6-Adresse. Die Gegenseite kann Ihre\nContainer also nicht voneinander unterscheiden.",[91,2900,2901,2904],{},[115,2902,2903],{},"Das Verhalten ist ausfallsicher."," Ein über den Agenten geleiteter Container hat gar kein\nInternet, solange der Tunnel unterbrochen ist, während er vorher Ihren normalen Anschluss\ngenutzt hätte. Das ist Absicht, damit Ihr Verkehr nie ohne Ihr Wissen auf die Adresse Ihres\nInternetanbieters ausweicht. Überlegen Sie aber gut, bevor Sie etwas, auf das Sie angewiesen\nsind, über den Agenten leiten.",[91,2906,2907,2910],{},[115,2908,2909],{},"Wenn ein Container das Internet nicht erreicht",", liegt das Problem fast immer an seiner\nRoute und nicht am Agenten. Prüfen Sie im Container selbst:",[223,2912,2914],{"className":225,"code":2913,"language":227,"meta":228,"style":228},"docker exec web ip route      # default must be via the agent's address\ndocker exec web ip -6 route   # and this one too, if you use IPv6\n",[95,2915,2916,2930],{"__ignoreMap":228},[232,2917,2918,2920,2922,2924,2926,2928],{"class":234,"line":235},[232,2919,89],{"class":673},[232,2921,2630],{"class":246},[232,2923,2582],{"class":246},[232,2925,2635],{"class":246},[232,2927,2638],{"class":246},[232,2929,2641],{"class":1242},[232,2931,2932,2934,2936,2938,2940,2942,2944],{"class":234,"line":286},[232,2933,89],{"class":673},[232,2935,2630],{"class":246},[232,2937,2582],{"class":246},[232,2939,2635],{"class":246},[232,2941,2654],{"class":396},[232,2943,2638],{"class":246},[232,2945,2946],{"class":1242},"   # and this one too, if you use IPv6\n",[103,2948,2950],{"id":2949},"container-berechtigungen","Container-Berechtigungen",[731,2952,2953,2963],{},[734,2954,2955],{},[737,2956,2957,2960],{},[740,2958,2959],{},"Einstellung",[740,2961,2962],{},"Wofür sie benötigt wird",[750,2964,2965,2975,2985,2995,3008],{},[737,2966,2967,2972],{},[755,2968,2969],{},[95,2970,2971],{},"cap_add: NET_ADMIN",[755,2973,2974],{},"Konfiguration der WireGuard-Schnittstelle und der Weiterleitungsregeln",[737,2976,2977,2982],{},[755,2978,2979],{},[95,2980,2981],{},"devices: \u002Fdev\u002Fnet\u002Ftun",[755,2983,2984],{},"Das Tunnelgerät selbst",[737,2986,2987,2992],{},[755,2988,2989],{},[95,2990,2991],{},"net.ipv4.ip_forward=1",[755,2993,2994],{},"Weiterleitung des Verkehrs vom Tunnel an Ihren Ziel-Container",[737,2996,2997,3002],{},[755,2998,2999],{},[95,3000,3001],{},"net.ipv4.conf.all.src_valid_mark=1",[755,3003,3004,3005],{},"Erforderlich für das Routing-Setup von ",[95,3006,3007],{},"wg-quick",[737,3009,3010,3015],{},[755,3011,3012],{},[95,3013,3014],{},"net.ipv6.conf.all.forwarding=1",[755,3016,3017],{},"Nur nötig, wenn Sie IPv6 weiterleiten",[103,3019,39],{"id":3020},"macos",[91,3022,3023,3024,3027],{},"Verwenden Sie ",[120,3025,153],{"className":3026,"href":151,"target":152},[123],",\ndann funktioniert die Compose-Datei oben unverändert, auf Intel ebenso wie auf Apple Silicon.",[91,3029,3030],{},"Andere Docker-Laufzeitumgebungen für macOS (Colima, OrbStack, Rancher Desktop) verwenden andere\nKernels und wurden nicht geprüft. Wir können daher nicht sagen, ob der Tunnel dort aufgebaut\nwird.",[103,3032,43],{"id":3033},"windows",[91,3035,3036,3037,3040],{},"Die Compose-Datei oben braucht unter Windows mit ",[120,3038,153],{"className":3039,"href":151,"target":152},[123]," keine Änderungen.",[91,3042,3043],{},"Docker Desktop benötigt ein 64-Bit-Windows 10 oder 11 in einer Version, die Microsoft noch\nunterstützt, sowie das WSL-2-Backend, das standardmäßig verwendet wird. Vor dem Start sollten\nSie dann zwei Dinge prüfen.",[91,3045,3046,3049],{},[115,3047,3048],{},"1. Docker Desktop muss im Modus für Linux-Container laufen."," Die Engine für\nWindows-Container kann dieses Image nicht ausführen und steht mit dem WSL-2-Backend ohnehin\nnicht zur Verfügung.",[91,3051,3052,3055,3056,3059],{},[115,3053,3054],{},"2. Ihr WSL2-Kernel muss Version 6.6.x haben."," Älteren Kernels, darunter 5.15, fehlt ein\nNetfilter-Modul, das der Tunnel benötigt, und aus dem Container heraus lässt sich das nicht\numgehen. Der Tunnel kommt dann nicht zustande und meldet\n",[95,3057,3058],{},"unknown option '--save-mark'",". Prüfen und aktualisieren Sie das in PowerShell:",[223,3061,3065],{"className":3062,"code":3063,"language":3064,"meta":228,"style":228},"language-powershell shiki shiki-themes monokai","wsl --version    # need \"Kernel version: 6.6.x\"\nwsl --update     # if it reports anything older\n","powershell",[95,3066,3067,3072],{"__ignoreMap":228},[232,3068,3069],{"class":234,"line":235},[232,3070,3071],{},"wsl --version    # need \"Kernel version: 6.6.x\"\n",[232,3073,3074],{"class":234,"line":286},[232,3075,3076],{},"wsl --update     # if it reports anything older\n",[91,3078,3079],{},"6.6 wurde erst um WSL 2.4 bis 2.7 herum zum festen Standard. Ein Rechner, der länger nicht\naktualisiert wurde, kann also noch auf 5.15 laufen. Dieselbe Voraussetzung gilt, wenn Sie statt\nDocker Desktop Docker CE in einer WSL2-Distribution betreiben, denn diese nutzt denselben\nKernel.",[91,3081,3082,3083,3086],{},"Unter 6.6 ist ",[95,3084,3085],{},"tun"," ein Modul und nicht fest eingebaut. Prüfen Sie daher, ob der Geräteknoten\nexistiert, bevor Sie den Fehler beim Agenten suchen. Dieser Befehl schlägt schon beim Erstellen\ndes Containers fehl, wenn er fehlt:",[223,3088,3090],{"className":3062,"code":3089,"language":3064,"meta":228,"style":228},"docker run --rm --device \u002Fdev\u002Fnet\u002Ftun alpine ls -l \u002Fdev\u002Fnet\u002Ftun\n",[95,3091,3092],{"__ignoreMap":228},[232,3093,3094],{"class":234,"line":235},[232,3095,3089],{},[91,3097,3098],{},"Sie brauchen weder eine Regel in der Windows-Firewall noch eine Portweiterleitung. Eingehender\nVerkehr kommt über den Tunnel an, weder die Windows-Firewall noch das NAT von WSL liegen also\nauf dem Weg.",[103,3100,3102],{"id":3101},"laptops-und-ruhezustand","Laptops und Ruhezustand",[91,3104,3105,3108],{},[115,3106,3107],{},"Der Ruhezustand unterbricht den Tunnel."," Unter macOS und Windows pausiert die Linux-VM, wenn\nIhr Rechner in den Ruhezustand geht, und Ihre öffentliche IP-Adresse ist bis zum Aufwachen\nnicht erreichbar; danach baut sich der Tunnel automatisch wieder auf. Probieren Sie es gern auf\nIhrem Laptop aus, betreiben Sie es aber auf einem Server: Ein Rechner, der schläft, ist ein\nschlechter Host für eine öffentliche IP-Adresse, die immer erreichbar sein soll.",[103,3110,3112],{"id":3111},"ein-api-schlüssel-ein-tunnel","Ein API-Schlüssel, ein Tunnel",[3114,3115,3116],"blockquote",{},[91,3117,3118],{},"Ein WireGuard-Schlüssel gehört zu genau einem Endpunkt. Laufen zwei Container mit demselben\nAPI-Schlüssel, werfen sie sich gegenseitig aus der Verbindung. Es gewinnt jeweils der, dessen\nHandshake am jüngsten ist, und der andere verwirft stillschweigend Verkehr bis zu seinem\nnächsten Keepalive. Das sieht nach zufälliger Unzuverlässigkeit aus statt nach einem klaren\nFehler. Die übliche Ursache ist ein Test auf dem Laptop, während ein Server bereits mit\ndemselben Schlüssel verbunden ist.",[91,3120,3121],{},"Dieses Problem diagnostiziert sich selbst: Beide Container starten immer wieder neu, weil jeder\nvon ihnen zu dem Schluss kommt, er sei der defekte. Ein Container, der in einer Neustartschleife\nhängt, obwohl die Internetverbindung des Rechners in Ordnung ist, bedeutet fast immer, dass ein\nzweiter Agent denselben Schlüssel verwendet.",[91,3123,3124],{},"Verwenden Sie einen API-Schlüssel pro laufendem Tunnel.",[103,3126,3128],{"id":3127},"fehlerbehebung","Fehlerbehebung",[91,3130,3131,3132,192],{},"Beginnen Sie mit ",[95,3133,3134],{},"docker compose logs -f getpublicip",[731,3136,3137,3147],{},[734,3138,3139],{},[737,3140,3141,3144],{},[740,3142,3143],{},"Was Sie sehen",[740,3145,3146],{},"Was es bedeutet",[750,3148,3149,3162,3172,3181,3197,3213,3223,3231,3245,3257,3267,3276,3298,3308,3321,3339,3358,3372,3382,3399],{},[737,3150,3151,3156],{},[755,3152,3153],{},[95,3154,3155],{},"GETPUBLICIP_API_KEY is required",[755,3157,3158,3159,3161],{},"Die Variable ist nicht gesetzt, oder Ihre ",[95,3160,217],{},"-Datei wird nicht eingelesen",[737,3163,3164,3169],{},[755,3165,3166],{},[95,3167,3168],{},"tunnel up: … 401",[755,3170,3171],{},"Der API-Schlüssel ist ungültig",[737,3173,3174,3178],{},[755,3175,3176],{},[95,3177,1410],{},[755,3179,3180],{},"Das Ziel läuft noch nicht, der Dienstname ist falsch, oder der Agent teilt kein Netzwerk mit ihm",[737,3182,3183,3188],{},[755,3184,3185,3187],{},[95,3186,3007],{}," oder Berechtigungsfehler",[755,3189,3190,785,3193,3196],{},[95,3191,3192],{},"NET_ADMIN",[95,3194,3195],{},"\u002Fdev\u002Fnet\u002Ftun"," fehlt",[737,3198,3199,3204],{},[755,3200,3201],{},[95,3202,3203],{},"iptables-restore … unknown option '--save-mark'",[755,3205,3206,3207,3209,3210],{},"Nur Windows: ein WSL2-Kernel älter als 6.6. Führen Sie ",[95,3208,178],{}," aus. Siehe ",[120,3211,43],{"className":3212,"href":191},[123],[737,3214,3215,3220],{},[755,3216,3217],{},[95,3218,3219],{},"error gathering device information … \u002Fdev\u002Fnet\u002Ftun",[755,3221,3222],{},"Der Geräteknoten existiert auf dem Host nicht. Prüfen Sie unter Docker Desktop die Version Ihres WSL2-Kernels",[737,3224,3225,3228],{},[755,3226,3227],{},"Verkehr kommt an, aber Antworten hängen",[755,3229,3230],{},"Die sysctls für die Weiterleitung sind nicht gesetzt",[737,3232,3233,3236],{},[755,3234,3235],{},"Eine Zuordnung zum Host wird abgelehnt",[755,3237,3238,3239,3241,3242,3244],{},"Der Dienst auf dem Host ist an ",[95,3240,1257],{}," statt an ",[95,3243,1253],{}," gebunden, oder eine Host-Firewall verwirft Verkehr aus dem Bridge-Subnetz",[737,3246,3247,3251],{},[755,3248,3249],{},[95,3250,1524],{},[755,3252,3253,3254],{},"Die Verbindung ist abgebrochen. Der Agent kümmert sich bereits darum. Siehe ",[120,3255,456],{"className":3256,"href":455},[123],[737,3258,3259,3264],{},[755,3260,3261],{},[95,3262,3263],{},"tunnel health cannot be determined",[755,3265,3266],{},"Der Agent konnte den Status des Tunnels diesmal nicht lesen, was nicht dasselbe ist wie ein ausgefallener Tunnel. Er bekommt mehr Zeit, sich von selbst zu erholen, bevor der Container neu gestartet wird",[737,3268,3269,3273],{},[755,3270,3271],{},[95,3272,1528],{},[755,3274,3275],{},"Normale Wiederherstellung, kein Fehler. Der Container kommt mit einer frischen Verbindung zurück. Wiederholt sich das über längere Zeit, hat der Rechner entweder kein Internet, oder zwei Agenten teilen sich einen API-Schlüssel",[737,3277,3278,3284],{},[755,3279,3280,3281,3283],{},"Im Log sieht nichts falsch aus, aber eingehender Verkehr hängt, und ",[95,3282,1553],{}," ist aktiv",[755,3285,3286,3287,3290,3291,3294,3295],{},"Das Ziel schickt seine Antworten nicht über den Agenten zurück. Führen Sie ",[95,3288,3289],{},"docker exec \u003Ctarget> ip route"," aus: Die Standardroute muss auf den Agenten zeigen, und bei IPv6-Weiterleitung auch ",[95,3292,3293],{},"ip -6 route",". Siehe ",[120,3296,1286],{"className":3297,"href":1285},[123],[737,3299,3300,3305],{},[755,3301,3302],{},[95,3303,3304],{},"these destinations cannot work while preserving client IPs",[755,3306,3307],{},"Ein Ziel auf dem Host ist zugeordnet, während die Erhaltung der Client-IP aktiv ist, und das kann nicht funktionieren. Verlegen Sie diese Zuordnungen auf einen zweiten Agenten, bei dem die Einstellung aus bleibt",[737,3309,3310,3314],{},[755,3311,3312],{},[95,3313,967],{},[755,3315,3316,3317],{},"Eine Bereichszuordnung zeigt auf andere Ports am Ziel, oder auf einer Seite steht ein Bereich und auf der anderen ein einzelner Port. Lassen Sie den internen Port weg oder wiederholen Sie denselben Bereich. Siehe ",[120,3318,938],{"className":3319,"href":3320},[123],"#portbereiche",[737,3322,3323,3327],{},[755,3324,3325],{},[95,3326,1096],{},[755,3328,3329,3330,3332,3333,3294,3335],{},"Eine ",[95,3331,808],{},"-Zuordnung zeigt auf einen Dienst ohne IPv6-Adresse, meist ein Compose-Netzwerk ohne ",[95,3334,1001],{},[120,3336,982],{"className":3337,"href":3338},[123],"#ipv6-weiterleiten",[737,3340,3341,3346],{},[755,3342,3343,3344,3283],{},"Ein Container, den Sie über den Agenten geleitet haben, hat kein Internet, und ",[95,3345,2669],{},[755,3347,3348,3349,3351,3352,3294,3354],{},"Entweder ist der Tunnel unterbrochen (dieser Modus ist absichtlich ausfallsicher), oder die Standardroute des Containers zeigt nicht auf den Agenten. Führen Sie ",[95,3350,3289],{}," aus und bei IPv6 auch ",[95,3353,3293],{},[120,3355,2663],{"className":3356,"href":3357},[123],"#ausgehenden-datenverkehr-über-ihre-ip-adresse-senden",[737,3359,3360,3365],{},[755,3361,3362],{},[95,3363,3364],{},"GETPUBLICIP_MAPPINGS is required (or set GETPUBLICIP_OUTBOUND=true for egress with no inbound ports)",[755,3366,3367,3368,3371],{},"Sie haben den Agenten ohne Portzuordnungen gestartet. Das ist nur bei einem rein ausgehenden Setup erlaubt, das ",[95,3369,3370],{},"GETPUBLICIP_OUTBOUND=true"," braucht",[737,3373,3374,3379],{},[755,3375,3376],{},[95,3377,3378],{},"skipping API push: no mappings configured (egress-only)",[755,3380,3381],{},"Kein Fehler. Ein rein ausgehender Agent lässt die Portfreigaben Ihrer IP-Adresse unberührt, statt sie zu löschen",[737,3383,3384,3389],{},[755,3385,3386],{},[95,3387,3388],{},"preserveClientIp and masqueradeOutbound are mutually exclusive",[755,3390,3391,199,3393,3396,3397],{},[95,3392,1553],{},[95,3394,3395],{},"GETPUBLICIP_MASQUERADE"," waren beide aktiviert. Entfernen Sie ",[95,3398,3395],{},[737,3400,3401,3406],{},[755,3402,3403],{},[95,3404,3405],{},"is not a boolean (use true or false)",[755,3407,3408,3409,3411,3412,785,3414,3417,3418,199,3421,3424],{},"Eine Einstellung wie ",[95,3410,1553],{}," hat einen anderen Wert als ",[95,3413,1475],{},[95,3415,3416],{},"false"," erhalten. ",[95,3419,3420],{},"yes",[95,3422,3423],{},"on"," werden bewusst abgelehnt, damit ein Tippfehler die Einstellung nicht deaktiviert lässt, ohne dass Sie es merken",[91,3426,3427],{},"Um eine Konfiguration zu prüfen, ohne etwas zu starten oder die API zu kontaktieren, führen Sie\nsie im Dry-Run-Modus aus. Er gibt die Regeln aus, die angewendet würden, und beendet sich dann:",[223,3429,3431],{"className":225,"code":3430,"language":227,"meta":228,"style":228},"docker run --rm \\\n  -e GETPUBLICIP_API_KEY=x -e GETPUBLICIP_DRY_RUN=true \\\n  -e GETPUBLICIP_ISOLATED_INTERFACE=eth0 \\\n  -e GETPUBLICIP_MAPPINGS=\"8080\u002Ftcp->web:80\" \\\n  ghcr.io\u002Fgetpublicip\u002Fgetpublicip:latest\n",[95,3432,3433,3446,3464,3473,3482],{"__ignoreMap":228},[232,3434,3435,3437,3440,3443],{"class":234,"line":235},[232,3436,89],{"class":673},[232,3438,3439],{"class":246}," run",[232,3441,3442],{"class":396}," --rm",[232,3444,3445],{"class":396}," \\\n",[232,3447,3448,3451,3454,3457,3460,3462],{"class":234,"line":286},[232,3449,3450],{"class":396},"  -e",[232,3452,3453],{"class":246}," GETPUBLICIP_API_KEY=x",[232,3455,3456],{"class":396}," -e",[232,3458,3459],{"class":246}," GETPUBLICIP_DRY_RUN=",[232,3461,1475],{"class":396},[232,3463,3445],{"class":396},[232,3465,3466,3468,3471],{"class":234,"line":294},[232,3467,3450],{"class":396},[232,3469,3470],{"class":246}," GETPUBLICIP_ISOLATED_INTERFACE=eth0",[232,3472,3445],{"class":396},[232,3474,3475,3477,3480],{"class":234,"line":306},[232,3476,3450],{"class":396},[232,3478,3479],{"class":246}," GETPUBLICIP_MAPPINGS=\"8080\u002Ftcp->web:80\"",[232,3481,3445],{"class":396},[232,3483,3484],{"class":234,"line":317},[232,3485,3486],{"class":246},"  ghcr.io\u002Fgetpublicip\u002Fgetpublicip:latest\n",[103,3488,3490],{"id":3489},"häufig-gestellte-fragen","Häufig gestellte Fragen",[3492,3493,3496,3500],"details",{"className":3494},[3495],"faq-item",[3497,3498,3499],"summary",{},"Muss ich Ports an meinen Containern veröffentlichen, um GetPublicIP zu nutzen?",[91,3501,3502,3503,3505,3506,3508],{},"Nein. Der Datenverkehr kommt über den WireGuard-Tunnel an, nicht über einen veröffentlichten Host-Port. Die Dienste, die Sie erreichbar machen, brauchen daher keine ",[95,3504,97],{},"-Einträge und überhaupt keine Änderungen. Mit ",[95,3507,97],{}," wäre der Dienst auch in Ihrem LAN erreichbar, was meist nicht gewünscht ist.",[3492,3510,3512,3515],{"className":3511},[3495],[3497,3513,3514],{},"Muss der GetPublicIP-Container privilegiert laufen?",[91,3516,3517,3518,3520,3521,3523],{},"Nein. Der Container braucht die Capability ",[95,3519,3192],{},", das Gerät ",[95,3522,3195],{}," und die sysctls für die Weiterleitung, sonst nichts.",[3492,3525,3527,3530],{"className":3526},[3495],[3497,3528,3529],{},"Muss das WireGuard-Kernelmodul auf dem Host installiert sein?",[91,3531,3532,3533,3536],{},"Nein. Das Image nutzt das Kernelmodul des Hosts, wenn es vorhanden ist, und greift andernfalls auf das mitgelieferte Userspace-",[95,3534,3535],{},"wireguard-go"," zurück. Auf dem Host ist in keinem Fall etwas zu installieren, auf keiner Plattform.",[3492,3538,3540,3543],{"className":3539},[3495],[3497,3541,3542],{},"Funktioniert das unter macOS und Windows?",[91,3544,3545,3546,175,3548,3550],{},"Ja, und die Compose-Datei braucht auf keinem der beiden Systeme Änderungen. Der Host Ihres Containers ist eine Linux-VM und nicht das Desktop-Betriebssystem. Das Tunnelgerät stammt also aus dieser VM, und unter macOS oder Windows selbst ist nichts zu installieren. macOS funktioniert mit Docker Desktop unverändert auf Intel und Apple Silicon. Unter Windows muss Docker Desktop im Modus für Linux-Container laufen, und Ihr WSL2-Kernel muss Version 6.6.x haben. Prüfen Sie das mit ",[95,3547,174],{},[95,3549,178],{}," aus, falls eine ältere Version angezeigt wird, denn Kernels vor 6.6 fehlt ein Netfilter-Modul, das der Tunnel benötigt.",[3492,3552,3554,3557],{"className":3553},[3495],[3497,3555,3556],{},"Entschlüsselt GetPublicIP meinen HTTPS-Datenverkehr?",[91,3558,3559],{},"Nein. GetPublicIP leitet Pakete weiter und terminiert niemals TLS. Wir besitzen also keines Ihrer Zertifikate oder privaten Schlüssel und haben nichts, womit wir entschlüsseln könnten. Die TLS-Sitzung wird direkt zwischen dem Browser Ihres Besuchers und dem Ihrer Dienste ausgehandelt, der sie terminiert, und erst dort zum ersten Mal entschlüsselt. Dieser Dienst braucht ein eigenes gültiges Zertifikat, genau wie auf jedem anderen öffentlichen Host. Let's Encrypt ist kostenlos, automatisiert und dafür gut geeignet. Wenn Sie eine HTTP-01-Challenge verwenden, denken Sie daran, neben Port 443 auch Port 80 zuzuordnen.",[3492,3561,3563,3566],{"className":3562},[3495],[3497,3564,3565],{},"Kann ich einen Port an einen Dienst auf dem Docker-Host statt an einen Container weiterleiten?",[91,3567,3568,3569,3571,3572,3575,3576,3578,3579,3581,3582,3584],{},"Ja. Lassen Sie die Zuordnung auf ",[95,3570,1192],{}," zeigen und ergänzen Sie unter Linux ",[95,3573,3574],{},"extra_hosts: - \"host.docker.internal:host-gateway\"",". In Docker Desktop ist das bereits eingebaut. Eine feste IP-Adresse funktioniert ebenfalls. Der Dienst auf dem Host muss außerdem auf ",[95,3577,1253],{}," statt auf ",[95,3580,1257],{}," lauschen, und eine Host-Firewall muss eingehenden Verkehr aus dem Bridge-Subnetz erlauben. Ziele auf dem Host sind das Einzige, was sich nicht mit ",[95,3583,1553],{}," kombinieren lässt.",[3492,3586,3588,3591],{"className":3587},[3495],[3497,3589,3590],{},"Können meine Container die echte IP-Adresse des Besuchers sehen?",[91,3592,3593,3594,3597],{},"Ja, mit ",[95,3595,3596],{},"GETPUBLICIP_PRESERVE_CLIENT_IP=true",". Standardmäßig ist das aus, weil es Arbeit auf Ihrer Seite erfordert. Normalerweise schreibt der Agent die Quelladresse des eingehenden Verkehrs auf seine eigene um, damit die Antworten über ihn zurückkommen. Deshalb zeigen Ihre Access-Logs für jeden Besucher dieselbe Adresse. Schalten Sie das ab, muss jeder Dienst, an den Sie weiterleiten, seine Antworten stattdessen selbst über den Agenten zurückschicken, und dafür muss die Standardroute dieses Dienstes geändert werden. Die Einstellung gilt für Ihre gesamte Compose-Datei und nicht für eine einzelne Zuordnung, und die Weiterleitung an einen Dienst auf dem Docker-Host funktioniert nicht, solange sie aktiv ist. Richten Sie sie immer zusammen mit der Route ein, nie allein: Die Variable allein hinterlässt einen Dienst, der hängt, während die Logs weiterhin gesund aussehen.",[3492,3599,3601,3604],{"className":3600},[3495],[3497,3602,3603],{},"Kann ich X-Forwarded-For statt GETPUBLICIP_PRESERVE_CLIENT_IP verwenden?",[91,3605,3606,3607,3610],{},"Nicht allein. ",[95,3608,3609],{},"X-Forwarded-For"," hilft nur, wenn das, was den Header hinzufügt, die echte Client-Adresse überhaupt sehen kann. Die Quelladresse wird auf Paketebene umgeschrieben, bevor irgendetwas eine HTTP-Anfrage liest. Ein Reverse Proxy in Ihrer Compose-Datei erhält also Pakete, die bereits vorgeben, vom GetPublicIP-Container zu stammen, und hat nichts Wahres, was er in den Header schreiben könnte. Dort einen hinzuzufügen, hält die falsche Adresse nur an einer zweiten Stelle fest. In einem Fall funktioniert der Header jedoch, und Sie brauchen nichts davon: Wenn Ihr Datenverkehr ein CDN oder einen externen Proxy wie Cloudflare erreicht, bevor er bei Ihrer öffentlichen IP-Adresse ankommt, sieht dieser Dienst den echten Client und setzt den Header selbst. Ihre Container lesen ihn dann ganz normal aus.",[3492,3612,3614,3617],{"className":3613},[3495],[3497,3615,3616],{},"Können meine Container meine öffentliche IP-Adresse auch für ausgehenden Datenverkehr nutzen?",[91,3618,3593,3619,3621],{},[95,3620,3370],{},". Standardmäßig nutzt nur eingehender Verkehr den Tunnel, und Ihre Container erreichen das Internet weiterhin über Ihren normalen Anschluss. Wenn Sie diese Einstellung aktivieren, läuft auch ihr ausgehender Verkehr durch den Tunnel und verlässt ihn mit Ihrer GetPublicIP-Adresse. Dafür ist dieselbe Änderung nötig wie für die echte Client-IP (die Standardroute jedes Containers muss auf den GetPublicIP-Container zeigen). Haben Sie das bereits eingerichtet, müssen Sie nur noch die Einstellung hinzufügen. Alle Container dahinter teilen sich die eine Adresse. Außerdem ist das Verhalten bewusst ausfallsicher: Solange der Tunnel unterbrochen ist, haben diese Container gar kein Internet, statt auf die Adresse Ihres Internetanbieters auszuweichen.",[3492,3623,3625,3628],{"className":3624},[3495],[3497,3626,3627],{},"Was passiert, wenn meine Internetverbindung abbricht?",[91,3629,3630,3631,3633],{},"Der Tunnel baut sich von selbst wieder auf. Es gibt nichts neu zu starten und nichts zu konfigurieren. Die meisten Abbrüche behebt der Keepalive, der die Verbindung offen hält, ohne dass der Agent eingreifen muss; bei einem echten Tunnel haben wir gemessen, dass der Verkehr etwa 17 Sekunden nach der Wiederherstellung der Verbindung wieder floss. Bei den selteneren Fehlern, die ein Keepalive nicht beheben kann, stoppt der Agent den Container, statt den Tunnel an Ort und Stelle zu reparieren, und Ihre Restart-Policy startet ihn sofort mit einer frischen Verbindung neu. Deshalb setzt das Compose-Beispiel ",[95,3632,450],{},". Solange Ihr Internet ausgefallen ist, ist Ihr Dienst nicht erreichbar, und der Tunnel baut sich wieder auf, sobald eine Verbindung verfügbar ist.",[3492,3635,3637,3640],{"className":3636},[3495],[3497,3638,3639],{},"Was passiert, wenn einer meiner Container mit einer neuen IP-Adresse neu startet?",[91,3641,3642,3643,3646],{},"Der Agent löst alle Dienstnamen der Ziele in regelmäßigen Abständen neu auf (",[95,3644,3645],{},"GETPUBLICIP_RESOLVE_INTERVAL",", standardmäßig 30 Sekunden) und wendet die Weiterleitungsregeln erneut an, wenn ein Container umgezogen ist. Sie müssen nichts neu starten. Eine einzelne verlorene Anfrage direkt nach einer Neusynchronisierung ist normal, solange sich das Connection Tracking einpendelt.",[3492,3648,3650,3653],{"className":3649},[3495],[3497,3651,3652],{},"Kann ich denselben API-Schlüssel an zwei Orten gleichzeitig verwenden?",[91,3654,3655],{},"Nein. Ein WireGuard-Schlüssel gehört zu genau einem Endpunkt. Zwei Container mit demselben API-Schlüssel werfen sich daher gegenseitig aus der Verbindung. Es gewinnt jeweils der, dessen Handshake am jüngsten ist. Das äußert sich in zufälligen, sporadischen Ausfällen statt in einer klaren Fehlermeldung. Ein eindeutiges Signal gibt es aber: Beide Container starten immer wieder neu, weil jeder von ihnen zu dem Schluss kommt, er sei der defekte. Verwenden Sie einen API-Schlüssel pro laufendem Tunnel.",[3657,3658],"hr",{},[91,3660,3661,3665,3666,187,3670,192],{},[120,3662,60],{"className":3663,"href":3664},[123],"\u002Fde\u002Fdocs\u002Fgetting-started"," erklärt, wie der Dienst\nfunktioniert. Wenn Sie Ihre Dienste direkt auf einem Host statt in Containern betreiben, lesen\nSie die Anleitungen für ",[120,3667,35],{"className":3668,"href":3669},[123],"\u002Fde\u002Fdocs\u002Flinux",[120,3671,43],{"className":3672,"href":3673},[123],"\u002Fde\u002Fdocs\u002Fwindows",[3675,3676,3677],"style",{},"html pre.shiki code .sCdxs, html code.shiki .sCdxs{--shiki-default:#F8F8F2}html pre.shiki code .s8I7P, html code.shiki .s8I7P{--shiki-default:#F92672}html pre.shiki code .s_Ekj, html code.shiki .s_Ekj{--shiki-default:#E6DB74}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html pre.shiki code .s7s5_, html code.shiki .s7s5_{--shiki-default:#AE81FF}html pre.shiki code .sHkqI, html code.shiki .sHkqI{--shiki-default:#A6E22E}html pre.shiki code .snpHw, html code.shiki .snpHw{--shiki-default:#88846F}",{"title":228,"searchDepth":286,"depth":286,"links":3679},[3680,3681,3682,3685,3689,3694,3695,3696,3697,3698,3699,3705,3709,3710,3711,3712,3713,3714,3715],{"id":105,"depth":286,"text":106},{"id":210,"depth":286,"text":211},{"id":264,"depth":286,"text":265,"children":3683},[3684],{"id":461,"depth":294,"text":462},{"id":710,"depth":286,"text":711,"children":3686},[3687,3688],{"id":937,"depth":294,"text":938},{"id":981,"depth":294,"text":982},{"id":1106,"depth":286,"text":1107,"children":3690},[3691,3692,3693],{"id":1127,"depth":294,"text":1128},{"id":1137,"depth":294,"text":1138},{"id":1178,"depth":294,"text":1179},{"id":1185,"depth":286,"text":1186},{"id":1290,"depth":286,"text":1291},{"id":1414,"depth":286,"text":1415},{"id":1479,"depth":286,"text":1480},{"id":1512,"depth":286,"text":456},{"id":1541,"depth":286,"text":1286,"children":3700},[3701,3702,3703,3704],{"id":1576,"depth":294,"text":1577},{"id":1610,"depth":294,"text":1611},{"id":2542,"depth":294,"text":2543},{"id":2604,"depth":294,"text":2605},{"id":2662,"depth":286,"text":2663,"children":3706},[3707,3708],{"id":2851,"depth":294,"text":2852},{"id":2891,"depth":294,"text":2892},{"id":2949,"depth":286,"text":2950},{"id":3020,"depth":286,"text":39},{"id":3033,"depth":286,"text":43},{"id":3101,"depth":286,"text":3102},{"id":3111,"depth":286,"text":3112},{"id":3127,"depth":286,"text":3128},{"id":3489,"depth":286,"text":3490},"2026-08-09","Machen Sie Ihre Docker-Compose-Dienste über eine eigene öffentliche IP-Adresse erreichbar. Ein Container mehr genügt, Ihre Dienste bleiben unverändert.","md",[3720,3722,3724,3726,3728,3729,3731,3733,3735,3737,3739,3741],{"question":3499,"answer":3721},"Nein. Der Datenverkehr kommt über den WireGuard-Tunnel an, nicht über einen veröffentlichten Host-Port. Die Dienste, die Sie erreichbar machen, brauchen daher keine `ports:`-Einträge und überhaupt keine Änderungen. Mit `ports:` wäre der Dienst auch in Ihrem LAN erreichbar, was meist nicht gewünscht ist.",{"question":3514,"answer":3723},"Nein. Der Container braucht die Capability `NET_ADMIN`, das Gerät `\u002Fdev\u002Fnet\u002Ftun` und die sysctls für die Weiterleitung, sonst nichts.",{"question":3529,"answer":3725},"Nein. Das Image nutzt das Kernelmodul des Hosts, wenn es vorhanden ist, und greift andernfalls auf das mitgelieferte Userspace-`wireguard-go` zurück. Auf dem Host ist in keinem Fall etwas zu installieren, auf keiner Plattform.",{"question":3542,"answer":3727},"Ja, und die Compose-Datei braucht auf keinem der beiden Systeme Änderungen. Der Host Ihres Containers ist eine Linux-VM und nicht das Desktop-Betriebssystem. Das Tunnelgerät stammt also aus dieser VM, und unter macOS oder Windows selbst ist nichts zu installieren. macOS funktioniert mit Docker Desktop unverändert auf Intel und Apple Silicon. Unter Windows muss Docker Desktop im Modus für Linux-Container laufen, und Ihr WSL2-Kernel muss Version 6.6.x haben. Prüfen Sie das mit `wsl --version` und führen Sie `wsl --update` aus, falls eine ältere Version angezeigt wird, denn Kernels vor 6.6 fehlt ein Netfilter-Modul, das der Tunnel benötigt.",{"question":3556,"answer":3559},{"question":3565,"answer":3730},"Ja. Lassen Sie die Zuordnung auf `host.docker.internal` zeigen und ergänzen Sie unter Linux `extra_hosts: - \"host.docker.internal:host-gateway\"`. In Docker Desktop ist das bereits eingebaut. Eine feste IP-Adresse funktioniert ebenfalls. Der Dienst auf dem Host muss außerdem auf `0.0.0.0` statt auf `127.0.0.1` lauschen, und eine Host-Firewall muss eingehenden Verkehr aus dem Bridge-Subnetz erlauben. Ziele auf dem Host sind das Einzige, was sich nicht mit `GETPUBLICIP_PRESERVE_CLIENT_IP` kombinieren lässt.",{"question":3590,"answer":3732},"Ja, mit `GETPUBLICIP_PRESERVE_CLIENT_IP=true`. Standardmäßig ist das aus, weil es Arbeit auf Ihrer Seite erfordert. Normalerweise schreibt der Agent die Quelladresse des eingehenden Verkehrs auf seine eigene um, damit die Antworten über ihn zurückkommen. Deshalb zeigen Ihre Access-Logs für jeden Besucher dieselbe Adresse. Schalten Sie das ab, muss jeder Dienst, an den Sie weiterleiten, seine Antworten stattdessen selbst über den Agenten zurückschicken, und dafür muss die Standardroute dieses Dienstes geändert werden. Die Einstellung gilt für Ihre gesamte Compose-Datei und nicht für eine einzelne Zuordnung, und die Weiterleitung an einen Dienst auf dem Docker-Host funktioniert nicht, solange sie aktiv ist. Richten Sie sie immer zusammen mit der Route ein, nie allein: Die Variable allein hinterlässt einen Dienst, der hängt, während die Logs weiterhin gesund aussehen.",{"question":3603,"answer":3734},"Nicht allein. `X-Forwarded-For` hilft nur, wenn das, was den Header hinzufügt, die echte Client-Adresse überhaupt sehen kann. Die Quelladresse wird auf Paketebene umgeschrieben, bevor irgendetwas eine HTTP-Anfrage liest. Ein Reverse Proxy in Ihrer Compose-Datei erhält also Pakete, die bereits vorgeben, vom GetPublicIP-Container zu stammen, und hat nichts Wahres, was er in den Header schreiben könnte. Dort einen hinzuzufügen, hält die falsche Adresse nur an einer zweiten Stelle fest. In einem Fall funktioniert der Header jedoch, und Sie brauchen nichts davon: Wenn Ihr Datenverkehr ein CDN oder einen externen Proxy wie Cloudflare erreicht, bevor er bei Ihrer öffentlichen IP-Adresse ankommt, sieht dieser Dienst den echten Client und setzt den Header selbst. Ihre Container lesen ihn dann ganz normal aus.",{"question":3616,"answer":3736},"Ja, mit `GETPUBLICIP_OUTBOUND=true`. Standardmäßig nutzt nur eingehender Verkehr den Tunnel, und Ihre Container erreichen das Internet weiterhin über Ihren normalen Anschluss. Wenn Sie diese Einstellung aktivieren, läuft auch ihr ausgehender Verkehr durch den Tunnel und verlässt ihn mit Ihrer GetPublicIP-Adresse. Dafür ist dieselbe Änderung nötig wie für die echte Client-IP (die Standardroute jedes Containers muss auf den GetPublicIP-Container zeigen). Haben Sie das bereits eingerichtet, müssen Sie nur noch die Einstellung hinzufügen. Alle Container dahinter teilen sich die eine Adresse. Außerdem ist das Verhalten bewusst ausfallsicher: Solange der Tunnel unterbrochen ist, haben diese Container gar kein Internet, statt auf die Adresse Ihres Internetanbieters auszuweichen.",{"question":3627,"answer":3738},"Der Tunnel baut sich von selbst wieder auf. Es gibt nichts neu zu starten und nichts zu konfigurieren. Die meisten Abbrüche behebt der Keepalive, der die Verbindung offen hält, ohne dass der Agent eingreifen muss; bei einem echten Tunnel haben wir gemessen, dass der Verkehr etwa 17 Sekunden nach der Wiederherstellung der Verbindung wieder floss. Bei den selteneren Fehlern, die ein Keepalive nicht beheben kann, stoppt der Agent den Container, statt den Tunnel an Ort und Stelle zu reparieren, und Ihre Restart-Policy startet ihn sofort mit einer frischen Verbindung neu. Deshalb setzt das Compose-Beispiel `restart: unless-stopped`. Solange Ihr Internet ausgefallen ist, ist Ihr Dienst nicht erreichbar, und der Tunnel baut sich wieder auf, sobald eine Verbindung verfügbar ist.",{"question":3639,"answer":3740},"Der Agent löst alle Dienstnamen der Ziele in regelmäßigen Abständen neu auf (`GETPUBLICIP_RESOLVE_INTERVAL`, standardmäßig 30 Sekunden) und wendet die Weiterleitungsregeln erneut an, wenn ein Container umgezogen ist. Sie müssen nichts neu starten. Eine einzelne verlorene Anfrage direkt nach einer Neusynchronisierung ist normal, solange sich das Connection Tracking einpendelt.",{"question":3652,"answer":3655},{},{"title":47,"icon":48,"description":3744},"Machen Sie Ihre Docker-Compose-Dienste über einen GetPublicIP-Tunnel aus dem Internet erreichbar.",{"title":82,"description":3717},"2026-10-31","HVRN6c1jiUIN_U0ofG-5gZHZ-MOYt10sCMmXru25_wM",1793914055125]