Dev Container VPN-only होस्ट तक नहीं पहुँचता: कहाँ देखें
ब्राउज़र और कंटेनर के resolver, proxy और रूट संदर्भ अलग-अलग हैं। कोई VPN सेटिंग बदलने से पहले पता लगाएँ कि विफल प्रक्रिया किसका उपयोग कर रही है।
निजी API आपके डेस्कटॉप ब्राउज़र में खुलता है और डेवलपमेंट कंटेनर में विफल हो जाता है। यह कोई विरोधाभास नहीं है, और शायद ही कभी VPN स्वयं कारण होता है। ब्राउज़र का अनुरोध और विफल अनुरोध अलग-अलग प्रक्रियाओं ने बनाए थे, अलग resolver, proxy और रूट के साथ, और अक्सर पूरी तरह अलग नेटवर्क नामस्थानों से। “मेरे लैपटॉप पर” का अर्थ Windows होस्ट, कोई WSL वितरण, Docker Desktop वर्चुअल मशीन और उस VM के अंदर का कंटेनर हो सकता है — चार संदर्भ, जिनमें से हर एक एक ही होस्टनाम का अलग उत्तर दे सकता है। एक भी सेटिंग छूने से पहले पता लगाएँ कि विफल प्रक्रिया किसका उपयोग कर रही है।
सेटिंग बदलने से पहले प्रक्रिया खोजें
VPN क्लाइंट से नहीं, कंटेनर इंजन से शुरू करें। पूछें कि कमांड लाइन किस संदर्भ से बात कर रही है और वह इंजन किस ऑपरेटिंग सिस्टम पर चलता है, क्योंकि डेस्कटॉप VM द्वारा प्रबंधित Linux कंटेनर स्थानीय डेमॉन द्वारा प्रबंधित कंटेनर से अलग रास्ता लेता है:
docker context ls
docker info --format '{{.OperatingSystem}} / {{.Name}}'
docker run --rm alpine ip route
Windows पर, wsl -l -v बताता है कि वितरण WSL 2 के अंतर्गत चल रहा है या नहीं, जो उसे उसके अपने वर्चुअल स्विच के पीछे रखता है। यही विवरण तय करता है कि कंटेनर होस्ट की रूटिंग तालिका साझा करता है या ऐसे NAT के पीछे बैठता है जिसे होस्ट तक पहुँचने के लिए फ़ॉरवर्ड किया गया पोर्ट या होस्टनाम चाहिए।
एक अनुरोध स्थिर रखें और तुलना करें
निजी होस्ट पर एक हानिरहित एंडपॉइंट चुनें और हर तुलना के लिए उसका उपयोग करें: ब्राउज़र से, होस्ट टर्मिनल से, WSL वितरण से और कंटेनर के अंदर से। हर प्रयास के लिए चार बातें लिखें: हल किया गया पता, क्या proxy उपयोग हुआ, विफलता का वर्ग और बीता समय। नाम खोज, कनेक्शन स्थापित करना, TLS सत्यापन और HTTP स्थिति चार अलग समस्याएँ हैं, और उन्हें “काम नहीं करता” में मिला देना एक सुबह बर्बाद कर देता है।
तुलना उसी कंटेनर के अंदर चलाएँ जो विफल हो रहा है, टाइमआउट के साथ, ताकि कोई खामोश फ़ायरवॉल टर्मिनल को मिनटों तक न रोके। नया कंटेनर इंजन का नेटवर्क संदर्भ दोहराता है, लेकिन एप्लिकेशन कंटेनर का नामस्थान, proxy चर या resolver नहीं, इसलिए असली कंटेनर में docker exec ही आधिकारिक परीक्षण है, और साइडकार केवल यह अलग करने का तरीका है कि अंतर इंजन में है या कंटेनर में:
docker exec -it app /bin/sh -c "getent hosts api.internal; curl -v --max-time 8 https://api.internal/ 2>&1 | tail -20"
docker run --rm --network container:app curlimages/curl:latest -sv --max-time 8 https://api.internal/ 2>&1 | tail -20
alpine बेस इमेज में busybox है और curl नहीं, और यही वह बारीकी है जो कॉपी किए गए डायग्नोस्टिक ब्लॉक को विफल कर देती है: क्लाइंट वाली इमेज चुनें, या उसे उसी रन में जोड़ें। असंबंधित सार्वजनिक साइटों से तुलना कुछ भी अलग नहीं करती। यदि कंटेनर से https://example.com काम करता है, तो आपने केवल यह सीखा कि कंटेनर के पास इंटरनेट पहुँच है, और यह नहीं कि वह टनल से निजी पते तक पहुँचता है या नहीं। इसी तरह, नया टर्मिनल खोलना केवल यह सिद्ध करता है कि नया टर्मिनल काम करता है, यह नहीं कि वह विफल एप्लिकेशन के साथ एक ही रनटाइम साझा करता है।
Docker Desktop VPN के साथ काम कर सकता है
Docker का अपना दस्तावेज़ VPN और होस्ट कनेक्टिविटी पर इसे समर्थित सेटअप बताता है, और ईमानदार सार यह है कि यह काम करता है, अपने आप टूटा नहीं है। यह न मानें कि डेस्कटॉप VM डिज़ाइन से ही होस्ट की टनल को बायपास करता है; कई सेटअप में ट्रैफ़िक होस्ट की टनल का सही ढंग से अनुसरण करता है, और इसीलिए “Docker VPN को अनदेखा करता है” वाली किंवदंती आत्मविश्वासी और ग़लत सलाह देती है।
जो अभी भी मायने रखता है वह है उपयोग किया गया backend, क्लाइंट की split-tunnel नीति और VM को मिली resolver कॉन्फ़िगरेशन। ऐसा VPN क्लाइंट जो रूट इंस्टॉल करता है पर DNS नहीं, या ऐसा DNS सर्वर धकेलता है जिस तक VM नहीं पहुँच सकता, कंटेनर के अंदर नाम खोज विफलता उत्पन्न करता है जबकि होस्ट काम करता है क्योंकि उसके पास अतिरिक्त resolver या कैश किया हुआ उत्तर है। यह कंटेनर की पोशाक में resolver की समस्या है। यह आपके हर VPN पुनःकनेक्शन में बनी रहती है, क्योंकि टनल पहले से ही वह ट्रैफ़िक ले जा रही है जो आपने उसे ले जाने को कहा था।
पता अतिव्यापन और MTU अलग विफलताएँ हैं
दो विफलताएँ अपना अलग निदान माँगती हैं क्योंकि उन्हें अक्सर पहुँच नीति समझ लिया जाता है। पहला है पता अतिव्यापन: यदि VPN ऐसी श्रेणी धकेलता है जो कंटेनर नेटवर्क के डिफ़ॉल्ट ब्रिज सबनेट से टकराती है, तो उस श्रेणी के लिए कंटेनर का रूट स्थानीय ब्रिज की ओर इशारा करता है और कभी टनल तक नहीं पहुँचता। अनुमान लगाने के बजाय वास्तविक सबनेट देखें:
docker network inspect bridge --format '{{range .IPAM.Config}}{{.Subnet}}{{end}}'
ip route get 10.20.30.40
दूसरा MTU समस्या है। यदि कनेक्शन बनता है और TLS पूरा होता है पर बड़े उत्तर अटक जाते हैं, तो आपके पास पैकेट-आकार की समस्या है, अनुमति की नहीं, और DNS रिकॉर्ड बदलने से यह कभी ठीक नहीं होगा। कुछ भी बदलने से पहले छोटे और बड़े अनुरोध से परीक्षण करें, और दोनों परिणाम लिख लें।
अतिव्यापन का समाधान दूसरा कंटेनर सबनेट या सीमित रूट है, जिसे पता योजना का स्वामी चुनता है। MTU अटकाव का समाधान टनल या इंटरफ़ेस के MTU को ऐसे मान तक घटाना है जो मार्ग में टिके, और इसे उस परत पर लागू करना है जिसे आप नियंत्रित करते हैं।
Proxy कॉन्फ़िगरेशन प्रति प्रक्रिया है, प्रति मशीन नहीं
कंटेनर के अंदर, localhost उसी कंटेनर के अपने नेटवर्क संदर्भ को नाम देता है, इसलिए होस्ट पर चलने वाला proxy वहाँ उस नाम से पहुँच योग्य नहीं है। Docker Desktop होस्ट पहुँच के लिए host.docker.internal देता है, और Linux पर आप उसे --add-host=host.docker.internal:host-gateway से स्पष्ट रूप से जोड़ते हैं। किसी भी तरह, वह नाम आपको होस्ट तक रूट देता है; वह proxy सेवा नहीं बनाता और उसके उपयोग का अधिकार भी नहीं देता।
वास्तविक परिवेश के लिए दिए गए proxy पते और पोर्ट का उपयोग करें, और देखें कि उन्हें कौन पढ़ रहा है। इंटरैक्टिव शेल में निर्यात किए गए चर अपने आप हर एडिटर एक्सटेंशन, भाषा सर्वर, बिल्ड टूल और पृष्ठभूमि डेमॉन को कॉन्फ़िगर नहीं करते। मायने वह प्रक्रिया रखती है जिसने विफल अनुरोध किया, इसलिए उसका परिवेश देखें, अपने टर्मिनल का नहीं।
अंत में, सुधार को स्वयं समझाने दें। उपयोगी समाधान उस सीमा का नाम लेता है जो ग़लत थी, उस सेटिंग का जिसने उसे बदला, और उन प्रक्रियाओं के समूह का जिन पर अब वह प्रभाव डालता है। VPN, एडिटर और इंजन को क्रम से पुनः आरंभ करना लक्षण बदल सकता है, पर वह अगले व्यक्ति के काम आने वाला कुछ नहीं छोड़ता।