2016-01-06 15 views
23

में कमांड आउटपुट रीडायरेक्ट करना मैं अपने सर्वर के लिए कुछ सरल लॉगिंग करना चाहता हूं जो एक डॉकर कंटेनर में चल रहा एक छोटा फ्लास्क ऐप है।डॉकर

यहाँ Dockerfile

# Dockerfile 
FROM dreen/flask 
MAINTAINER dreen 
WORKDIR /srv 

# Get source 
RUN mkdir -p /srv 
COPY perfektimprezy.tar.gz /srv/perfektimprezy.tar.gz 
RUN tar x -f perfektimprezy.tar.gz 
RUN rm perfektimprezy.tar.gz 

# Run server 
EXPOSE 80 
CMD ["python", "index.py", "1>server.log", "2>server.log"] 

आप अंतिम पंक्ति मैं एक फाइल करने के लिए stderr और stdout अनुप्रेषित पर देख सकते हैं है। अब मैं इस कंटेनर चलाने के लिए और में यह

docker run -d -p 80:80 perfektimprezy 
docker exec -it "... id of container ..." bash 

खोल और निरीक्षण निम्नलिखित बातें:

सर्वर चल रहा है और काम

वेबसाइट कोई /srv/server.log

ps aux | grep python पैदावार है:

root   1 1.6 3.2 54172 16240 ?  Ss 13:43 0:00 python index.py 1>server.log 2>server.log 
root  12 1.9 3.3 130388 16740 ?  Sl 13:43 0:00 /usr/bin/python index.py 1>server.log 2>server.log 
root  32 0.0 0.0 8860 388 ?  R+ 13:43 0:00 grep --color=auto python 

लेकिन वहां ar ई लॉग नहीं ... हालांकि, अगर मैं docker attach कंटेनर में हूं तो मैं कंसोल में ऐप जेनरेट आउटपुट देख सकता हूं।

डॉकर का उपयोग करते समय मैं फ़ाइल में stdout/err को सही तरीके से रीडायरेक्ट कैसे करूं?

उत्तर

23

जब आप के रूप में CMD के रूप में एक JSON सूची निर्दिष्ट करते हैं, तो इसे एक खोल में निष्पादित नहीं किया जाएगा, इसलिए सामान्य शैल फ़ंक्शंस, जैसे स्टडआउट और स्टेडर रीडायरेक्शन, काम नहीं करेंगे।

documentation से

:

कार्यकारी प्रपत्र एक JSON सारणी, जिसका अर्थ है कि आप शब्दों के आसपास डबल कोट्स (") नहीं एकल उद्धरण (') का उपयोग करना चाहिए के रूप में पार्स किया जाता है।

खोल फ़ॉर्म के विपरीत, निष्पादन फॉर्म कमांड खोल नहीं लगाता है। इसका मतलब है कि सामान्य खोल प्रसंस्करण नहीं होता है। उदाहरण के लिए, CMD [ "echo", "$HOME" ]$HOME पर परिवर्तनीय प्रतिस्थापन नहीं करेगा। यदि आप खोल प्रसंस्करण चाहते हैं तो या तो खोल फ़ॉर्म का उपयोग करें या सीधे एक खोल निष्पादित करें, उदाहरण के लिए: CMD [ "sh", "-c", "echo", "$HOME" ]

क्या अपने आदेश वास्तव में करता है अपने index.py स्क्रिप्ट पर कार्य करते हैं और उस अजगर स्क्रिप्ट में तार "1>server.log" और "2>server.log" कमांड लाइन तर्क के रूप में पारित करने के लिए है।

उपयोग के बजाय निम्न में से एक (दोनों काम करना चाहिए):

  1. CMD "python index.py > server.log 2>&1"
  2. CMD ["/bin/sh", "-c", "python index.py > server.log 2>&1"]
+0

https://github.com/docker/docker/issues/7440 – user2915097

+2

देखें [प्रलेखन] (https: //docs.docker।कॉम/इंजन/संदर्भ/बिल्डर/# शेल-फॉर्म-एंट्रीपॉइंट-उदाहरण) कंटेनर ओएस सिग्नल और 'डॉकर स्टॉप' का सम्मान करने के लिए 'exec' shell अंतर्निहित' का उपयोग करने की अनुशंसा करता है। तो पहला आदेश बन जाता है: 'सीएमडी निष्पादन पायथन index.py> server.log 2> और 1' – lucian

4

बस एक पूरक, जब का उपयोग कर डोकर-रचना, आप भी आजमा सकते हैं:

command: bash -c "script_or_command > /path/to/log/command.log 2>&1"

+0

क्या आपने इसे आजमाया? यह मेरे लिए सही समझ में आता है, और काम नहीं करता है! अब तक मैं डॉकर-कंपोज़ 'कमांड' निर्देश का उपयोग करते समय stdout पर stderr को पूरी तरह से असफल कर रहा हूं। stdout ठीक से आता है। –

+0

हां, यह मेरे लिए सही काम करता है। –

+0

आह, मेरी समस्या यह साबित होती है कि मुझे 'PYTHONUNBUFFERED' पर्यावरण चर सेट करने या' -u' ध्वज के साथ पायथन चलाने की आवश्यकता है, क्योंकि यह बताता है: http://stackoverflow.com/a/24183941/562883 –