अमान्य एन्कोडिंग या अमान्य एन्कोडेड वर्णों के साथ फ़ाइलों का नाम बदलने के लिए कैसे?


16

मेरे पास एक डेबियन सर्वर है और मैं एक इंटरनेट रेडियो स्टेशन के लिए संगीत की मेजबानी कर रहा हूं। मुझे फ़ाइल नामों और रास्तों से परेशानी है क्योंकि बहुत सारी फ़ाइलों को एक अवैध एन्कोडिंग मिली है, उदाहरण के लिए:

./music/Bändname - Some Title - additional Info/B�ndname - 07 - This Title Is Cörtain, The EncÃding Not.mp3

आदर्श रूप से, मैं उन सभी चीजों को हटाना चाहूंगा जो अक्षर A-Z/ a-zया संख्या 0-9या डैश -/ अंडरस्कोर नहीं हैं _... परिणाम कुछ इस तरह दिखना चाहिए:

./music/Bndname-SomeTitle-additionalInfo/Bndname-07-ThisTitleIsCrtain,TheEncdingNot.mp3

बहुत सारी फ़ाइलों और निर्देशिकाओं के एक बैच के लिए इसे कैसे प्राप्त करें?

मैंने इस तरह के सवाल को देखा है: विशेष पात्रों के साथ फ़ाइलों का नाम बदलना (या सही ढंग से प्रदर्शित)

लेकिन यह केवल एन्कोडिंग को ठीक करता है, मैं ऊपर वर्णित अनुसार अधिक सख्त दृष्टिकोण पसंद करूंगा।

जवाबों:


14

यदि आप एक ही समय में फ़ाइलों और निर्देशिकाओं का नाम बदलना चाहते हैं, तो आप कुछ समस्याओं में भाग लेंगे । सिर्फ एक फ़ाइल का नाम बदलना काफी आसान है। लेकिन आप यह सुनिश्चित करना चाहते हैं कि निर्देशिकाओं का भी नाम बदला जाए। आप बस नहीं कर सकते हैं mv Motörhead/Encöding Motorhead/Encodingके बाद से Motorheadकॉल के समय मौजूद नहीं होंगे।

इसलिए, हमें सभी फ़ाइलों और फ़ोल्डरों की गहराई-पहले ट्रैवर्सल की आवश्यकता है, और फिर केवल वर्तमान फ़ाइल या फ़ोल्डर का नाम बदलें। निम्नलिखित findमेरे OS X पर GNU और बैश 4.2.42 के साथ काम करता है।

#!/usr/bin/env bash
find "$1" -depth -print0 | while IFS= read -r -d '' file; do
  d="$( dirname "$file" )"
  f="$( basename "$file" )"
  new="${f//[^a-zA-Z0-9\/\._\-]/}"
  if [ "$f" != "$new" ]      # if equal, name is already clean, so leave alone
  then
    if [ -e "$d/$new" ]
    then
      echo "Notice: \"$new\" and \"$f\" both exist in "$d":"
      ls -ld "$d/$new" "$d/$f"
    else
      echo mv "$file" "$d/$new"      # remove "echo" to actually rename things
    fi
  fi
done

new="${f//[\\\/\:\*\?\"<>|]/}"यदि आप ऐसी किसी भी चीज़ को बदलना चाहते हैं, जिसे आप नहीं संभाल सकते हैं, तो आप रेगेक्स को बदल सकते हैं।

इस स्क्रिप्ट को इस रूप में सहेजें rename.sh, इसे निष्पादन योग्य बनाएं chmod +x rename.sh। फिर, इसे कॉल करें rename.sh /some/path

किसी भी फ़ाइल नाम टकराव (" Notice" घोषणाओं) को हल करना सुनिश्चित करें ।

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

सुरक्षित होने के लिए, मैं इसे पहले फाइलों के एक छोटे उपसमुच्चय पर परीक्षण करने की सलाह दूंगा।


विकल्प समझाया

यह बताने के लिए कि यहाँ क्या होता है:

  • -depthयह सुनिश्चित करेगा कि निर्देशिकाओं की गहराई-पहले पुनरावृत्ति की जाए, इसलिए हम अंत से सब कुछ "रोल अप" कर सकते हैं। आमतौर पर, findअलग-अलग तरीके से पता चलता है (लेकिन चौड़ाई पहले नहीं)।
  • -print0यह सुनिश्चित करता है कि findआउटपुट शून्य-सीमांकित है, इसलिए हम इसे चर read -d ''में पढ़ सकते हैं file। ऐसा करने से हमें सभी प्रकार के अजीब फ़ाइल नामों से निपटने में मदद मिलती है, जिनमें रिक्त स्थान और यहां तक ​​कि नए अंक भी शामिल हैं।
  • हमें फ़ाइल की निर्देशिका मिल जाएगी dirname। हमेशा अपने चर को ठीक से उद्धृत करने के लिए मत भूलना, अन्यथा रिक्त स्थान या गोलाकार पात्रों के साथ कोई भी पथ इस स्क्रिप्ट को तोड़ देगा।
  • हमें वास्तविक फ़ाइल नाम (या निर्देशिका नाम) मिलेगा basename
  • फिर, हम $fबैश की स्ट्रिंग प्रतिस्थापन क्षमताओं का उपयोग करने से किसी भी अमान्य चरित्र को हटाते हैं । अमान्य का मतलब है कि कुछ भी नहीं- या अपरकेस अक्षर, एक अंक, एक स्लैश ( \/), एक डॉट ( \.), एक अंडरस्कोर, या एक माइनस-हाइफ़न।
  • यदि $fपहले से ही साफ है (साफ किया गया नाम वर्तमान नाम के समान है), तो इसे छोड़ दें।
  • यदि $newपहले से ही निर्देशिका में मौजूद है $d(उदाहरण के लिए, आपके पास नाम resumeऔर résuméउसी निर्देशिका में फ़ाइलें हैं ), तो चेतावनी जारी करें। आप इसका नाम नहीं बदलना चाहते, क्योंकि, कुछ सिस्टम पर, mv foo fooसमस्या का कारण बनता है। अन्यथा,
  • हम अंततः मूल फ़ाइल (या निर्देशिका) को उसके नए नाम में बदल देते हैं

इस के बाद से ही गहरी पदानुक्रम पर कार्य करेगा, का नाम बदलने Motörhead/Encödingके लिए Motorhead/Encodingदो चरणों में किया जाता है:

  1. mv Motörhead/Encöding Motörhead/Encoding
  2. mv Motörhead Motorhead

यह सुनिश्चित करता है कि सभी प्रतिस्थापन सही क्रम में किए गए हैं।


उदाहरण फ़ाइलें और परीक्षण रन

चलो एक बेस फ़ोल्डर में कुछ फ़ाइलों को कहते हैं test:

test
test/Motörhead
test/Motörhead/anöther_file.mp3
test/Motörhead/Encöding
test/Randöm
test/Täst
test/Täst/Töst
test/with space
test/with-hyphen.txt
test/work
test/work/resume
test/work/résumé
test/work/schedule

यहाँ डिबग मोड में एक रन से आउटपुट है ( echoसामने के साथ mv), यानी, कमांड्स जिन्हें कहा जाएगा, और टकराव की चेतावनी:

mv test/Motörhead/anöther_file.mp3 test/Motörhead/another_file.mp3
mv test/Motörhead/Encöding test/Motörhead/Encoding
mv test/Motörhead test/Motorhead
mv test/Randöm test/Random
mv test/Täst/Töst test/Täst/Tost
mv test/Täst test/Tast
mv test/with space test/withspace
Notice: "resume" and "résumé" both exist in test/work:
-rw-r—r--  …  …  test/work/resume
-rw-r—r--  …  …  test/work/résumé

सूचना के लिए गए संदेशों के अभाव with-hyphen.txt, scheduleहै, और testअपने आप में।


1
आप उस मामले को संभालने के लिए तर्क जोड़ना चाह सकते हैं जहां mvपहले से मौजूद है, जो तब हो सकता है (1) यदि आपके पास पहले से साफ (परिणामस्वरूप mv foo foo), या (2) फाइलें हैं, तो आपके पास एक ही नाम वाली फाइलें हैं विशेष वर्णों के लिए (उदाहरण के लिए mv Encöding Encoding, जहां आपके पास पहले से ही एक Encodingफ़ाइल है Encöding)।
स्कॉट

अच्छा विचार है, धन्यवाद। उस मामले में क्या करना है पर कोई विशेष सुझाव? दी गई - पहले की तुलना में इसे साफ और सेंस तरीके से हासिल करना कठिन है। यदि आपके पास कुछ है, तो निःसंकोच संपादित करें।
19

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

+1 को "एनकोडिंग" के साथ उदाहरण का उपयोग करने के लिए बहुत ज्यादा! :-)
मार्सेल

तीन साल बाद भी मैं यहां वापस आ गया हूं। इतना उपयोगी! :-)
अफ्र

15

मुझे पता है कि यह वही नहीं है जो आप चाहते थे, लेकिन अगर आप मूल एन्कोडिंग को जानते हैं, तो शायद आप convmvएन्कोडिंग को यूटीएफ -8 में बदल सकते हैं , जिससे अधिकांश समस्याओं को ठीक करना चाहिए।

यह मेरे लिए कुछ अमान्य एन्कोडेड पोलिश फ़ाइलनाम वाले फ़ोल्डर पर काम करता है:

convmv -f cp1250 -t utf8 -r .

ध्यान दें कि यह आदेश वास्तव में कुछ भी नहीं बदलता है; --notestफ़ाइलों को वास्तव में नाम बदलने का विकल्प जोड़ें ।


1
उन लोगों के लिए जिनके पास एक स्थिर सेट है (या वर्णों का एक विविध मिश्रण नहीं है), convmvविकल्प आश्चर्यजनक सरल और परिपूर्ण है। ओपी के लिए, वर्णों की संभावित भीड़ होने पर, इसे दूसरे उत्तर के साथ मिलाया जा सकता है, क्योंकि convmvयह पता लगता है कि यह कब या कब सही प्रारूप का सामना नहीं करता है। चरस के माध्यम से पाशन के माध्यम से convmv --list, एक उन्हें ठीक से इनकोडिंग मिलेगा।

1
इसका मतलब है, अगर, ओपी के रूप में, डेबियन सर्वर चलाता है, तो निश्चित रूप से इन दिनों UTF8 मान जाएगा, इस स्थिति में, कोई भी मूल पत्र रख सकता है। मेरे पास कुछ नॉर्डिक वर्णों का एक फ़ोल्डर था, और उपयोग किया जाता था: convmv -t utf8 --nfc -f iso-8859-1 --notest -r .- यह --nfcओएस एक्स के आगे लिनक्स के अनुरूप था, इसलिए, टाइप convmvकरने से उपयोगी (उपयोगी) विकल्प मिलते हैं।

0

मुझे पता है, आपने नाम बदलने के बारे में पूछा।

लेकिन आप MusicBrainz Picard जैसे सॉफ़्टवेयर का उपयोग करके समस्या को आसानी से चकमा दे सकते हैं ।

यह संगीत (ऑडियो फ़िंगरप्रिंटिंग) की पहचान करने में सक्षम है, विशाल म्यूज़िकब्रेनज़ डेटाबेस से सभी आवश्यक डेटा (कवर छवियां, जहां उपलब्ध है) डाउनलोड कर रहा है और फ़ाइलों को इधर-उधर ले जा रहा है ताकि आपका संग्रह आपके पसंद के किसी भी पैटर्न को फिट कर सके। मैं इसे सालों से इस्तेमाल कर रहा हूँ और यह हमेशा साइरिलिक से लेकर अरबी तक किसी भी चीज़ के साथ पूरी तरह से काम करता है; और निश्चित रूप से (कम से कम लैटिन-आधारित लिपियों के लिए) यह ASCII में रूपांतरण भी कर सकता है।

इस दृष्टिकोण के साथ यह वास्तव में मायने नहीं रखता है कि आपके संग्रह को वास्तव में कितना गड़बड़ / बुरी तरह से नामित किया गया है, जब तक कि फाइलें पठनीय और पूर्ण नहीं होती हैं।

(क्या मैंने इसका उल्लेख मुफ्त में किया है? दोनों मुफ्त भाषण में और मुफ्त बीयर में दोनों सॉफ्टवेयर और डेटाबेस ..?)

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