मैं बहुत सारे टूटे हुए सीमलिंक कैसे "रिलिंक" कर सकता हूं?


54

मेरे पास एक डाइरेक्टरी ट्री है, जिसमें फाइलों के नीचे प्रतीकात्मक लिंक का एक गुच्छा है /home... हालांकि, मैं स्थानांतरित हो /homeगया हूं /mnt/homeऔर सभी सिमिलिंक को "रिलिंक" करने के लिए एक तरीका चाहिए। क्या ऐसी कार्यक्षमता मौजूद है या क्या मुझे ऐसा करने के लिए स्क्रिप्ट लिखने की आवश्यकता है?

एक उदाहरण के रूप में, मेरे पास कुछ इस तरह है:

[root@trees ~]# ls -l /mnt/home/someone/something
total 4264
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 a -> /home/someone/someotherthing/a
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 b -> /home/someone/someotherthing/b
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 c -> /home/someone/someotherthing/c
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 d -> /home/someone/someotherthing/d
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 e -> /home/someone/someotherthing/e

/mnt/home/someone/something/subdir:
total 4264
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 a -> /home/someone/someotherthing/subdir/a
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 b -> /home/someone/someotherthing/subdir/b
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 c -> /home/someone/someotherthing/subdir/c
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 d -> /home/someone/someotherthing/subdir/d
lrwxrwxrwx 1 jnet www-data      55 2011-08-07 13:50 e -> /home/someone/someotherthing/subdir/e

मुझे एक कमांड चाहिए, जो सभी सिम्लिंक पाएगी और एक ही जगह पर रिंकल होगी लेकिन /mnt/homeइसके बजाय नीचे/home

क्या ऐसी आज्ञा मौजूद है?

जवाबों:


55

प्रतीकात्मक लिंक को फिर से प्राप्त करने के लिए कोई आदेश नहीं है, आप बस इसे हटा सकते हैं और एक और एक बना सकते हैं। मान लें कि आपके पास GNU उपयोगिताओं (जैसे गैर-एम्बेडेड लिनक्स या साइगविन के तहत) है, तो आप अपने लक्ष्य द्वारा प्रतीकात्मक लिंक से मेल खाने -lnameके findलिए और readlinkलिंक की सामग्री को पढ़ने के लिए प्राथमिक का उपयोग कर सकते हैं । untested:

find /mnt/home/someone/something -lname '/home/someone/*' \
     -exec sh -c 'ln -snf "/mnt$(readlink "$0")" "$0"' {} \;

इन प्रतीकात्मक संबंधों को सापेक्ष बनाना बेहतर होगा। symlinksकई लिनक्स वितरणों में मौजूद एक सुविधाजनक छोटी उपयोगिता कहा जाता है (मूल रूप से मार्क लॉर्ड्स, जिसे अब जे। ब्रांट बकले ने बनाए रखा है)। इस कदम से पहले, या ऊपर दिए गए मान्य लिंक को पुनर्स्थापित करने के बाद, symlinks -c /mnt/home/someone/somethingजब तक कि वे एक फाइल सिस्टम सीमा को पार नहीं करते हैं, तब तक सभी पूर्ण सहसंबंधों को निर्दिष्ट सिम्बलिंक के अंतर्गत पूर्ण सहसंबंधों में परिवर्तित करने के लिए चलाते हैं ।


कोई अपराध नहीं है, यह एक महान लाइनर है, लेकिन बैश के स्ट्रिंग प्रतिस्थापन शायद कुछ जादू wrt पथ परिवर्तन कर सकता है और आसान होगा।
0xC0000022L 20

@STATUS_ACCESS_DENIED ऐसा कैसे? केवल स्ट्रिंग ऑपरेशन /mntएक पथ के लिए प्रस्तुत करना है; आप संघनन की तुलना में कोई कट्टरपंथी स्ट्रिंग ऑपरेशन की आवश्यकता है।
गिल्स एसओ- बुराई को रोकना '

@ गिल्स: क्षमा करें, मैं आपकी टिप्पणी के बारे में अधिक सोच रहा था। अपने उदाहरण के सटीक "अनुवाद" के लिए आप निश्चित रूप से सही हैं।
0xC0000022L

13

मुझे पता है कि यह बिल्कुल वैसा नहीं है जैसा कि लेखक अनुरोध कर रहा है, लेकिन ऐसा लगता है कि उनके पास पहले से ही उनका जवाब है इसलिए मैं इसे मेरे जैसे अन्य लोगों के लिए जोड़ रहा हूं जो प्रश्न पर ठोकर खाते हैं।

निम्नलिखित को मदद करनी चाहिए यदि अधिक लचीले समाधान की आवश्यकता है जैसे कि टूटी हुई प्रतीकात्मक लिंक का एक गुच्छा जो प्रतीकात्मक लिंक के लक्ष्यों का हिस्सा बदलकर तय किया जा सकता है।

जैसे। उपयोगकर्ता नाम बदलने के बाद, पुराने उपयोगकर्ता नाम को बदलने के लिए, कई लिंक के लक्ष्य में नए उपयोगकर्ता नाम के साथ, पहले से ही किया गया था। नीचे दी गई जगह-सिमलिंक नामक एक स्क्रिप्ट बनाएं:

#!/bin/bash
link=$1
# grab the target of the old link
target=$(readlink -- "$1")

# replace the first occurrence of oldusername with newusername in the target string
target=${target/oldusername/newusername}

# Test the link creation
echo ln -s -- "$target" "$link"

# If the above echo shows the correct commands are being issued, then uncomment the following lines and run the command again
#rm $link
#ln -s "$target" "$link"

और इसे निम्नलिखित कमांड के साथ कॉल करें:

find /home/newusername/ -lname '/home/oldusername/*' -exec ~/bin/replace-simlinks {} \;

आशा है कि यह किसी की मदद करेंगे

संपादित करें: इस स्क्रिप्ट पर किकस्टार्ट के लिए धन्यवाद गाइल्स और लिंक को सापेक्ष बनाने के लिए सिम्लिंक स्क्रिप्ट का उपयोग करने के बारे में टिप।


1
मुझे यह समाधान बेहतर लगता है क्योंकि यह एक स्ट्रिंग प्रतिस्थापन का उपयोग करता है, जो उन मामलों में मदद करता है जहां आपको पथ के बीच में एक फ़ोल्डर का नाम बदलना पड़ता है। यदि आवश्यक हो तो अधिक जटिल परिवर्तनों को करने के लिए संशोधित करने के लिए समाधान भी काफी आसान है।
गैलाकियो

मैं स्ट्रिंग प्रतिस्थापन के तर्कों को उद्धृत करने की सलाह दूंगा, जैसे कि ओपी के प्रश्न में पथ के लिए स्लैश का उपयोग करने के लिए किया जाना चाहिए। target=${target/"/home"/"/mnt/home"}हालांकि बहुत उपयोगी है। धन्यवाद।
वाल्टर निसेन

3

/homeएक सिम्लिंक के रूप में बनाएं /mnt/home, और सभी मौजूदा सिम्बलिंक फिर से मान्य होंगे।


2
बिंद-बढ़ते अक्सर परिदृश्यों में सहानुभूति की तुलना में कम नाजुक होते हैं जहां कार्यक्रमों को सहानुभूति के बारे में पता चलता है और इस तथ्य के आधार पर अलग-अलग कार्य करते हैं ...
0xC0000022L
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.