test, [, और [[ (2020)
Shell programmers POSIX-standard `[ / test` और Bash-specific `[[` के बीच conditionals के लिए trade-offs पर विचार करते हैं, और यह दिखाते हैं कि कैसे सूक्ष्म syntax rules, quoting pitfalls, और boolean logic की अजीबताएँ आसानी से bugs ला सकती हैं। कई लोग उन scripts के लिए, जिन्हें विविध या सीमित systems (जैसे BSD, embedded, minimal Docker images) पर चलना हो, portable, Bourne-compatible `sh` पर टिके रहने की वकालत करते हैं, जबकि दूसरे controlled environments में सुविधा के लिए Bash, zsh या ksh features को प्राथमिकता देते हैं। बातचीत आगे बढ़कर इस प्रश्न तक जाती है कि क्या जटिल shell scripts को Python या Perl जैसी “real” languages से बदल देना चाहिए, ShellCheck और `set -euo pipefail` जैसे tools की भूमिका क्या है, और long-term portability तथा developer productivity के बीच कैसे संतुलन बनाया जाए।
शेल का चुनाव और पोर्टेबिलिटी
- “सिर्फ Bash/[[ इस्तेमाल करो” और “POSIX sh को लक्ष्य बनाओ” के बीच बड़ा विभाजन है।
- Bash के पक्ष में:
[[ज़्यादा स्पष्ट और शक्तिशाली है; जिन वातावरणों पर उनका नियंत्रण है, उनमें वैसे भी bash, zsh, या ksh मौजूद होते हैं। कई संदर्भों में bash इंस्टॉल करना कम मेहनत वाला माना जाता है। - पोर्टेबिलिटी के पक्ष में: bash हमेशा मौजूद नहीं होता (BSDs, embedded systems, minimal Docker images, OpenWRT, केवल busybox वाले सेटअप, locked-down ग्राहक मशीनें, पुराने bash वाला macOS)।
- Bourne/POSIX sh में लिखना, उन प्रणालियों पर जहाँ स्क्रिप्टें अज्ञात या विरासत प्रणालियों पर चलती हैं, पेशेवर परिपक्वता का हिस्सा बताया गया है।
- कुछ लोगों का तर्क है कि पोर्टेबिलिटी की एक लागत होती है और इसे सार्वभौमिक लक्ष्य नहीं होना चाहिए; इन-हाउस स्क्रिप्टों के लिए bashisms पर निर्भर होना ठीक है।
[, test, और [[
[,testPOSIX हैं और आमतौर पर binaries या builtins होते हैं;[[shell-specific है (bash, zsh, ksh, आदि)।- कई लोग
[की बजायtestको पसंद करते हैं ताकि यह ज़ोर दिया जा सके कि यह एक command है, syntax नहीं;[का बंद करने वाला]और दिखने में मिलती-जुलती “syntax” भ्रामक हैक मानी जाती है। - दूसरे कहते हैं कि जब आपने पहले ही Bash चुन लिया है, तो
[[बेहतर है, क्योंकि इसके semantics अधिक सुरक्षित हैं (जैसे regex, pattern matching, कम quoting pitfalls)। - कुछ लोग केवल POSIX features का उपयोग करने पर ज़ोर देते हैं, भले ही shells
[[सपोर्ट करते हों; दूसरे इसे अनावश्यक “पोर्टेबिलिटी की पूजा” कहते हैं।
आम footguns और तकनीकें
- सबसे बड़ा pitfall:
test/[के साथ unquoted variables (खाली या spaces वाले मान, single-argument behavior)। बार-बार सलाह दी जाती है: “अपनी variables को quote करो” और ShellCheck तथाset -euo pipefailजैसे tools का उपयोग करो। &&/||कोifshorthand की तरह इस्तेमाल करना लोकप्रिय है, लेकिन&&के बाद वाला command fail होने पर इसके failure semantics अलग होते हैं।testके भीतर-a/-oको अप्रचलित माना जाता है; अलग-अलग tests को&&/||से chain करना बेहतर है।- Boolean logic असुविधाजनक है: वास्तविक boolean type नहीं है; workaround के तौर पर exit codes या numeric 0/1 का उपयोग किया जाता है।
शेल कब और कब कोई दूसरी भाषा
- कई लोगों का तर्क है कि जटिल logic को “real” language (Python, Perl, Node/zx, आदि) में ले जाना चाहिए; shell glue, orchestration, और integration tests के लिए सबसे अच्छा है।
- दूसरे लोग shell का बचाव एक “real language” के रूप में करते हैं, यदि उसे अनुशासन के साथ इस्तेमाल किया जाए, लेकिन फिर भी बड़े प्रोजेक्ट्स की शुरुआत इसमें नहीं करेंगे।
मानक, GNUisms, और ecosystem की विचित्रताएँ
- POSIX से चिपके रहने बनाम GNU/Bash extensions (
pipefail, GNUgrep/sedflags, आदि) का लाभ उठाने पर बहस। - POSIX को interoperability के लिए मूल्यवान माना जाता है, लेकिन साथ ही वास्तविक दुनिया की ज़रूरतों से पीछे भी।
- विभिन्न side notes: Debian/Ubuntu पर
/bin/shके रूप में dash, macOS के BSD बनाम GNU tools, autoconf का[]के साथ विशेष व्यवहार,$_के अजीब व्यवहार, और busybox की symlink बनाम hardlink layouts।