किसी निर्देशिका या फ़ाइल का स्वामी ढूंढें, लेकिन केवल वही लौटाएं और कुछ नहीं


62

मैं एक ऐसी कमांड की तलाश कर रहा हूं, जो एक डायरेक्टरी के मालिक को लौटाए और केवल वही - जैसे कि रीजैक्स ls -latकमांड को पार्स करने या कुछ इसी तरह का? मैं दूसरी स्क्रिप्ट में परिणाम का उपयोग करना चाहता हूं।

जवाबों:


102

stat से GNU coreutils ऐसा कर सकते हैं:

stat -c '%U' /path/of/file/or/directory

दुर्भाग्य से, के कई संस्करण हैं stat, और उनके सिंटैक्स में बहुत अधिक स्थिरता नहीं है। उदाहरण के लिए, FreeBSD पर, यह होगा

stat -f '%Su' /path/of/file/or/directory

यदि पोर्टेबिलिटी एक चिंता का विषय है, तो आप शायद बेहतर कर रहे हैं का उपयोग कर गाइल्स के सुझाव के संयोजन के lsऔर awk। इसे एक के बजाय दो प्रक्रियाएं शुरू करनी होंगी, लेकिन इसमें केवल POSIX- मानक कार्यक्षमता का उपयोग करने का लाभ है:

ls -ld /path/of/file/or/directory | awk '{print $3}'

2
स्टेट -c% U / पाथ, यदि संक्षिप्तता एक बोनस है।
tsvallender

1
वह GNU स्टेट मानती है, जो पुराने Linux सिस्टम पर नहीं है (यहां तक ​​कि नए सिस्टम पर भी मैं सावधान रहूंगा, उपयोगकर्ता के घर statमें /usr/local/binया कहीं और एक अलग (साइट-वाइड मानक) हो सकता है , और शायद ही कभी उपलब्ध हो। अन्य यूनियनों पर।
गिल्स

1
stat -c %Uअगर कार्यभारstat संकलित है , तो बिजीबॉक्स के साथ काम करने का भी फायदा है।
गिल्स

1
अच्छा, अंतिम उदाहरण (ls) यूनिक्स / OSX और लिनक्स दोनों पर काम करता है
kenorb

1
ध्यान दें कि अगर कोई स्थानीय उपयोगकर्ता स्वामी से मेल नहीं खाता है (तो, नेटवर्क शेयर पर), लेकिन stat -c '%U' DIRप्रिंट करेगा UNKNOWN, जो कि कम सहायक या अधिक उपयुक्त है, इस पर निर्भर करता है कि आप इसे कैसे देखते हैं।
basic6

18

के उत्पादन को पार्स करना lsशायद ही कभी एक अच्छा विचार है , लेकिन पहले कुछ क्षेत्रों को प्राप्त करना एक अपवाद है, यह वास्तव में सभी "पारंपरिक" यूनियनों पर काम करता है (यह कुछ विंडोज कार्यान्वयन जैसे प्लेटफार्मों पर काम नहीं करता है जो उपयोगकर्ता नामों में रिक्त स्थान की अनुमति देते हैं)।

ls -ld /path/to/directory | awk 'NR==1 {print $3}'

एक अन्य विकल्प एक statकमांड का उपयोग करना है , लेकिन statशेल से समस्या यह है कि अलग-अलग सिंटैक्स के साथ कई कमांड हैं, इसलिए statशेल स्क्रिप्ट में अनपोर्टेबल (लिनक्स इंस्टॉलेशन के पार भी) है।

ध्यान दें कि किसी दिए गए उपयोगकर्ता का परीक्षण एक अलग प्रस्ताव है या नहीं।

if [ -n "$(find . -user "$username" -print -prune -o -prune)" ]; then
  echo "The current directory is owned by $username."
fi
if [ -n "$(find . -user "$(id -u)" -print -prune -o -prune)" ]; then
  echo "The current directory is owned by the current user."
fi

वहाँ ls | awkभी दुर्भाग्य से दृष्टिकोण के साथ कुछ caveats हैं , जैसा कि मैंने यहां नोट किया है । मैं अभी तक के लिए एक समाधान के साथ नहीं आया है, "लक्ष्य फ़ाइल / डीआईआर एक अलग नाम के साथ एक सहिष्णु है," मुद्दा मैंने अपनी हालिया टिप्पणी में उल्लेख किया है।
रिपोर्टर जूल

इसके बजाय find . -user "$username" -print -prune -o -pruneआप बस कर सकते हैंfind . -maxdepth 0 -user "$username"
निकल्स होल्म

@ गिल्स क्या कोई कारण है जो आप awk 'NR==1 {print $3}'सिर्फ के बजाय उपयोग करते हैं awk '{print $3}'? मुझे यकीन नहीं है कि NR==1यहाँ क्यों आवश्यक है।
हेरोल्ड फिशर

1
@ हेरोल्डफिशर केवल एक किनारे के मामले में जहां पथ में एक नई रेखा होती है। यह शायद ही कभी आवश्यक है, लेकिन कभी हानिकारक नहीं है।
गिल्स

@ गिल्स को जानकर बहुत अच्छा लगा !! बस जिज्ञासु, क्या आप इसे लागू करने के बारे में जानते हैं lsजहां एक मार्ग में एक नई रेखा दो में विभाजन को विभाजित करती है (जो मुझे लगता है कि वह किनारे का मामला है जिसे आप कवर करने की कोशिश कर रहे हैं)? जीएनयू पर ls(काफ़ी नया संस्करण), बिजीबॉक्स lsऔर FreeBSD lsएक नई पंक्ति के रूप में दिया जाता है $'\n', ?और ?क्रमश:।
हेरोल्ड फिशर

9

GNU खोज के साथ भी कोई ऐसा कर सकता है:

find $directoryname -maxdepth 0 -printf '%u\n'

यह जीएनयू प्रणाली के बाहर पोर्टेबल नहीं है, लेकिन मुझे लिनक्स वितरण खोजने में आश्चर्य होगा जहां यह काम नहीं करता है।


1
यह हर गैर-एम्बेडेड लिनक्स सिस्टम और कुछ अन्य (जैसे Cygwin) पर काम करता है। एंबेडेड सिस्टम में बिजीबॉक्स होने की संभावना है , जिनके findपास नहीं है -printf
गाइल्स

जैसा मैंने कहा, GNU सिस्टम।
mattdm

GNU कोरुटिल्स (जैसे FreeBSD) के बिना सिस्टम नहीं है -printf:-(?
pevik

@pevik हाँ, जैसा मैंने कहा, अभी भी। लेकिन आप जीएनयू को स्थापित कर सकते हैं यदि आपको इसकी आवश्यकता है। :)
Mattdm

। @mattdm:। हमेशा नहीं :-( सबसे महत्वपूर्ण बात है जब आप स्क्रिप्ट लिखने जो पोर्टेबल होना चाहिए
pevik

2

शुद्ध बैश में आप lsएक सरणी और इंडेक्स के आउटपुट को इसमें परिवर्तित कर सकते हैं ।

# (lrwxr-xr-x, 1, myuser, staff, 36, Oct, 21, 16:36, /path/to/file)    
file_meta=($(ls -ld /path/to/file))
file_owner="${file_meta[2]}" # myuser

यह का उपयोग कर के रूप में के रूप में सुंदर नहीं है stat, findया awkहै, लेकिन एक चुटकी में काम कर सकता था।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.