डॉकर कमांड में --net = होस्ट विकल्प वास्तव में क्या करता है?


97

मैं डोकर के लिए थोड़ा शुरुआती हूं। मुझे इस बात का कोई स्पष्ट विवरण नहीं मिल पाया है कि यह विकल्प docker run कमांड में क्या करता है और इसके बारे में थोड़ा उलझन में है।

क्या हम पोर्ट निर्दिष्ट किए बिना डॉकटर कंटेनरों पर चल रहे एप्लिकेशन तक पहुंचने के लिए इसका उपयोग कर सकते हैं? एक उदाहरण के रूप में अगर मैं -p 8080:8080डॉक रन कमांड में विकल्प का उपयोग करके पोर्ट 8080 में एक डॉक इमेज के माध्यम से तैनात एक वेबप रन करता हूं, तो मुझे पता है कि मुझे इसे डॉकर कंटेनर आईपी / -वेबएपनाम पर 8080 पोर्ट पर एक्सेस करना होगा। लेकिन मैं वास्तव में इस तरह से नहीं सोच सकता कि --net=hostविकल्प कैसे काम करता है।

जवाबों:


131

डॉक इंस्टॉलेशन के बाद आपके पास डिफ़ॉल्ट रूप से 3 नेटवर्क हैं:

docker network ls
NETWORK ID          NAME                DRIVER              SCOPE
f3be8b1ef7ce        bridge              bridge              local
fbff927877c1        host                host                local
023bb5940080        none                null                local

मैं इसे सरल रखने की कोशिश कर रहा हूं। इसलिए यदि आप डिफॉल्ट रूप से एक कंटेनर शुरू करते हैं तो यह ब्रिज (docker0) नेटवर्क के अंदर बनाया जाएगा।

$ docker run -d jenkins
1498e581cdba        jenkins             "/bin/tini -- /usr..."   3 minutes ago       Up 3 minutes        8080/tcp, 50000/tcp   friendly_bell

जेंकिन्स के डॉकफाइल में बंदरगाह 8080और 50000उजागर होते हैं। उन बंदरगाहों को उसके पुल नेटवर्क पर कंटेनर के लिए खोला जाता है। उस पुल नेटवर्क के अंदर सब कुछ तो बंदरगाह पर कंटेनर का उपयोग कर सकते 8080हैं और 50000। ब्रिज नेटवर्क में सब कुछ निजी श्रेणी में है "Subnet": "172.17.0.0/16",यदि आप उन्हें बाहर से एक्सेस करना चाहते हैं तो आपको पोर्ट के साथ मैप करना होगा -p 8080:8080। यह आपके कंटेनर के पोर्ट को आपके वास्तविक सर्वर (होस्ट नेटवर्क) के पोर्ट पर मैप करेगा। इसलिए आपके सर्वर तक पहुँच 8080पोर्ट पर आपके ब्रिजनेट नेटवर्क के लिए होगी 8080

अब आपके पास अपना होस्ट नेटवर्क भी है। जो कंटेनरों को नेटवर्किंग नहीं करता है। इसलिए यदि आप मेजबान नेटवर्क में एक कंटेनर शुरू करते हैं तो यह इस तरह दिखेगा (यह पहला है):

CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                 NAMES
1efd834949b2        jenkins             "/bin/tini -- /usr..."   6 minutes ago       Up 6 minutes                              eloquent_panini
1498e581cdba        jenkins             "/bin/tini -- /usr..."   10 minutes ago      Up 10 minutes       8080/tcp, 50000/tcp   friendly_bell

अंतर बंदरगाहों के साथ है। आपका कंटेनर अब आपके होस्ट नेटवर्क के अंदर है। इसलिए यदि आप 8080अपने मेजबान पर पोर्ट खोलते हैं तो आप कंटेनर को तुरंत हटा देंगे।

$ sudo iptables -I INPUT 5 -p tcp -m tcp --dport 8080 -j ACCEPT

मैंने 8080अपने फ़ायरवॉल में पोर्ट खोला है और जब मैं पोर्ट पर अपने सर्वर पर आरोप लगा 8080रहा हूँ तो मैं अपने जेनकींस तक पहुँच रहा हूँ। मुझे लगता है कि यह ब्लॉग इसे बेहतर समझने के लिए भी उपयोगी है।


4
क्या --net=hostडॉकरफाइल के अंदर विकल्प जोड़ना संभव है ?
AnirbanDebnath

6
@AnirbanDebnath मुझे नहीं लगता कि इसे डॉकटराइल में रखना संभव है लेकिन docker v17 के बाद से आप इसे अपने docker build के लिए एक पैरामीटर के रूप में उपयोग कर सकते हैं docker build --network=host:। डॉक बिल्ड के लिए निर्दिष्ट होस्ट नेटवर्क केवल उन पैकेजों को डाउनलोड करने के लिए है जो छवि बनाने के लिए आवश्यक हैं। जब आप अपने कंटेनर को होस्ट नेटवर्क पर चलाना चाहते हैं, तब भी आपको --network = होस्ट विकल्प को परिभाषित करना होगा।
lvthillo

हां @AirirbanDebnath, Dockerfile में इसकी अनुमति है। उदाहरण के लिए v3 - network_mode: "host"(रेफ - docs.docker.com/compose/compose-file/#network_mode )
मोहनीश

1
यह एक डॉकटर-कम्पोज फाइल है, जिसमें कंटेनर को चलाने का तरीका बताया गया है। डॉकरफाइल नहीं है। लेकिन वास्तव में, वहाँ यह संभव है और docker चलाने के रूप में एक ही काम करता है
nnetwork

32

--net=hostविकल्प नेटवर्क के नजरिए से, डोकर कंटेनर नज़र अंदर कार्यक्रम बनाने के लिए की तरह वे मेजबान पर ही चल रहे हैं प्रयोग किया जाता है। यह कंटेनर को सामान्य रूप से प्राप्त करने की तुलना में अधिक नेटवर्क एक्सेस की अनुमति देता है।

आम तौर पर आपको होस्ट मशीन से कंटेनर में बंदरगाहों को अग्रेषित करना होता है, लेकिन जब कंटेनर मेजबान के नेटवर्क को साझा करते हैं, तो कोई भी नेटवर्क गतिविधि सीधे मेजबान मशीन पर होती है - ठीक वैसे ही जैसे कि प्रोग्राम स्थानीय स्तर पर मेजबान के अंदर चलने के बजाय चल रहा होता है कंटेनर।

हालांकि इसका मतलब यह है कि आपको अब बंदरगाहों को उजागर नहीं करना है और उन्हें कंटेनर बंदरगाहों में मैप करना है, इसका मतलब है कि आपको अपने डॉकफर्फ़ाइल्स को उन बंदरगाहों को समायोजित करने के लिए संपादित करना होगा जिन पर प्रत्येक कंटेनर सुनता है, संघर्षों से बचने के लिए क्योंकि आपके पास दो कंटेनर नहीं हैं। होस्ट पोर्ट। हालांकि, इस विकल्प का असली कारण उन एप्लिकेशन को चलाने के लिए है जिन्हें नेटवर्क एक्सेस की आवश्यकता होती है जो पोर्ट स्तर पर एक कंटेनर के माध्यम से अग्रेषित करना मुश्किल है।

उदाहरण के लिए, यदि आप डीएचसीपी सर्वर चलाना चाहते हैं तो आपको नेटवर्क पर प्रसारण ट्रैफ़िक सुनने और पैकेट से मैक एड्रेस निकालने में सक्षम होना चाहिए। यह जानकारी पोर्ट फ़ॉरवर्डिंग प्रक्रिया के दौरान खो जाती है, इसलिए डॉकर के अंदर डीएचसीपी सर्वर को चलाने का एकमात्र तरीका कंटेनर को चलाना है --net=host

आम तौर पर बोलना, --net=hostकेवल तभी आवश्यक होता है जब आप बहुत विशिष्ट, असामान्य नेटवर्क की जरूरत वाले कार्यक्रम चला रहे हों।

अंत में, सुरक्षा के नजरिए से, डॉकर कंटेनर कई पोर्ट पर सुन सकते हैं, भले ही वे केवल एक ही पोर्ट का विज्ञापन (एक्सपोज) करते हों। आम तौर पर यह ठीक है क्योंकि आप केवल एकल अपेक्षित पोर्ट को आगे बढ़ाते हैं, हालांकि यदि आप उपयोग करते हैं --net=hostतो आपको होस्ट पर सुनने वाले सभी कंटेनर के पोर्ट मिल जाएंगे , यहां तक ​​कि जो डॉकरफाइल में सूचीबद्ध नहीं हैं। इसका मतलब है कि आपको कंटेनर को बारीकी से जांचने की आवश्यकता होगी (विशेषकर यदि यह आपका नहीं है, उदाहरण के लिए एक सॉफ्टवेयर परियोजना द्वारा प्रदान किया गया एक अधिकारी) यह सुनिश्चित करने के लिए कि आप मशीन पर अनजाने में अतिरिक्त सेवाओं को उजागर नहीं करते हैं।


यदि कई कंटेनरों को '--नेट = होस्ट' विकल्पों के साथ शुरू किया जाए तो व्यवहार कैसा होगा? अनुरोधों को एक यादृच्छिक कंटेनर में भेजा जाएगा?
user482594

@ user482594: वे सभी एक ही नेटवर्क स्टैक साझा करेंगे, जैसे आप एक ही कंटेनर के अंदर सभी प्रोग्राम चलाते हैं। उदाहरण के लिए, यदि आप दो वेबसर्वर चलाते हैं, तो आपको यह सुनिश्चित करने की आवश्यकता होगी कि वे विभिन्न बंदरगाहों पर सुन रहे हैं अन्यथा दूसरे कंटेनर को एक त्रुटि मिलेगी कि पोर्ट पहले उपयोग में है। आने वाले ट्रैफ़िक को आगे भेजा जाएगा जो भी कंटेनर के लिए सुन रहा है (तकनीकी रूप से सभी --net=hostकंटेनर ट्रैफ़िक देखेंगे, लेकिन निश्चित रूप से एक समय में केवल एक प्रोग्राम किसी दिए गए पोर्ट पर सुन सकता है कोई फर्क नहीं पड़ता कि आप इसे किस कंटेनर में चलाते हैं, इस सेट अप में )।
मालवीयस

1
  1. आप अपना नया नेटवर्क बना सकते हैं जैसे --net = "anyname"
  2. यह अलग-अलग कंटेनर से सेवाओं को अलग करने के लिए किया जाता है।
  3. मान लें कि एक ही सेवा अलग-अलग कंटेनरों में चल रही है, लेकिन पोर्ट मैपिंग एक ही रहती है, पहला कंटेनर अच्छी तरह से शुरू होता है, लेकिन दूसरे कंटेनर से एक ही सेवा विफल हो जाएगी। तो इससे बचने के लिए, या तो पोर्ट मैपिंग बदलें या एक नेटवर्क बनाएं।

1
उल्लेख के लिए धन्यवाद "2. यह अलग-अलग कंटेनर से नेटवर्क (नेटवर्क) सेवाओं को अलग करने के लिए किया जाता है"। hostअगर वास्तव में एक ही मेजबान पर कई कंटेनरों को चलाने की संभावना है, तो मैं अन्य docker नेटवर्क कॉन्फिगर (अन्य ) का उपयोग करने का मूल्य देखता हूं । अन्य मामलों में (जहां नेटवर्क अलगाव की आवश्यकता नहीं है), मैं पसंद करूंगा --net=host
C --Z
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.