नोट:
* यह उत्तर संभवतः उपयोग के मामले के वारंट की तुलना में अधिक गहरा है, और find 2>/dev/nullकई स्थितियों में पर्याप्त हो सकता है। यह अभी भी एक क्रॉस-प्लेटफ़ॉर्म परिप्रेक्ष्य के लिए और कुछ उन्नत शेल तकनीकों की चर्चा के लिए एक समाधान खोजने के हित में हो सकता है जो यथासंभव मजबूत है, भले ही इसके खिलाफ लगाए गए मामले काफी हद तक काल्पनिक हो सकते हैं।
* यदि आपका सिस्टम स्थानीयकृत त्रुटि संदेशों को दिखाने के लिए कॉन्फ़िगर किया गया है , तो यह सुनिश्चित करने के लिए findनीचे LC_ALL=C( LC_ALL=C find ...) के साथ कॉल उपसर्ग करें ताकि यह सुनिश्चित हो सके कि अंग्रेजी संदेश रिपोर्ट किए गए हैं grep -v 'Permission denied'। सदा ही, हालांकि, किसी भी त्रुटि संदेश है कि है प्रदर्शित हो तो अंग्रेजी में रूप में अच्छी तरह हो जाएगा।
यदि आपका शेल bashया हैzsh , तो एक ऐसा समाधान है जो केवल POSIX- अनुरूप findसुविधाओं का उपयोग करते हुए यथोचित सरल होने के साथ मजबूत है ; जबकि bashखुद पॉसिक्स का हिस्सा नहीं है, अधिकांश आधुनिक यूनिक्स प्लेटफार्म इसके साथ आते हैं, जिससे यह समाधान व्यापक रूप से पोर्टेबल हो जाता है:
find . > files_and_folders 2> >(grep -v 'Permission denied' >&2)
नोट: एक छोटा सा मौका है कि कुछ grepआउटपुट पूर्ण होने के बाद आ सकते हैं find, क्योंकि समग्र कमांड >(...)समाप्त होने के लिए कमांड के अंदर इंतजार नहीं करता है । इसमें bash, आप | catकमांड में जोड़कर इसे रोक सकते हैं ।
>(...)एक (शायद ही कभी इस्तेमाल) है उत्पादन प्रक्रिया प्रतिस्थापन उत्पादन पुनः निर्देशित करने की अनुमति देता है कि (इस मामले में, stderr निर्गम ( 2>) कमांड के अंदर की stdin के लिए >(...)।
के अलावा bashऔर zsh, kshका समर्थन करता है उन्हें रूप में अच्छी तरह सिद्धांत रूप में , लेकिन से पुनर्निर्देशन के साथ उन्हें गठबंधन करने के लिए कोशिश कर रहा है stderr , जैसा कि यहां किया गया है ( 2> >(...)), चुपचाप नजरअंदाज किया गया (में ksh 93u+) प्रतीत होता है ।
grep -v 'Permission denied'फिल्टर बाहर ( -v) (से सभी लाइनों findआदेश के stderr स्ट्रीम) कि वाक्यांश वाले Permission deniedऔर stderr करने के लिए शेष लाइनों आउटपुट ( >&2)।
यह दृष्टिकोण है:
मजबूत : grepकेवल त्रुटि संदेशों पर लागू होता है (और फ़ाइल पथों और त्रुटि संदेशों के संयोजन के लिए नहीं, संभवत: झूठी सकारात्मकता की ओर अग्रसर होता है), और अनुमति से वंचित लोगों के अलावा त्रुटि संदेश, stderr के माध्यम से पारित किए जाते हैं।
साइड-इफ़ेक्ट फ्री : findका एक्ज़िट कोड संरक्षित है: कम से कम एक फाइल सिस्टम आइटम तक पहुँचने में असमर्थता का परिणाम एग्ज़िट कोड में मिलता है 1(हालाँकि यह आपको नहीं बताएगा कि अनुमति-अस्वीकृत लोगों के अलावा अन्य त्रुटियां हुईं (भी))।
POSIX- संगत समाधान:
पूरी तरह से POSIX- अनुरूप समाधानों में या तो सीमाएं हैं या अतिरिक्त कार्य की आवश्यकता है।
यदि findकिसी भी तरह से आउटपुट को फाइल में कैद किया जाना है (या पूरी तरह से दबा दिया गया है), तो जोनाथन लेफ़लर के उत्तर से पाइपलाइन आधारित समाधान सरल, मजबूत और पॉसिक्स-अनुरूप है:
find . 2>&1 >files_and_folders | grep -v 'Permission denied' >&2
ध्यान दें कि पुनर्निर्देश का क्रम मायने रखता है: पहले2>&1 आना चाहिए ।
एक फाइल अप फ्रंट में स्टडआउट आउटपुट को कैप्चर 2>&1करने से पाइप लाइन के माध्यम से केवल त्रुटि संदेश भेजने की अनुमति मिलती है , जो grepतब असंबद्ध रूप से काम कर सकता है।
केवल नकारात्मक पक्ष यह है कि समग्र बाहर निकलें कोड हो जाएगा grepआदेश के , नहीं findकरता है, तो देखते हैं: की, जो इस मामले में अर्थ है कोई सब या कम से त्रुटियों केवल अनुमति से इनकार त्रुटियों, बाहर निकलें कोड दिया जाएगा 1(संकेत विफलता ), अन्यथा ( अनुमति-अस्वीकृत लोगों के अलावा अन्य त्रुटियां) 0- जो इरादे के विपरीत है।
उस ने कहा, find'एग्जिट कोड' का इस्तेमाल वैसे भी कम ही किया जाता है , क्योंकि यह अक्सर गैर-मौजूद रास्ते से गुजरने जैसी मूलभूत विफलता से परे बहुत कम जानकारी देता है ।
हालाँकि, केवल कुछ का विशिष्ट मामलाइनपुट पथ अनुमतियों की कमी के कारण दुर्गम होने का है में परिलक्षित होता findहै बाहर निकलने के कोड (दोनों जीएनयू और बीएसडी में find): एक अनुमति-से इनकार त्रुटि तब होती है, तो के लिए किसी भी कार्रवाई की फाइलों की, बाहर निकलें कोड के लिए निर्धारित है 1।
निम्नलिखित भिन्नताएं संबोधित करती हैं कि:
find . 2>&1 >files_and_folders | { grep -v 'Permission denied' >&2; [ $? -eq 1 ]; }
अब, निकास कोड इंगित करता है कि क्या हुई के अलावा कोई त्रुटि है Permission denied: 1यदि हां, तो 0अन्यथा।
दूसरे शब्दों में: अब बाहर निकलने का कोड कमांड के असली इरादे को दर्शाता है: सफलता ( 0) की सूचना दी गई है, यदि कोई त्रुटि नहीं है या केवल अनुमति-अस्वीकृत त्रुटियां हुई हैं।
यह findशीर्ष पर समाधान के रूप में, केवल पासिंग एक्जिट कोड से गुजरने से बेहतर है ।
टिप्पणी में gniourf_gniourf ने परिष्कृत पुनर्निर्देशन का उपयोग करके इस समाधान के एक (अभी भी POSIX- अनुरूप) सामान्यीकरण का प्रस्ताव किया है , जो फ़ाइल पथों को stdout में प्रिंट करने के डिफ़ॉल्ट व्यवहार के साथ भी काम करता है :
{ find . 3>&2 2>&1 1>&3 | grep -v 'Permission denied' >&3; } 3>&2 2>&1
संक्षेप में: कस्टम फ़ाइल डिस्क्रिप्टर 3का उपयोग अस्थायी रूप से stdout ( 1) और Stderr ( 2) को स्वैप करने के लिए किया जाता है , ताकि अकेले त्रुटि संदेशों grepको stdout के माध्यम से पाइप किया जा सके ।
इन पुनर्निर्देशनों के बिना, डेटा (फ़ाइल पथ) और त्रुटि संदेश दोनों grepको stdout के माध्यम से पाइप किया grepजाएगा , और फिर त्रुटि संदेश Permission denied और (काल्पनिक) फ़ाइल के बीच अंतर करने में सक्षम नहीं होगा जिसका नाम वाक्यांश को समाहित करने के लिए होता हैPermission denied ।
पहले समाधान के रूप में, हालांकि, बाहर निकलने का कोड grep's नहीं find, बल्कि रिपोर्ट किया जाएगा , लेकिन इसके बाद के संस्करण के समान ही लागू किया जा सकता है।
मौजूदा उत्तरों पर नोट:
वहाँ कई बिंदुओं के बारे में नोट करने के लिए कर रहे हैं माइकल Brux के जवाब , find . ! -readable -prune -o -print:
इसके लिए जीएनयू की आवश्यकता है find; विशेष रूप से, यह macOS पर काम नहीं करेगा। बेशक, अगर आपको केवल GNU के साथ काम करने के लिए कमांड की आवश्यकता है find, तो यह आपके लिए कोई समस्या नहीं होगी।
कुछ Permission deniedत्रुटियां अभी भी सतह पर हो सकती हैं : निर्देशिकाओं find ! -readable -pruneकी बाल वस्तुओं के लिए ऐसी त्रुटियां रिपोर्ट करती हैं जिनके लिए वर्तमान उपयोगकर्ता की rअनुमति है, लेकिन कमी x(निष्पादन योग्य) अनुमति नहीं है। कारण यह है कि क्योंकि निर्देशिका ही है है पठनीय, -pruneनिष्पादित नहीं है, और उतरना करने के प्रयास में है कि निर्देशिका तो त्रुटि संदेश से चलाता है। उस ने कहा, ठेठ मामला rलापता होने की अनुमति के लिए है।
नोट: निम्नलिखित बिंदु दर्शन और / या विशिष्ट उपयोग के मामले की बात है, और आप यह तय कर सकते हैं कि यह आपके लिए प्रासंगिक नहीं है और यह कि कमांड आपकी आवश्यकताओं को अच्छी तरह से फिट बैठता है, खासकर यदि केवल रास्तों को प्रिंट करने के लिए आप सब करते हैं:
- यदि आप अनुमति-अस्वीकृत त्रुटि संदेशों के फ़िल्टरिंग को एक अलग कार्य मानते हैं, जिसे आप किसी भी
find कमांड पर लागू करने में सक्षम होना चाहते हैं , तो अनुमति-अस्वीकृत त्रुटियों को रोकने के विपरीत दृष्टिकोण को findकमांड में "शोर" शुरू करने की आवश्यकता होती है , जो यह भी बताता है जटिलता और तार्किक नुकसान ।
- उदाहरण के लिए, माइकल के जवाब (इस लेखन के अनुसार) पर सबसे अधिक मतदान वाली टिप्पणी यह दिखाने का प्रयास करती है कि एक फिल्टर सहित कमांड को कैसे बढ़ाया जाए
-name , इस प्रकार है:
find . ! -readable -prune -o -name '*.txt'
यह, हालांकि, इरादा के अनुसार काम नहीं करता है , क्योंकि अनुगामी -printकार्रवाई की आवश्यकता होती है ( इस उत्तर में एक स्पष्टीकरण पाया जा सकता है )। इस तरह की सूक्ष्मता बग का परिचय दे सकती है।
में पहली समाधान जोनाथन Leffler की जवाब , find . 2>/dev/null > files_and_folders, के रूप में वह खुद को कहा गया है, आँख बंद करके चुप्पी सभी त्रुटि संदेश (और वैकल्पिक हल, बोझिल और पूरी तरह से मजबूत नहीं है के रूप में वह यह भी बताते हैं)। व्यावहारिक रूप से बोलना , हालांकि, यह सबसे सरल समाधान है , क्योंकि आप यह मान सकते हैं कि कोई भी और सभी त्रुटियां अनुमति से संबंधित होंगी।
धुंध का जवाब , sudo find . > files_and_folders, संक्षिप्त और व्यावहारिक, लेकिन केवल के अलावा और कुछ के लिए बीमार की सलाह दी है मुद्रण फ़ाइल नाम , सुरक्षा कारणों से: क्योंकि आप के रूप में चला रहे हैं जड़ उपयोगकर्ता, "यदि आप अपने पूरे सिस्टम होने खोजने में एक बग द्वारा गड़बड़ जा रहा जोखिम या एक दुर्भावनापूर्ण संस्करण, या एक गलत आह्वान जो अप्रत्याशित रूप से कुछ लिखता है, जो सामान्य विशेषाधिकार के साथ ऐसा करने पर नहीं हो सकता है "( ट्रिपलआई द्वारा धुंध के जवाब पर एक टिप्पणी से )।
Viraptor के उत्तर में दूसरा समाधान , find . 2>&1 | grep -v 'Permission denied' > some_fileझूठी सकारात्मकता का जोखिम चलाता है (पाइपलाइन के माध्यम से stdout और stderr का मिश्रण भेजने के कारण), और, संभवतः, stderr के माध्यम से गैर- प्रवेश-अस्वीकार त्रुटियों की रिपोर्ट करने के बजाय , उन्हें आउटपुट पथ के साथ कैप्चर करता है आउटपुट फ़ाइल में।
find . 2>&1 > files_and_folders | grep -v 'Permission denied' >&2:?