(बैश) स्क्रिप्ट ए, स्क्रिप्ट बी का इंतजार करें, लेकिन इसकी बाल प्रक्रिया नहीं


9

इसलिए मेरे पास स्क्रिप्ट है जो करता है:

ssh server1 -- scriptB &
ssh server2 -- scriptB &
ssh server3 -- scriptB &
wait
otherstuffhappens

ScriptB करता है:

rsync -av /important/stuff/. remoteserver:/remote/dir/.
rsync -av /not/so/important/stuff/. remoteserver:/remote/dir/. &
exit

मेरा वांछित परिणाम है scriptA स्क्रिप्टबी के सभी उदाहरणों के लिए आगे बढ़ने से पहले खत्म होने का इंतजार करेगा, जो कि वर्तमान में करता है, हालांकि यह पृष्ठभूमि के rsyncs के लिए भी इंतजार कर रहा है इतना महत्वपूर्ण सामान नहीं है। ये बड़ी फाइलें हैं जिन पर मैं इंतजार नहीं करना चाहता।

मैंने नोह के बीच अंतर के माध्यम से पढ़ा है , डिसाइड किया और & विभिन्न संयोजनों की कोशिश की, लेकिन मुझे वह परिणाम नहीं मिल रहा है जिसकी मुझे तलाश है।

इस बिंदु पर मैं बहुत स्टम्प्ड हूं। किसी भी सहायता की सराहना की जाएगी!

जवाबों:


15

यहां समस्या यह है कि sshdपाइप पर एंड-ऑफ-फाइल की प्रतीक्षा करता है यह कमांड के स्टडआउट को पढ़ रहा है (किसी कारण से स्टेडर नहीं, कम से कम उस संस्करण के साथ जिस पर मैं परीक्षण कर रहा हूं)। और पृष्ठभूमि नौकरी उस पाइप के लिए एक fd विरासत में मिली।

तो, उस के आसपास काम करने के लिए, उस पृष्ठभूमि rsyncकमांड के आउटपुट को कुछ फ़ाइल पर रीडायरेक्ट करें या /dev/nullयदि आप इसकी परवाह नहीं करते हैं। आपको stderr को पुनर्निर्देशित भी करना चाहिए, क्योंकि भले ही sshd संबंधित पाइप की प्रतीक्षा नहीं कर रहा है, sshdबाहर निकलने के बाद , पाइप टूट rsyncजाएगा इसलिए इसे stderr पर लिखने की कोशिश करने पर उसे मार दिया जाएगा।

इसलिए:

rsync ... > /dev/null 2>&1 &

की तुलना करें:

$ time ssh localhost 'sleep 2 &'
ssh localhost 'sleep 2 &'  0.05s user 0.00s system 2% cpu 2.365 total
$ time ssh localhost 'sleep 2 > /dev/null &'
ssh localhost 'sleep 2 > /dev/null &'  0.04s user 0.00s system 12% cpu 0.349 total

तथा:

$ ssh localhost '(sleep 1; ls /x; echo "$?" > out) > /dev/null &'; sleep 2; cat out
141  # ls by killed with SIGPIPE upon writing the error message
$ ssh localhost '(sleep 1; ls /x; echo "$?" > out) > /dev/null 2>&1 &'; sleep 2; cat out
2    # ls exited normally after writing the error on /dev/null instead
     # of a broken pipe

4

एक स्क्रिप्ट लिखें जो दोनों के माता-पिता हैं, फिर आप दोनों को आसानी से नियंत्रित कर सकते हैं । वैकल्पिक रूप से दो चैनलों के बीच एक संचार चैनल स्थापित करें

विशेष रूप से कुछ पृष्ठभूमि नौकरियों को अनदेखा करने के लिए आप पीआईडी ​​पर कब्जा कर सकते हैं ( $!अंतिम पृष्ठभूमि वाली नौकरी पीआईडी ​​है) और wait $pidकेवल उस नौकरी के पूरा होने का इंतजार करने के लिए।


3

-fकरने के लिए ध्वज sshफिक्स समस्या। पर परीक्षण किया गया:

#!/bin/sh -e
echo $$_script__begin
( echo sleeping; sleep 2; echo slept )&
echo $$_script__end

जब मैं इसे चलाता हूं ssh localhost ./script, तब तक इंतजार करता है जब तक कि sleptपता नहीं चलता। -fध्वज के साथ , यह बाहर निकलता है echo $$_script__endऔर sleptबाद में sshकमांड के वापस आने के बाद पृष्ठभूमि में दिखाई देता है ।


2

यह OpenSSH सर्वर की एक ज्ञात समस्या है, जो कि अपस्ट्रीम Bugzilla # 2071 में वर्णित और चर्चित है । बग में, ओपनएसएसएच पक्ष में या तो स्क्रिप्ट के लिए कई वर्कअराउंड प्रस्तावित हैं।

आप स्क्रिप्ट के उत्पादन के लिए प्रतीक्षा करने के लिए चाहते हैं, तो आप एक जोड़ने चाहिए waitसे पहले exitकी scriptBभी।

यदि आप आउटपुट के बारे में परवाह नहीं करते हैं, nohupऔर IO पुनर्निर्देशन के कुछ भिन्नरूपों का उपयोग करते हैं /dev/null, जो समस्या को उसी तरह हल करेगा।


1

आप यह कोशिश कर सकते हैं। $!डिफ़ॉल्ट शेल वैरिएबल है जिसमें हाल ही में निष्पादित पृष्ठभूमि पाइपलाइन / प्रक्रिया की प्रक्रिया आईडी शामिल है।

command1 &
lpid1=$!

command2 &
lpid2=$!

command3 &
lpid=$!

wait $lpid1  # waits for only the process with PID lpid1  to complete. 

आपको exportचर आदि का उपयोग करके इसे अपनी स्क्रिप्ट के अनुसार उपयोग करने की आवश्यकता है


1

B को केवल अपनी पृष्ठभूमि प्रक्रियाओं के लिए प्रतीक्षा करने की आवश्यकता है:

rsync -av /important/stuff/. remoteserver:/remote/dir/.
rsync -av /not/so/important/stuff/. remoteserver:/remote/dir/. &
wait
exit

उस बिंदु पर आप पृष्ठभूमि में दूसरा rsync नहीं चला सकते हैं और waitपूरी तरह से उपयोग करने से बच सकते हैं। हालांकि मैं अनुमान लगा रहा हूं कि ओपी का मतलब क्या था, दोनों rsyncप्रक्रियाओं को समानांतर में चलाया गया , जिसका मतलब होगा कि उन दोनों को (साथ &) और फिर उपयोग करना wait। किसी भी मामले में, मैं सहमत हूं कि यह समस्या को ठीक करने का सबसे सीधा तरीका है और वह है जो मैं प्रश्न में जानकारी के आधार पर चुनूंगा।
डेविड
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.