क्या बैश स्क्रिप्ट को डीबग करने का कोई तरीका है? जैसे कुछ ऐसा जो एक तरह के निष्पादन लॉग को प्रिंट करता है जैसे "कॉलिंग लाइन 1", "कॉलिंग लाइन 2" आदि।
क्या बैश स्क्रिप्ट को डीबग करने का कोई तरीका है? जैसे कुछ ऐसा जो एक तरह के निष्पादन लॉग को प्रिंट करता है जैसे "कॉलिंग लाइन 1", "कॉलिंग लाइन 2" आदि।
जवाबों:
sh -x script [arg1 ...]
bash -x script [arg1 ...]
ये आपको अंजाम दे रहे हैं जो निष्पादित किया जा रहा है। (उत्तर के निचले भाग के पास 'स्पष्टीकरण' भी देखें।)
कभी-कभी, आपको स्क्रिप्ट के भीतर डिबगिंग को नियंत्रित करने की आवश्यकता होती है। उस स्थिति में, जैसा कि चेतो ने मुझे याद दिलाया , आप उपयोग कर सकते हैं:
set -x
इससे डिबगिंग चालू हो जाती है। आप इसे फिर से बंद कर सकते हैं:
set +x
(आप $-मौजूदा झंडे की स्थिति का विश्लेषण करके पता लगा सकते हैं , वर्तमान झंडे, के लिए x)
इसके अलावा, गोले आम तौर पर -n'कोई निष्पादन नहीं' और -v'क्रिया' मोड के लिए विकल्प प्रदान करते हैं ; आप यह देखने के लिए संयोजन में इनका उपयोग कर सकते हैं कि क्या शेल को लगता है कि यह आपकी स्क्रिप्ट को निष्पादित कर सकता है - कभी-कभी उपयोगी यदि आपके पास एक असंतुलित उद्धरण है
इस बात पर विवाद है कि -xबाश में ' ' विकल्प अन्य गोले (टिप्पणियों को देखें) से अलग है। बैश मैनुअल का कहना है:
-एक्स
साधारण कमांड्स, forकमांड्स, caseकमांड्स, selectकमांड्स और अरिथमेटिक forकमांड्स और उनके तर्कों या संबंधित शब्द सूचियों को उनके विस्तारित होने के बाद और उनके निष्पादित होने से पहले प्रिंट करें । PS4चर के मूल्य का विस्तार किया जाता है और परिणामी मूल्य को कमांड और उसके विस्तारित तर्कों से पहले प्रिंट किया जाता है।
यह बहुत अलग व्यवहार को इंगित नहीं करता है। मैं -xमैनुअल में ' ' के लिए कोई अन्य प्रासंगिक संदर्भ नहीं देखता हूं । यह स्टार्टअप अनुक्रम में अंतर का वर्णन नहीं करता है।
क्लेरिफिकेशन : एक विशिष्ट लिनक्स बॉक्स जैसे सिस्टम पर, जहां '' /bin/sh'एक सिमलिंक है' /bin/bash'(या जहां भी बैश निष्पादन योग्य पाया जाता है), दो कमांड लाइन निष्पादन ट्रेस के साथ स्क्रिप्ट को चलाने के बराबर प्रभाव को प्राप्त करते हैं। अन्य प्रणालियों पर (उदाहरण के लिए, सोलारिस और लिनक्स के कुछ और आधुनिक संस्करण), /bin/shबैश नहीं है, और दो कमांड लाइन अलग-अलग परिणाम देंगे। सबसे विशेष रूप से, ' /bin/sh' बैश में निर्माणों से भ्रमित होगा कि यह बिल्कुल भी नहीं पहचानता है। (सोलारिस पर, /bin/shएक बॉर्न शेल है, आधुनिक लिनक्स पर, यह कभी-कभी डैश होता है - एक छोटा, अधिक कड़ाई से पीओएस-ओनली शेल।) जब इस तरह के नाम से आह्वान किया जाता है, तो 'शेबंग' लाइन (' #!/bin/bash' बनाम '#!/bin/sh'')
बैश मैनुअल में बैश पोसिक्स मोड पर एक सेक्शन है , जो इस उत्तर के लंबे समय तक लेकिन गलत संस्करण के विपरीत है (नीचे टिप्पणी भी देखें), विस्तृत विवरण में 'बैश इनवॉल्ड sh' और 'बैश इनवॉक्ड' के बीच के अंतर का वर्णन करता है। bash'।
जब (बश) शेल स्क्रिप्ट को डीबग करना, यह समझदार और समझदार होगा - आवश्यक भी - -xविकल्प के साथ शेलबैंग लाइन में नामित शेल का उपयोग करने के लिए । अन्यथा, आप (विल?) स्क्रिप्ट चलाते समय डिबगिंग करते समय अलग व्यवहार प्राप्त कर सकते हैं।
bashस्क्रिप्ट निर्दिष्ट की । और इसके साथ बैश स्क्रिप्ट चलाने से sh -xयह पूरी तरह से अलग व्यवहार करेगा! कृपया अपना उत्तर अपडेट करें।
export PS4='+(${BASH_SOURCE}:${LINENO}): ${FUNCNAME[0]:+${FUNCNAME[0]}(): }'
मैंने अपनी स्क्रिप्ट को डीबग करने के लिए निम्न विधियों का उपयोग किया है।
set -eयदि कोई बाहरी कार्यक्रम एक गैर-शून्य निकास स्थिति देता है, तो स्क्रिप्ट को तुरंत रोक देता है। यह उपयोगी है यदि आपकी स्क्रिप्ट सभी त्रुटि मामलों को संभालने का प्रयास करती है और जहां ऐसा करने में विफलता फंस गई है।
set -x ऊपर उल्लेख किया गया था और निश्चित रूप से सभी डिबगिंग विधियों में सबसे उपयोगी है।
set -n यदि आप सिंटैक्स त्रुटियों के लिए अपनी स्क्रिप्ट की जांच करना चाहते हैं तो यह उपयोगी हो सकता है।
straceयह देखने के लिए भी उपयोगी है कि क्या हो रहा है। विशेष रूप से उपयोगी है यदि आपने स्वयं स्क्रिप्ट नहीं लिखी है।
strace -fयदि आप स्क्रिप्ट द्वारा शुरू की गई प्रक्रियाओं में त्रुटियों को ढूंढना चाहते हैं, तो इसकी आवश्यकता है। (जो इसे कई गुना अधिक क्रियात्मक बनाता है, लेकिन फिर भी उपयोगी है यदि आप इसे उन सीस्कॉल तक सीमित करते हैं जो आप रुचि रखते हैं)।
set -eहै ... कंट्रोवर्शियल ।
यह उत्तर मान्य और उपयोगी है: https://stackoverflow.com/a/951352
लेकिन, मुझे लगता है कि "मानक" स्क्रिप्ट डीबगिंग विधियाँ अक्षम, अचूक, और उपयोग करने में कठिन हैं। उन लोगों के लिए जो परिष्कृत GUI डीबगर्स का उपयोग करते थे, जो आपकी उंगलियों पर सब कुछ डालते हैं और काम को आसान समस्याओं (और कठिन समस्याओं के लिए संभव) के लिए एक हवा बनाते हैं, ये समाधान बहुत संतोषजनक नहीं हैं।
मैं जो भी करता हूं वह DDD और bashdb के संयोजन का उपयोग करता है। पूर्व अपने उत्तरार्द्ध को निष्पादित करता है, और उत्तरार्द्ध आपकी स्क्रिप्ट को निष्पादित करता है। यह आपके सिर में संदर्भ बनाए रखने या स्रोत को फिर से सूचीबद्ध करने के लिए निरंतर मानसिक प्रयास के बिना, संदर्भ में कोड के माध्यम से कदम रखने और चर, स्टैक आदि को देखने के लिए एक बहु-खिड़की यूआई प्रदान करता है।
यहाँ स्थापित करने पर मार्गदर्शन है: http://ubuntuforums.org/showthread.php?t=660223
आप स्क्रिप्ट के भीतर "सेट -x" भी लिख सकते हैं।
मुझे शेलचेक उपयोगिता मिली और कुछ लोगों को यह दिलचस्प लग सकता है https://github.com/koalaman/shellcheck
एक छोटा सा उदाहरण:
$ cat test.sh
ARRAY=("hello there" world)
for x in $ARRAY; do
echo $x
done
$ shellcheck test.sh
In test.sh line 3:
for x in $ARRAY; do
^-- SC2128: Expanding an array without an index only gives the first element.
बग को ठीक करें, पहले प्रयास करें ...
$ cat test.sh
ARRAY=("hello there" world)
for x in ${ARRAY[@]}; do
echo $x
done
$ shellcheck test.sh
In test.sh line 3:
for x in ${ARRAY[@]}; do
^-- SC2068: Double quote array expansions, otherwise they're like $* and break on spaces.
चलो फिर से कोशिश करें...
$ cat test.sh
ARRAY=("hello there" world)
for x in "${ARRAY[@]}"; do
echo $x
done
$ shellcheck test.sh
अभी खोजे!
यह सिर्फ एक छोटा सा उदाहरण है।
प्लग किए गए और बेसहेस के साथ ग्रहण का उपयोग करें।
https://sourceforge.net/projects/shelled/?ource=directory https://sourceforge.net/projects/basheclipse/?source=directory
शेल्ड के लिए: ज़िप डाउनलोड करें और इसे सहायता के माध्यम से ग्रहण में आयात करें -> नया सॉफ़्टवेयर स्थापित करें: स्थानीय संग्रह के लिए आधारभूत: जार को ड्रॉप्सीन की निर्देशिका में कॉपी करें
चरणों का पालन करें https://sourceforge.net/projects/basheclipse/files/?source=navbar
मैंने http://dietrichschroff.blogspot.de/2017/07/bash-en enable-eclipse-for-bash.html पर कई स्क्रीनशॉट के साथ एक ट्यूटोरियल लिखा है
मैंने एक बैश डीबगर बनाया। इसे मात्र आजमाएं। मुझे उम्मीद है कि यह https://sourceforge.net/projects/bashdebugingbash मदद करेगा
set + x = @ECHO OFF, सेट -x = @ECHO ON।
आप -xvनिम्न प्रकार से मानक शेबंग में विकल्प जोड़ सकते हैं :
#!/bin/bash -xv
-x: प्रदर्शन कमांड और उनके तर्क जैसे ही वे निष्पादित होते हैं।
-v: शेल इनपुट लाइनें प्रदर्शित करें क्योंकि वे पढ़े जाते हैं।
ltraceके समान एक और लिनक्स उपयोगिता है strace। हालाँकि, ltraceसभी लाइब्रेरी कॉल को एक निष्पादन योग्य या चलने वाली प्रक्रिया में सूचीबद्ध करता है। इसका नाम खुद लाइब्रेरी-कॉल ट्रेसिंग से आता है। उदाहरण के लिए:
ltrace ./executable <parameters>
ltrace -p <PID>
मुझे लगता है कि आप इस बैश डीबगर को आज़मा सकते हैं: http://bashdb.sourceforge.net/ ।
set -[nvx]के अतिरिक्त
set -x
तथा
set +x
डंप को रोकने के लिए।
मैं set -vविच डंप के बारे में कम विकसित आउटपुट के रूप में बोलना चाहूंगा ।
bash <<<$'set -x\nfor i in {0..9};do\n\techo $i\n\tdone\nset +x' 2>&1 >/dev/null|wc -l
21
for arg in x v n nx nv nvx;do echo "- opts: $arg"
bash 2> >(wc -l|sed s/^/stderr:/) > >(wc -l|sed s/^/stdout:/) <<eof
set -$arg
for i in {0..9};do
echo $i
done
set +$arg
echo Done.
eof
sleep .02
done
- opts: x
stdout:11
stderr:21
- opts: v
stdout:11
stderr:4
- opts: n
stdout:0
stderr:0
- opts: nx
stdout:0
stderr:0
- opts: nv
stdout:0
stderr:5
- opts: nvx
stdout:0
stderr:5
कुछ चर का परीक्षण करने के लिए, मैं कुछ समय का उपयोग करता हूं:
bash <(sed '18ideclare >&2 -p var1 var2' myscript.sh) args
जोड़ने के लिए:
declare >&2 -p var1 var2
पंक्ति 18 पर और परिणामी स्क्रिप्ट ( आर्ग्स के साथ ) चल रही है, उन्हें संपादित किए बिना।
बेशक, इसे जोड़ने के लिए इस्तेमाल किया जा सकता है set [+-][nvx]:
bash <(sed '18s/$/\ndeclare -p v1 v2 >\&2/;22s/^/set -x\n/;26s/^/set +x\n/' myscript) args
declare -p v1 v2 >&2लाइन 18 के बाद, set -xलाइन 22 set +xसे पहले और लाइन 26 से पहले जोड़ देगा ।
bash <(sed '2,3s/$/\ndeclare -p LINENO i v2 >\&2/;5s/^/set -x\n/;7s/^/set +x\n/' <(
seq -f 'echo $@, $((i=%g))' 1 8)) arg1 arg2
arg1 arg2, 1
arg1 arg2, 2
declare -i LINENO="3"
declare -- i="2"
/dev/fd/63: line 3: declare: v2: not found
arg1 arg2, 3
declare -i LINENO="5"
declare -- i="3"
/dev/fd/63: line 5: declare: v2: not found
arg1 arg2, 4
+ echo arg1 arg2, 5
arg1 arg2, 5
+ echo arg1 arg2, 6
arg1 arg2, 6
+ set +x
arg1 arg2, 7
arg1 arg2, 8
नोट: देखभाल के बारे में मक्खी संशोधनों से $LINENOप्रभावित होगा !
(परिणामी स्क्रिप्ट को देखने के लिए, केवल ड्रॉप करना bash <(और ) arg1 arg2)
बैश स्क्रिप्ट को कैसे प्रोफाइल करें, इस बारे में मेरे जवाब पर एक नज़र डालें
शेल के वैश्विक वैरिएबल के माध्यम से शेल स्क्रिप्ट के लिए लॉगिंग पर विस्तार की अच्छी मात्रा है। हम शेल स्क्रिप्ट में इसी तरह की लॉगिंग का अनुकरण कर सकते हैं: http://www.cubicrace.com/2016/03/log-tracing-mechnism-for-shell-scripts.html
इस पोस्ट में INFO, DEBUG, ERROR जैसे लॉग स्तरों के परिचय पर विवरण है। स्क्रिप्ट प्रविष्टि, स्क्रिप्ट निकास, फ़ंक्शन प्रविष्टि, फ़ंक्शन निकास जैसे अनुरेखण विवरण।
नमूना लॉग: