डॉक रचना में पर्यावरण चर का उपयोग कैसे करें


217

मैं docker-compose.yml के अंदर env वैरिएबल का उपयोग करने में सक्षम होना चाहूंगा, docker- कंपोज के समय में पारित मूल्यों के साथ। इसका उदाहरण है। मैं आज बुनियादी डॉक रन कमांड के साथ ऐसा कर रहा हूं, जो मेरी स्क्रिप्ट के चारों ओर लिपटा हुआ है। क्या इस तरह की रचना के साथ इसे प्राप्त करने का कोई तरीका है, बिना किसी ऐसे बैश रैपर के?

proxy:
  hostname: $hostname
  volumes:
    - /mnt/data/logs/$hostname:/logs
    - /mnt/data/$hostname:/data

2
अलग-अलग विकल्पों के लिए देखें: docs.docker.com/compose/environment-variables
मसूद खारी

2
यह रचना के अंतिम संस्करण में हल किया गया है, आपका उदाहरण उसी तरह काम करेगा। चर प्रतिस्थापन के बारे में docs.docker.com/compose/compose-file/#variable-substeration की जाँच करें ।
नटबुसा

1
डॉकटर-ऐप को मत भूलना (जून 2018 के बाद से): stackoverflow.com/a/51007138/6309
VONC

जवाबों:


93
  1. एक बनाएँ template.yml, जो आपके docker-compose.ymlपर्यावरण चर के साथ है।
  2. मान लीजिए कि आपके पर्यावरण चर एक फ़ाइल 'env.sh' में हैं
  3. एक sh फ़ाइल में कोड का निचला भाग डालें और इसे चलाएं।

source env.sh; rm -rf docker-compose.yml; envsubst <"template.yml"> "docker-compose.yml";

docker-compose.ymlपर्यावरण चर के सही मानों के साथ एक नई फ़ाइल बनाई जाएगी।

नमूना टेम्प्लेट। हाइमल फ़ाइल:

oracledb:
        image: ${ORACLE_DB_IMAGE}
        privileged: true
        cpuset: "0"
        ports:
                - "${ORACLE_DB_PORT}:${ORACLE_DB_PORT}"
        command: /bin/sh -c "chmod 777 /tmp/start; /tmp/start"
        container_name: ${ORACLE_DB_CONTAINER_NAME}

नमूना env.sh फ़ाइल:

#!/bin/bash 
export ORACLE_DB_IMAGE=<image-name> 
export ORACLE_DB_PORT=<port to be exposed> 
export ORACLE_DB_CONTAINER_NAME=ORACLE_DB_SERVER

@Meet "BASH समाधान" के तहत, मेरे उत्तर बेली को देखने के लिए स्वतंत्र महसूस करें, जहाँ मैं इस दृष्टिकोण को थोड़ा और अच्छी तरह से रेखांकित करता हूँ।
modulitos

7
अभी भी कोई बेहतर समाधान फिलहाल?
लेविथिलो

13
आप पुनरावर्ती रूप से फ़ाइल को क्यों हटाएंगे (rm -rf docker-compose.yml)
moritzsiplefer

@ lorenzvth7 आप नीचे दिए गए मेरे उत्तर की जांच कर सकते हैं, जो मुझे लगता है कि थोड़ा और पूरी तरह से है: stackoverflow.com/a/33186458/1884158
modulitos

5
-1 यह समाधान केवल चीजों को जटिल करता है और इसे नई क्षमताओं के अनुसार अद्यतन किया जाना चाहिए। docs.docker.com/compose/environment-variables/…
Efrat Levitan

240

डॉक्टर समाधान:

ऐसा लगता है कि डॉकटर-कंपोजिट 1.5+ ने वैरिएबल सबस्टेशन को सक्षम किया है: https://github.com/docker/compose/releases

नवीनतम Docker Compose आपको अपनी रचना फ़ाइल से पर्यावरण चर का उपयोग करने की अनुमति देता है। तो आप अपने पर्यावरण चर को स्रोत कर सकते हैं, फिर लिखें जैसे:

set -a
source .my-env
docker-compose up -d

तब आप $ {VARIABLE} का उपयोग करके docker-compose.yml में चर का संदर्भ दे सकते हैं, जैसे:

db:
  image: "postgres:${POSTGRES_VERSION}"

और यहाँ डॉक्स से अधिक जानकारी है, यहाँ लिया गया: https://docs.docker.com/compose/compose-file/#variable-substeration

जब आप इस कॉन्फ़िगरेशन के साथ डॉकटर-कंपोज़ करते हैं, तो कंपोज़ शेल में POSTGRES_VERSION वातावरण चर की तलाश करता है और इसके मूल्य को प्रतिस्थापित करता है। इस उदाहरण के लिए, कंपोज़ इमेज को पोस्टग्रेज करने के लिए हल करता है: 9.3 कॉन्फ़िगरेशन को चलाने से पहले।

यदि कोई पर्यावरण चर सेट नहीं है, तो रिक्त स्ट्रिंग के साथ विकल्प लिखें। ऊपर के उदाहरण में, यदि POSTGRES_VERSION सेट नहीं है, तो छवि विकल्प का मूल्य पोस्टग्रैजेस है:।

$ VARIABLE और $ {VARIABLE} सिंटैक्स दोनों का समर्थन किया जाता है। विस्तारित शैल-शैली की विशेषताएं, जैसे $ {VARIABLE-default} और $ {VARIABLE / foo / bar}, समर्थित नहीं हैं।

यदि आपको कॉन्फ़िगरेशन मान में शाब्दिक डॉलर का चिह्न लगाने की आवश्यकता है, तो डबल डॉलर चिह्न ($ $) का उपयोग करें।

और मेरा मानना ​​है कि इस सुविधा को इस पुल अनुरोध में जोड़ा गया था: https://github.com/docker/compose/pull/1765

BASH समाधान:

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

एक उदाहरण .env फ़ाइल:

EXAMPLE_URL=http://example.com
# Note that the variable below is commented out and will not be used:
# EXAMPLE_URL=http://example2.com 
SECRET_KEY=ABDFWEDFSADFWWEFSFSDFM

# You can even define the compose file in an env variable like so:
COMPOSE_CONFIG=my-compose-file.yml
# You can define other compose files, and just comment them out
# when not needed:
# COMPOSE_CONFIG=another-compose-file.yml

फिर इस बैश स्क्रिप्ट को उसी डायरेक्टरी में चलाएं, जिसमें सब कुछ ठीक से तैनात होना चाहिए:

#!/bin/bash

docker rm -f `docker ps -aq -f name=myproject_*`
set -a
source .env
cat ${COMPOSE_CONFIG} | envsubst | docker-compose -f - -p "myproject" up -d

बस अपने bash फ़ाइल में सामान्य bash सिंटैक्स (यानी फ़ाइल से ${SECRET_KEY}सम्मिलित करने के लिए ) के साथ अपने env चर को देखें ।SECRET_KEY.env

नोट COMPOSE_CONFIGमेरी में परिभाषित किया गया है .envफ़ाइल और मेरी पार्टी स्क्रिप्ट में प्रयोग किया है, लेकिन आप आसानी से जगह ले सकता है {$COMPOSE_CONFIG}के साथ my-compose-file.ymlबैश लिपि में।

यह भी ध्यान दें कि मैंने इस तैनाती को "myproject" उपसर्ग के साथ अपने सभी कंटेनरों का नाम देकर लेबल किया है। आप अपने इच्छित किसी भी नाम का उपयोग कर सकते हैं, लेकिन यह आपके कंटेनरों की पहचान करने में मदद करता है ताकि आप बाद में उन्हें आसानी से संदर्भित कर सकें। यह मानते हुए कि आपके कंटेनर बेकार हैं, जैसा कि उन्हें होना चाहिए, यह स्क्रिप्ट जल्दी से आपके कंटेनर को आपके .env फ़ाइल पैरामेट्स और आपके कंपोज़ YAML फ़ाइल के अनुसार हटा देगी।

अपडेट चूंकि यह उत्तर काफी लोकप्रिय लगता है, मैंने एक ब्लॉग पोस्ट लिखी है जो मेरे डॉकियर परिनियोजन वर्कफ़्लो का अधिक गहराई से वर्णन करता है: http://lukeswart.net/2016/03/lets-deploy-part-1/ जब आप जोड़ते हैं तो यह मददगार हो सकता है एक परिनियोजन कॉन्फ़िगरेशन के लिए अधिक जटिलता, जैसे कि nginx config, LetsEncrypt certs, और लिंक किए गए कंटेनर।


2
आप के grep foo file.textबजाय बस कर सकते हैं cat file.text | grep foo। मेरे मामले में मुझे करना था export $(grep "^[^#]" .config | xargs) && cat docker-compose.yml | envsubst
जॉर्ज लावेन

"मुझे लगता है कि लोगों के पास डॉकर के पर्यावरण चर समर्थन के साथ समस्याएं हैं" - क्या आपके पास टिकट के लिए कोई विवरण या लिंक है?
tleyden

क्षमा करें, मैं उस विशिष्ट मुद्दे को लॉग नहीं कर रहा था जिसका मैं अनुभव कर रहा था, और यह बहुत पहले (~ 6 महीने) था, मुझे नहीं पता कि क्या यह अभी भी प्रासंगिक है। लेकिन हां, डॉकर पर्यावरण चर समर्थन में कुछ विशेषताएं छोटी थीं, और यह कई उपयोगकर्ताओं द्वारा रिपोर्ट की गई थी। मेरा मानना ​​है कि अब यह काफी बेहतर है। लेकिन जब तैनाती विन्यास काफी जटिल हो जाता है, तो मैं कंटेनर ऑर्केस्ट्रेशन के लिए कॉन्फ़िगरेशन लॉजिक और डॉकर कम्पोज को संभालने के लिए बैश का उपयोग करके इसे संशोधित करना पसंद करूंगा।
modulitos

8
PSA: यह केवल साथ काम करता हैdocker-compose up और इसके साथ नहीं docker-compose run
क्रिएग्लस्टिग डेग

5
यह समाधान docs.docker.com/compose/compose-file/#envfile है जो मैं उपयोग करता हूं जहां आप एक .envअंडर से पर्यावरण चर जोड़ते हैं env_file। तब आप चर का docker-compose.ymlउपयोग कर संदर्भ ले सकते हैं${VARIABLE}
मुसल्ले

111

ऐसा लगता है कि फ़ाइल में डिफ़ॉल्ट पर्यावरण चर के लिए अब डॉकटर-कंपोज़ को देशी समर्थन प्राप्त है

आपको बस अपने वेरिएबल्स को नाम की फ़ाइल में घोषित करना .envहोगा और वे docker-compose.yml में उपलब्ध होंगे।

उदाहरण के लिए, .envसामग्री के साथ फ़ाइल के लिए :

MY_SECRET_KEY=SOME_SECRET
IMAGE_NAME=docker_image

आप अपने वैरिएबल को अंदर ले जा सकते हैं docker-compose.ymlया उन्हें कंटेनर में भेज सकते हैं:

my-service:
  image: ${IMAGE_NAME}
  environment:
    MY_SECRET_KEY: ${MY_SECRET_KEY}

4
यह सबसे अच्छा उपाय है!
लादेनकोव व्लादिस्लाव

4
यह मेरे लिए भी काम किया। मुझे नहीं पता, लेकिन फ़ाइल का नाम शाब्दिक होना चाहिए .env, उदाहरण के config.envलिए मेरे लिए काम नहीं किया।
एचबीटी

1
@HBat " एक छुपी हुई फ़ाइल का अर्थ है - यह स्थानीय विन्यास फाइल के लिए सामान्य प्रक्रिया है
जेरेमी हजेक

2
सबसे अच्छा समाधान। और हम /। / पर्यावरण प्रॉप्स को जोड़ सकते हैं और उन .env का उपयोग करने के साथ एक पर्यावरण के रूप में उपयोग कर सकते हैं। यह अधिक सुरक्षित होगा।
चिन्तक दिनदासा

24

कंटेनर के अंदर डॉक-कम्पोज़ 3.x सेट पर्यावरण चर के लिए निम्नलिखित लागू होता है

विधि - 1 सीधी विधि

web:
  environment:
    - DEBUG=1
      POSTGRES_PASSWORD: 'postgres'
      POSTGRES_USER: 'postgres'

विधि - 2 ".env" फ़ाइल

Docker-compose.yml के समान स्थान पर .env फ़ाइल बनाएँ

$ cat .env
TAG=v1.5
POSTGRES_PASSWORD: 'postgres'

और आपकी रचना फ़ाइल की तरह होगी

$ cat docker-compose.yml
version: '3'
services:
  web:
    image: "webapp:${TAG}"
    postgres_password: "${POSTGRES_PASSWORD}"

स्रोत


2
मैं विधि 1 का पूरा उदाहरण देखना चाहता हूं। मैं यह काम नहीं कर सका, इसलिए .env फ़ाइल (जो ठीक काम करती है) का उपयोग करके समाप्त हुई।
बॉबहाइ

20

वॉल्यूम के लिए पर्यावरण चर का उपयोग करते समय आपको आवश्यकता होती है:

  1. बनाने .env जिसमें एक ही फ़ोल्डर में फ़ाइल docker-compose.yaml फ़ाइल

  2. .envफ़ाइल में चर घोषित करें :

    HOSTNAME=your_hostname
    
  3. बदले $hostnameके लिए ${HOSTNAME}पर docker-compose.yaml फ़ाइल

    proxy:
      hostname: ${HOSTNAME}
      volumes:
        - /mnt/data/logs/${HOSTNAME}:/logs
        - /mnt/data/${HOSTNAME}:/data
    

बेशक आप प्रत्येक बिल्ड पर गतिशील रूप से ऐसा कर सकते हैं:

echo "HOSTNAME=your_hostname" > .env && sudo docker-compose up

9
ध्यान दें, डॉक्स के अनुसार:The .env file feature only works when you use the docker-compose up command and does not work with docker stack deploy.
जेम्स जेंट्स

19

सबसे अच्छा तरीका docker-compose.ymlफ़ाइल के बाहर पर्यावरण चर निर्दिष्ट करना है । आप env_fileसेटिंग का उपयोग कर सकते हैं , और उसी लाइन के भीतर अपनी पर्यावरण फ़ाइल को परिभाषित कर सकते हैं । फिर एक डॉक-कंपोज़ करना फिर से नए पर्यावरण चर के साथ कंटेनरों को फिर से बनाना चाहिए।

यहाँ मेरा docker-compose.yml कैसा दिखता है:

services:
  web:
    env_file: variables.env

नोट: docker-compose प्रत्येक पंक्ति में एक env फ़ाइल के VAR=VALप्रारूप में होने की अपेक्षा करता है। फ़ाइल के exportअंदर उपयोग करने से बचें .env। साथ ही, .envफ़ाइल को उस फ़ोल्डर में रखा जाना चाहिए जहाँ docker-compose कमांड निष्पादित हो।


2
सबसे अच्छा तरीका वास्तव में
डेन

नहीं। यह स्वचालित रूप से पर्यावरण चर को docker कंटेनर के अंदर उपलब्ध नहीं कराएगा। आपको अभी भी पर्यावरण अनुभाग के तहत इनका स्पष्ट रूप से उल्लेख करना होगा।
काटा

6

तुम नहीं कर सकते ... अभी तक। लेकिन यह एक विकल्प है, डॉक-कंपोजर की तरह सोचें। हाइमल जनरेटर:

https://gist.github.com/Vad1mo/9ab63f28239515d4dafd

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


4

मेरे पास एक सरल बैश स्क्रिप्ट है, जिसके लिए मैंने इसका उपयोग करने से पहले इसे अपनी फ़ाइल पर चलाने का अर्थ है: https://github.com/antonosmond-subber

मूल रूप से पर्यावरण चर को निरूपित करने के लिए डबल घुंघराले ब्रेसिज़ का उपयोग करके बस अपनी कंपोज़ फ़ाइल बनाएं:

app:
    build: "{{APP_PATH}}"
ports:
    - "{{APP_PORT_MAP}}"

डबल घुंघराले ब्रेसिज़ में कुछ भी उसी नाम के पर्यावरण चर के साथ बदल दिया जाएगा, अगर मेरे पास निम्न पर्यावरण चर सेट थे:

APP_PATH=~/my_app/build
APP_PORT_MAP=5000:5000

subber docker-compose.ymlपरिणामी फ़ाइल चलाने पर ऐसा दिखेगा:

app:
    build: "~/my_app/build"
ports:
    - "5000:5000"

2

जहाँ तक मुझे पता है, यह एक कार्य-प्रगति है। वे इसे करना चाहते हैं, लेकिन यह अभी तक जारी नहीं हुआ है। देखें 1377 ( "नया" 495 कि @Andy ने उल्लेख किया गया था)।

मैंने @Thomas द्वारा प्रस्तावित "CI के भाग के रूप में .yml" दृष्टिकोण को लागू करते हुए समाप्त किया।


1

env .env फ़ाइल में जोड़ें

जैसे कि

VERSION=1.0.0

फिर इसे सहेजें deploy.sh

INPUTFILE=docker-compose.yml
RESULT_NAME=docker-compose.product.yml
NAME=test

prepare() {
        local inFile=$(pwd)/$INPUTFILE
        local outFile=$(pwd)/$RESULT_NAME
        cp $inFile $outFile
        while read -r line; do
            OLD_IFS="$IFS"
            IFS="="
            pair=($line)
            IFS="$OLD_IFS"
               sed -i -e "s/\${${pair[0]}}/${pair[1]}/g" $outFile
            done <.env
     }
       
deploy() {
        docker stack deploy -c $outFile $NAME
}

        
prepare
deploy
    

1

Doer-compse.yml में गतिशील मानों को परिभाषित करने के लिए .env फ़ाइल का उपयोग करें। यह पोर्ट या कोई अन्य मूल्य हो।

नमूना डॉकटर-रचना:

testcore.web:
       image: xxxxxxxxxxxxxxx.dkr.ecr.ap-northeast-2.amazonaws.com/testcore:latest
       volumes: 
            - c:/logs:c:/logs
       ports:
            - ${TEST_CORE_PORT}:80
       environment:
            - CONSUL_URL=http://${CONSUL_IP}:8500 
            - HOST=${HOST_ADDRESS}:${TEST_CORE_PORT}

.Env फ़ाइल के अंदर आप इन चरों के मान को परिभाषित कर सकते हैं:

CONSUL_IP=172.31.28.151
HOST_ADDRESS=172.31.16.221
TEST_CORE_PORT=10002

1
env SOME_VAR="I am some var" OTHER_VAR="I am other var" docker stack deploy -c docker-compose.yml

संस्करण 3.6 का उपयोग करें:

version: "3.6"
services:
  one:
    image: "nginx:alpine"
    environment:
      foo: "bar"
      SOME_VAR:
      baz: "${OTHER_VAR}"
    labels:
      some-label: "$SOME_VAR"
  two:
    image: "nginx:alpine"
    environment:
      hello: "world"
      world: "${SOME_VAR}"
    labels:
      some-label: "$OTHER_VAR"

मुझे यह लिंक https://github.com/docker/cli/issues/939 मिला


1

1.25.4 के बाद से, डॉकटर-कम्पोज़ उस विकल्प का समर्थन करता --env-fileहै जो आपको चर युक्त फ़ाइल निर्दिष्ट करने में सक्षम बनाता है।

तुम्हारा इस तरह दिखना चाहिए:

hostname=my-host-name

और आज्ञा:

docker-compose --env-file /path/to/my-env-file config
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.