यह एक सवाल है कि मैं कुछ हफ्ते पहले यहां पोस्ट करने जा रहा था। टेराडॉन की तरह , मुझे समझ में आया कि .bashrcयह केवल इंटरैक्टिव बैश शेल के लिए खट्टा है , इसलिए .bashrcयह जांचने की कोई आवश्यकता नहीं होनी चाहिए कि क्या यह एक इंटरैक्टिव शेल में चल रहा है। भ्रामक रूप से, मेरे द्वारा उपयोग किए जाने वाले सभी वितरण (उबंटू, आरएचईएल और साइगविन) में कुछ प्रकार की जांच (परीक्षण $-या $PS1) थी ताकि यह सुनिश्चित किया जा सके कि वर्तमान शेल संवादात्मक है। मुझे कार्गो पंथ प्रोग्रामिंग पसंद नहीं है, इसलिए मैंने इस कोड के उद्देश्य को अपने में समझने के लिए निर्धारित किया है .bashrc।
बैश में दूरदराज के गोले के लिए एक विशेष मामला है
इस मुद्दे पर शोध करने के बाद, मुझे पता चला कि दूरस्थ गोले को अलग तरह से व्यवहार किया जाता है। जबकि गैर-इंटरएक्टिव बैश शेल सामान्य रूप ~/.bashrcसे स्टार्ट-अप पर कमांड नहीं चलाते हैं , जब शेल को रिमोट शेल द्वारा आमंत्रित किया जाता है, तो एक विशेष मामला बनाया जाता है :
बैश यह निर्धारित करने का प्रयास करता है कि यह कब नेटवर्क कनेक्शन से जुड़े अपने मानक इनपुट के साथ चलाया जा रहा है, जब दूरस्थ शेल डेमॉन द्वारा निष्पादित किया जाता है, आमतौर पर rshd, या सुरक्षित शेल डेमॉन sshd। यदि बैश यह निर्धारित करता है कि यह इस तरह से चलाया जा रहा है, तो यह ~ / .bashrc से कमांड पढ़ता है और निष्पादित करता है, यदि वह फाइल मौजूद है और पढ़ने योग्य है। यदि ऐसा किया जाता है तो यह ऐसा नहीं करेगा sh। --norcविकल्प इस व्यवहार को बाधित करने के लिए इस्तेमाल किया जा सकता है, और --rcfileविकल्प अन्य फ़ाइल पढ़ने के लिए मजबूर करने के लिए इस्तेमाल किया जा सकता, लेकिन न तो rshdहै और न ही sshdआम तौर पर उन विकल्पों के साथ खोल आह्वान या उन्हें निर्दिष्ट करने की अनुमति देते हैं।
उदाहरण
रिमोट की शुरुआत में निम्नलिखित डालें .bashrc। (यदि परीक्षण के दौरान इसे अस्थायी रूप से अक्षम कर दिया .bashrcजाता है .profileया .bash_profile:
echo bashrc
fun()
{
echo functions work
}
स्थानीय रूप से निम्न आदेश चलाएँ:
$ ssh remote_host 'echo $- $0'
bashrc
hBc bash
- कोई
iमें $-इंगित करता है कि खोल है गैर-सहभागी ।
- कोई अग्रणी
-में $0इंगित करता है कि खोल एक है लॉगिन खोल ।
रिमोट में परिभाषित शेल फ़ंक्शन .bashrcभी चलाए जा सकते हैं:
$ ssh remote_host fun
bashrc
functions work
मैंने देखा है कि ~/.bashrcहै केवल जब एक आदेश के लिए तर्क के रूप में निर्दिष्ट किया जाता है sourced ssh। यह समझ में आता है: जब sshएक नियमित लॉगिन खोल शुरू करने के लिए उपयोग किया जाता है, .profileया .bash_profileचलाया जाता है (और .bashrcकेवल इन फ़ाइलों में से एक द्वारा स्पष्ट रूप से किए जाने पर खट्टा हो जाता है)।
मुख्य .bashrc(गैर-संवादात्मक) रिमोट कमांड चलाने के दौरान मुख्य लाभ यह हो सकता है कि शेल फ़ंक्शन चलाए जा सकते हैं। हालांकि, एक ठेठ में अधिकांश कमांड .bashrcकेवल एक इंटरैक्टिव शेल में प्रासंगिक होते हैं, उदाहरण के लिए, एलियास का विस्तार नहीं किया जाता है जब तक कि शेल इंटरैक्टिव नहीं होता है।
दूरस्थ फ़ाइल स्थानांतरण विफल हो सकता है
यह जब एक समस्या आमतौर पर नहीं है rshया sshएक इंटरैक्टिव लॉगिन खोल या जब गैर-सहभागी गोले आदेशों को चलाने के लिए किया जाता है शुरू करने के लिए उपयोग किया जाता है। हालाँकि, यह प्रोग्राम के लिए एक समस्या हो सकती हैrcp , जैसे कि scpऔर डेटा ट्रांसफर करने के लिए रिमोट शेल काsftp उपयोग करें ।
यह पता चलता है कि रिमोट उपयोगकर्ता का डिफ़ॉल्ट शेल (जैसे बाश) scpकमांड का उपयोग करते समय अंतर्निहित है । मैन पेज में इसका कोई उल्लेख नहीं है - केवल एक उल्लेख है जो इसके डेटा ट्रांसफर के लिए scpउपयोग करता है ssh। इसका परिणाम यह होता है कि यदि .bashrcमानक आउटपुट पर प्रिंट करने वाली कोई भी कमांड होती है, तो फ़ाइल स्थानांतरण विफल हो जाएगा , उदाहरण के लिए,
त्रुटि के बिना scp विफल ।
15 साल पहले की इस संबंधित Red Hat बग रिपोर्ट को भी देखें, जब / / etc / bashrc (जो अंततः के रूप में बंद हो गया था WONTFIX) में एक इको कमांड है तो scp टूट जाता है ।
क्यों scpऔर sftpअसफल
एससीपी (सिक्योर कॉपी) और एसएफटीपी (सिक्योर फाइल ट्रांसफर प्रोटोकॉल) स्थानीय और दूरस्थ छोरों के लिए फाइल (एस) हस्तांतरित होने के बारे में जानकारी का आदान-प्रदान करने के लिए अपने स्वयं के प्रोटोकॉल हैं। दूरस्थ छोर से कोई भी अनपेक्षित पाठ प्रोटोकॉल के हिस्से के रूप में (गलत तरीके से) व्याख्या किया गया है और हस्तांतरण विफल रहता है। घोंघा किताब से एक FAQ के अनुसार
क्या अक्सर ऐसा होता है, हालांकि, वहाँ सर्वर पर या तो सिस्टम में बयान या प्रति-उपयोगकर्ता खोल स्टार्टअप फ़ाइलें (हैं कि .bashrc, .profile,
/etc/csh.cshrc, .login, आदि) जो प्रवेश पर उत्पादन पाठ संदेश, इरादा तरह मनुष्य के द्वारा पढ़ा जा करने के लिए ( fortune, echo "Hi there!", आदि।)।
इस तरह के कोड को केवल इंटरेक्टिव लॉगिन पर आउटपुट का उत्पादन करना चाहिए, जब
ttyमानक इनपुट से जुड़ा होता है। यदि यह इस परीक्षण को नहीं करता है, तो यह इन पाठ संदेशों को सम्मिलित करेगा जहां वे नहीं हैं: इस मामले में scp2/ sftpऔर के बीच प्रोटोकॉल स्ट्रीम को प्रदूषित कर रहा है sftp-server।
शेल स्टार्टअप फाइलें बिल्कुल प्रासंगिक हैं, इसका कारण यह है कि sshd
उपयोगकर्ता की ओर से किसी भी कार्यक्रम को शुरू करते समय उपयोगकर्ता के शेल को नियोजित किया जाता है
(उदाहरण के लिए / बिन / sh -c "कमांड")। यह एक यूनिक्स परंपरा है, और इसके फायदे हैं:
- रिमोट कमांड चलाने पर उपयोगकर्ता का सामान्य सेटअप (कमांड उपनाम, पर्यावरण चर, umask, आदि) प्रभावी होते हैं।
- किसी खाते के शेल को / बिन / झूठ को अक्षम करने की सामान्य प्रथा से इसे अक्षम करने से मालिक को किसी भी आदेश को चलाने से रोका जा सकता है, प्रमाणीकरण को अभी भी किसी कारण से गलती से सफल होना चाहिए।
एससीपी प्रोटोकॉल विवरण
एससीपी कैसे काम करता है, इसके विवरण में रुचि रखने वालों के लिए, मुझे दिलचस्प जानकारी मिली कि एससीपी प्रोटोकॉल कैसे काम करता है, जिसमें दूरस्थ पक्ष पर बातूनी खोल प्रोफाइल के साथ रनिंग एसपीपी पर विवरण शामिल हैं ? :
उदाहरण के लिए, यह हो सकता है यदि आप इसे दूरस्थ सिस्टम पर अपने शेल प्रोफाइल में जोड़ते हैं:
गूंज ""
यह सिर्फ लटका क्यों है? इस तरह से आता है कैसे scpमें स्रोत मोड पहले प्रोटोकॉल संदेश की पुष्टि के लिए इंतजार कर रहा है। यदि यह द्विआधारी 0 नहीं है, तो यह उम्मीद करता है कि यह एक दूरस्थ समस्या की सूचना है और नई लाइन आने तक त्रुटि संदेश बनाने के लिए अधिक वर्णों की प्रतीक्षा करता है। चूंकि आपने पहले एक के बाद एक और नई लाइन नहीं छापी थी, इसलिए आपका स्थानीय scpबस लूप में बंद रहता है read(2)। इस बीच, रिमोट प्रोफाइल पर शेल प्रोफाइल संसाधित होने के बाद, scpसिंक मोड शुरू किया गया था, जो कि ब्लॉक भी करता है read(2), डेटा ट्रांसफर की शुरुआत को दर्शाते हुए एक बाइनरी शून्य की प्रतीक्षा करता है।
निष्कर्ष / TLDR
एक ठेठ में अधिकांश बयान .bashrcकेवल एक इंटरैक्टिव शेल के लिए उपयोगी होते हैं - जब दूरस्थ कमांड के साथ rshया नहीं चल रहा हो ssh। ऐसी अधिकांश स्थितियों में, शेल चरों, उपनामों और परिभाषित कार्यों की स्थापना वांछित नहीं है - और किसी भी पाठ को मानक रूप से प्रिंट करना सक्रिय रूप से हानिकारक है यदि प्रोग्राम जैसे scpया का उपयोग करके फ़ाइलों को स्थानांतरित करना sftp। मौजूदा शेल गैर-इंटरैक्टिव होने की पुष्टि करने के बाद बाहर निकलना सबसे सुरक्षित व्यवहार है .bashrc।