मैं मौजूदा डॉकटर कंटेनर में पोर्ट मैपिंग कैसे निर्दिष्ट कर सकता हूं?


436

मुझे यकीन नहीं है कि अगर मैंने यहां कुछ गलत समझा है, लेकिन ऐसा लगता है कि एक छवि से एक नया कंटेनर बनाकर केवल पोर्ट मैपिंग सेट करना संभव है। क्या मौजूदा डॉकर कंटेनर में पोर्ट मैपिंग असाइन करने का कोई तरीका है?



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

2
पुराना प्रश्न और मैं इसका उत्तर नहीं दे रहा हूं, लेकिन मैं यह कहना चाहूंगा कि हो सकता है कि आप और लोग इस प्रश्न और उत्तर को स्वीकार कर रहे हों और कर्ता की अवधारणा को पूरी तरह गलत समझा हो। डॉकर स्टेटलेस एप्लिकेशन के लिए है, जो कई बार ऊपर या नीचे स्केल कर सकता है। आपको किसी उत्पादन संवर्धन के लिए कंटेनर के अंदर कभी भी कुछ नहीं रखना चाहिए जिसे फिर से बनाया नहीं जा सकता है, यदि आपको निर्देशिकाओं को जारी रखने की आवश्यकता है, तो निर्देशिकाओं को मैप करें। डॉकर एक "लाइट वीएम" जैसा कुछ नहीं है, हो सकता है कि आप जो खोज रहे हों वह linuxcontainers.org हो, lxd docker अवधारणा पर आधारित हो लेकिन "लाइट vm" को ध्यान में रखकर।
एडगर कारवाल्हो

बस इस मामले में मदद मिल सकती है, पहले से ही चल रहे कंटेनरों में पोर्ट मैपिंग को जोड़ने के लिए "किटेमैटिक" टूल का उपयोग करना संभव है। इसका मतलब यह होना चाहिए कि एक ही काम करने के लिए डॉकटर कमांड होना चाहिए, लेकिन थोड़ा
गुगली के

जवाबों:


298

आप hostconfig.jsonफ़ाइल को सीधे संपादित करके पोर्ट मैपिंग को बदल सकते हैं/var/lib/docker/containers/[hash_of_the_container]/hostconfig.json

आप docker inspect <container_name>कमांड के माध्यम से [hash_of_the_container] निर्धारित कर सकते हैं और "Id" फ़ील्ड का मान हैश है।

1) stop the container 
2) stop docker service (per Tacsiazuma's comment)
3) change the file
4) restart your docker engine (to flush/clear config caches)
5) start the container

इसलिए आपको इस दृष्टिकोण के साथ एक छवि बनाने की आवश्यकता नहीं है। आप यहां रिस्टार्ट फ़्लैग को भी बदल सकते हैं।

PS आप अपने होस्ट मशीन के अनुसार अपने डॉक इंजन को सही ढंग से पुनः आरंभ करने का तरीका जानने के लिए https://docs.docker.com/engine/admin/ पर जा सकते हैं । मैं sudo systemctl restart dockerअपने docker इंजन को पुनरारंभ करता था जो Ubuntu 16.04 पर चल रहा था


17
जब डॉकटर बंद हो जाता है, तो यह आपके परिवर्तनों को अधिलेखित करने लगता है, इसलिए 2. स्टॉप डॉक, 3. चेंज फ़ाइल, 4.
डॉक

5
मैंने ऊपर की कोशिश की है और यह काम करता है। अधिक जानकारी के लिए देखें: mybrainimage.wordpress.com/2017/02/05/…
rohitmohta

11
कंटेनर को रोकना, डॉक इंजन को रोकना और दोनों को बदलना hostconfig.jsonऔर config.v2.jsonयह काम करना महत्वपूर्ण है। विवरण देखने के लिए @rohitmohta द्वारा दिए गए लिंक का उपयोग करें।
कल्पक गद्रे

5
मेरे लिए काम किया है, बस एक बात अगर मैक पर docker ऐप का उपयोग करते हैं, तो / var / lib / docker / कंटेनरों के फ़ोल्डर में जाने के लिए यहां दिए गए निर्देशों का पालन करें: stackoverflow.com/a/41226917/2048266 , मूल रूप से चलाने के screen ~/Library/Containers/com.docker.docker/Data/com.docker.driver.amd64-linux/ttyबाद एक बार जब आप कर सकते हैं चलाने नेविगेट करने के लिए / var / lib / डोकर
nommer

14
खिड़कियों के लिए, क्या कोई कृपया मुझे कॉनटिनेटर्स फ़ोल्डर का स्थान साझा कर सकता है?
विजय

463

मुझे इस समस्या में भी दिलचस्पी है।

जैसा कि @ थैसमो ने उल्लेख किया है, पोर्ट अग्रेषण को केवल docker run(और docker create) कमांड के साथ निर्दिष्ट किया जा सकता है ।
अन्य आदेशों docker startमें -pविकल्प नहीं है और docker portकेवल वर्तमान अग्रेषण प्रदर्शित करता है।

पोर्ट फ़ॉरवर्डिंग जोड़ने के लिए, मैं हमेशा इन चरणों का पालन करता हूं,

  1. कंटेनर चलाना बंद करें

    docker stop test01
    
  2. प्रतिबद्ध कंटेनर

    docker commit test01 test02
    

    नोट: उपरोक्त, test02एक नई छवि है जो मैं test01कंटेनर से बना रहा हूं ।

  3. फिर से शुरू की गई छवि से चलाएँ

    docker run -p 8080:8080 -td test02
    

जहाँ पहला 8080 लोकल पोर्ट है और दूसरा 8080 कंटेनर पोर्ट है।


14
क्या होगा अगर मैं test01 नाम रखना चाहता हूं?
user69715

12
किसी को पता है कि क्या पोर्ट स्पेसिफिकेशन (-प्रकाश) के साथ अनुमति देने के लिए डॉकर के साथ एक खुला मुद्दा है docker start?
एलिजा लिन

8
और इस परिदृश्य में वॉल्यूम के साथ क्या होता है?
एंड्रयू सविनाख

78
यह एक भयानक समाधान है, मुझे नहीं पता कि यह 250 अपवोट कमाने में कैसे कामयाब रहा। हो सकता है कि जिन लोगों ने इस समस्या को हल किया हो उन्हें पता नहीं था कि किस तरह की गड़बड़ी हुई है। हां, यह भयानक है, और यह एक अलग बंदरगाह पर चलने वाले नए कंटेनर को शुरू करने के बराबर है।
अर्रर

25
@Arrrr शायद आप एक बेहतर जवाब छोड़ना चाहते हैं? मुझे यकीन है कि अगर आप हमें ऐसा करने का बेहतर तरीका बताएंगे तो हम सबकी सराहना करेंगे।
क्रॉकेआ

40

यदि "मौजूदा" से आपका मतलब "रनिंग" है, तो पोर्ट मैपिंग जोड़ना संभव नहीं है (वर्तमान में)।

हालाँकि, आप गतिशील रूप से उदाहरण के लिए एक नया नेटवर्क इंटरफ़ेस जोड़ सकते हैं, जैसे कि Pipework , यदि आपको बिना रुके / पुनः आरंभ किए किसी रनिंग कंटेनर में किसी सेवा को उजागर करना है।


4
यह शीर्ष उत्तर होना चाहिए। Succinct और यह OP के प्रश्न को संबोधित करता है जो अन्य कोई नहीं करता है! कभी-कभी एक नकारात्मक परिणाम एक परिणाम होता है!
आंशिक रूप से बादल छाए रहेंगे

19

यदि आप पोर्ट मैपिंग को एक कंटेनर में लागू कर सकते हैं तो निश्चित नहीं है। आप एक कंटेनर चलाते समय पोर्ट अग्रेषण लागू कर सकते हैं जो एक नया कंटेनर बनाने से अलग है।

$ docker run -p <public_port>:<private_port> -d <image>  

कंटेनर चलाना शुरू कर देंगे। यह ट्यूटोरियल पोर्ट पुनर्निर्देशन की व्याख्या करता है।


2
हां, इसलिए ऐसा लगता है कि कंटेनर निर्माण में पोर्ट मैपिंग जैसे विकल्पों को सेट करना संभव है।
थैस्मो

20
FYI करें यह उत्तर पूरी तरह से सही नहीं है। docker runएक नया कंटेनर बनाता है और शुरू करता है। इसके docker createबाद करने के बराबर है docker start
ट्रेवर सुलिवन 18

19

Hostconfig.json का संपादन अब काम नहीं कर रहा है। यह केवल उस पोर्ट के उजागर होने के साथ समाप्त होता है लेकिन होस्ट करने के लिए प्रकाशित नहीं किया जाता है। कंटेनरों को समेटना और उनका मनोरंजन करना मेरे लिए सबसे अच्छा तरीका नहीं है। किसी ने उल्लेख नहीं किया docker network?

सबसे अच्छा समाधान एक ही नेटवर्क के भीतर उल्टे प्रॉक्सी का उपयोग करना होगा

  1. एक नया नेटवर्क बनाएं यदि आपका पिछला कंटेनर किसी भी नाम से नहीं है।

    docker network create my_network

  2. अपने मौजूदा कंटेनर को बनाए गए नेटवर्क में शामिल करें

    docker network connect my_network my_existing_container

  3. एक ही नेटवर्क में शामिल होने के लिए आपके द्वारा आवश्यक पोर्ट को प्रकाशित करने के लिए एक उल्टा प्रॉक्सी सेवा (जैसे नगनेक्स) शुरू करें

    docker run -d --name nginx --network my_network -p 9000:9000 nginx

    वैकल्पिक रूप से nginx में default.conf को हटा दें

    docker exec nginx rm /etc/nginx/conf.d/default.conf

  4. एक नया nginx config बनाएँ

    server
    {
        listen 9000;
    
        location / {
            proxy_pass http://my_existing_container:9000;
            proxy_http_version 1.1;
            proxy_set_header Upgrade $http_upgrade;
            proxy_set_header Connection 'upgrade';
            proxy_set_header Host $host;
            proxy_cache_bypass $http_upgrade;
        }
    }
    

    Nginx कंटेनर के लिए कॉन्फ़िगरेशन की प्रतिलिपि बनाएँ।

    docker cp ./my_conf.conf nginx:/etc/nginx/conf.d/my_conf.conf

  5. नग्नेक्स को फिर से शुरू करें

    docker restart nginx

लाभ : नए बंदरगाहों को प्रकाशित करने के लिए, आप व्यवसाय कंटेनर को छुए बिना अपनी इच्छानुसार नगीन कंटेनर को सुरक्षित रूप से रोक सकते हैं / अपडेट / रीक्रिएट कर सकते हैं। यदि आपको नगनेक्स के लिए शून्य डाउन समय की आवश्यकता है, तो एक ही नेटवर्क में शामिल होने वाले अधिक उल्टे प्रॉक्सी सेवाओं को जोड़ना संभव है। इसके अलावा, एक कंटेनर एक से अधिक नेटवर्क में शामिल हो सकता है।

संपादित करें:

प्रॉक्सी नॉन-http सेवाओं को रिवर्स करने के लिए, कॉन्फ़िग फ़ाइल थोड़ी अलग है। ये रहा एक सरल उदाहरण:

upstream my_service {
    server my_existing_container:9000;
}

server {
    listen 9000;
    proxy_pass my_service;
}

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

1
@ एंटरप्राइज़ सिस्टम या प्रोजेक्ट्स के लिए @ एफ़शिन, मुझे लगता है कि यह समाधान (समय कम करने का कारण) या hostconfig.json फ़ाइल को हैक करने से बेहतर है (कम से कम आधिकारिक तौर पर पेश नहीं किया गया)। अतिरिक्त कंटेनर केवल आपके व्यवसाय कंटेनर के आंतरिक पोर्ट को उजागर करता है, इसके बजाय इसमें कोई भी बदलाव करता है।
सीन सी।

1
बहुत बढ़िया दृष्टिकोण। मुझे प्रॉक्सी के पीछे काम करने के लिए अपने कंटेनर के लिए अलग से नंगेक्स को कॉन्फ़िगर करने की आवश्यकता थी, लेकिन चीजों को करने का सही तरीका लगता है। नीली-हरी तैनाती के लिए भी काम करता है।
ब्रूक्स डुबोइस

17

फुजीमोटो में यूची का उदाहरण test01एक कंटेनर है, जबकि test02एक छवि है।

करने से पहले docker runआप मूल कंटेनर को हटा सकते हैं और फिर कंटेनर को फिर से उसी नाम से असाइन कर सकते हैं:

$ docker stop container01
$ docker commit container01 image01
$ docker rm container01
$ docker run -d -P --name container01 image01

( -Pमैन्युअल रूप से असाइन करने के बजाए रैंडम पोर्ट को पोर्ट एक्सपोज़ करने के लिए)।


12
कृपया ध्यान रखें। आप अपने सभी डेटा को खो देंगे, यह अंदर के आवेदन पर निर्भर करता है।
बैरी

14

यदि आप docker run <NAME>इसे चलाते हैं तो यह एक नई छवि पैदा करेगा, जो कि सबसे अधिक संभावना नहीं है कि आप क्या चाहते हैं।

यदि आप वर्तमान छवि बदलना चाहते हैं, तो निम्न कार्य करें:

docker ps -a

अपने लक्ष्य कंटेनर की आईडी लें और यहां जाएं:

cd /var/lib/docker/containers/<conainerID><and then some:)>

कंटेनर रोकें:

docker stop <NAME>

फाइलें बदलें

vi config.v2.json

"Config": {
    ....
    "ExposedPorts": {
        "80/tcp": {},
        "8888/tcp": {}
    },
    ....
},
"NetworkSettings": {
....
"Ports": {
     "80/tcp": [
         {
             "HostIp": "",
             "HostPort": "80"
         }
     ],

और फ़ाइल बदलें

vi hostconfig.json

"PortBindings": {
     "80/tcp": [
         {
             "HostIp": "",
             "HostPort": "80"
         }
     ],
     "8888/tcp": [
         {
             "HostIp": "",
             "HostPort": "8888"
         } 
     ]
 }

अपने कर्ता को पुनः आरंभ करें और उसे कार्य करना चाहिए।


2
यह मेरे लिए डॉकर संस्करण 17.09.0-CE पर काम नहीं किया। कंटेनर कॉन्‍फ़िगर करने की फ़ाइलों को पुराने मानों पर वापस लिखने के बाद मैंने शुरू किया।
thegeko

3
होस्ट सिस्टम @thegeko
yurenchen

1
यह काम! टी.के.एस! 1. स्टॉप कंटेनर, 2.चेंज फाइल्स, 3.स्टार्ट डॉकटर, 4.स्टार्ट बैक कंटेनर
डेटिनहॉकोक

12

आपके आस-पास का दूसरा तरीका यदि आप डॉकर गहराई विन्यास के साथ सहज नहीं हैं, तो आईपीटीवी आपके मित्र होंगे।

iptables -t nat -A DOCKER -p tcp --dport ${YOURPORT} -j DNAT --to-destination ${CONTAINERIP}:${YOURPORT}

iptables -t nat -A POSTROUTING -j MASQUERADE -p tcp --source ${CONTAINERIP} --destination ${CONTAINERIP} --dport ${YOURPORT}

iptables -A DOCKER -j ACCEPT -p tcp --destination ${CONTAINERIP} --dport ${YOURPORT}

यह सिर्फ एक ट्रिक है अनुशंसित तरीका नहीं यह मेरे परिदृश्य के साथ काम करता है क्योंकि मैं कंटेनर को रोक नहीं सकता था मुझे आशा है कि आप भी मदद करेंगे।


यह एक महान जवाब है! धन्यवाद! अगर मुझे नक्शा DOCKER_PORTबनाना है MACHINE_PORT, तो किन हिस्सों को बदलना चाहिए?
सिप्रियन टोमोयागो

नोट करने वाले wil को इस मैनुअल जोड़ के बारे में जानकारी नहीं है। जब आप बाद में पोर्ट को ठीक से उजागर करने वाले docker के साथ सेवा को पुनरारंभ करते हैं तो SO प्रविष्टियाँ नहीं निकाली जाती हैं। इसलिए जब कुछ भी बदलता है, तो iptables को बहुत सावधानी से जांचना सुनिश्चित करें। विशेषकर डुप्लिकेट प्रविष्टियों की तलाश करें!
एंथनी

8

हम इसे आसानी से पूरा करने के लिए ssh जैसे एक उपयोगी उपकरण का उपयोग करते हैं।

मैं ubuntu मेजबान और ubuntu आधारित docker छवि का उपयोग कर रहा था।

  1. डॉक करने वाले के पास ओपनश-क्लाइंट इंस्टॉल है।
  2. बाहरी डॉकटर (होस्ट) ने ओपनश-सर्वर सर्वर स्थापित किया है।

जब एक नए पोर्ट को मैप करने की आवश्यकता होती है,

कर्ता के अंदर निम्नलिखित कमांड चलाते हैं

ssh -R8888:localhost:8888 <username>@172.17.0.1

172.17.0.1 docker इंटरफ़ेस का आईपी था (आप इसे ifconfig docker0 | grep "inet addr" | cut -f2 -d":" | cut -f1 -d" "होस्ट पर चलाकर प्राप्त कर सकते हैं )।

यहाँ मैंने स्थानीय 8888 पोर्ट को होस्ट 8888 पर वापस मैप किया था। आप पोर्ट को आवश्यकतानुसार बदल सकते हैं।

यदि आपको एक और पोर्ट की आवश्यकता है, तो आप ssh को मार सकते हैं और नए पोर्ट के साथ इसमें -R की एक और लाइन जोड़ सकते हैं।

मैंने इसका परीक्षण नेटकैट से किया है।


2
  1. डॉक इंजन और उस कंटेनर को रोकें।
  2. /var/lib/docker/containers/${container_id}डायरेक्टरी में जाएं और एडिट करेंhostconfig.json
  3. संपादित करें PortBindings.HostPortकि आप परिवर्तन चाहते हैं।
  4. डॉक इंजन और कंटेनर शुरू करें।

-1

विंडोज और मैक उपयोगकर्ताओं के लिए, मैपिंग पोर्ट को बदलने का एक और आसान और अनुकूल तरीका है:

  1. डाउनलोड

  2. कंटेनर के सेटिंग पृष्ठ पर जाएं, पोर्ट टैब पर, आप सीधे प्रकाशित पोर्ट को संशोधित कर सकते हैं।

  3. कंटेनर फिर से शुरू करें


2
मैंने इस दृष्टिकोण की कोशिश की। काइनेमैटिक ने पोर्ट मैपिंग को लागू किया। होवेवर्टो ने उन्हें लागू किया, इसने मूल छवि से मेरे कंटेनर को फिर से बनाया। इसलिए यदि आप कंटेनर में किए गए परिवर्तनों को खोने से डरते हैं, तो इस विधि का उपयोग न करें।
वेगनहंटर 5

1
मैंने इसे पसंद किया, मुझे लगता है कि यह सवाल का जवाब नहीं देता है, और यह एक नया कंटेनर बनाता है। लेकिन कम से कम यह काम करता है, और यह एसओ परिणाम मेरी खोज के दौरान दिखाई दिया। +1
2b77bee6-5445-4c77-b1eb-4df3e5

-7

संक्षिप्त उत्तर: आप मौजूदा डॉकर कंटेनर में पोर्ट मैपिंग असाइन नहीं कर सकते

आपको एक नया कंटेनर चाहिए ... इससे निपटें।


4
रवैये की कोई जरूरत नहीं। इसके अलावा इस जवाब में पूरी तरह से कमी है।
14

1
विस्तार की कोई आवश्यकता नहीं। इस बार उत्तर देने और कंटेनरों की अल्पकालिक प्रकृति को व्यक्त करने के लिए टोन महत्वपूर्ण है।
स्टीफन

-11

यदि आप बस चल रहे कंटेनर के पोर्ट को बदलना चाहते हैं, तो आप निम्न कार्य करते हैं:

  1. मौजूदा कंटेनर बंद करें

    sudo docker ने NAME को रोक दिया

  2. अब नए पोर्ट मैपिंग के साथ पुनः आरंभ करें

    sudo docker रन -d -p 81:80 NAME

जहाँ तक:

"-d" बैकग्राउंड / डॉक करने वाले को

"-p" पोर्ट मैपिंग सक्षम करें

"81" बाहरी (उजागर) पोर्ट जिसका उपयोग आप अपने ब्राउज़र के साथ उपयोग करने के लिए करते हैं

"80" आंतरिक डॉकटर कंटेनर सुनो बंदरगाह


4
यह सिर्फ गलत है। में docker runआदेश, NAMEमें जबकि, से एक कंटेनर को चलाने के लिए छवि का नाम है बंद करने के लिए कंटेनर के नाम का उल्लेख है। docker stopNAME
जोंतन

1
"डॉकटर रन" एक नया कंटेनर बनाएगा। यह उसी कंटेनर नाम का उपयोग नहीं कर सकता है, जिसे रोक दिया गया था क्योंकि आप केवल उस नाम के साथ एक कंटेनर रख सकते हैं। इसलिए आपको यह करने की आवश्यकता होगी: "docker stop NAME", docker container rm NAME, फिर "docker run -d 81 -80 NAME" जैसा आपने लिखा है।
लांस काइंड
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.