PDA

Показать полную графическую версию : [BASh] Рекурсивный обход с переименованием


blackmane
18-07-2014, 17:58
Доброго дня!

Обратился пользователь с проблемой, в сетевой папке у большинства файлов с кириллическим названием слетела кодировка.

https://lh5.googleusercontent.com/-uTFQLcg-A78/U8kkwmVz_tI/AAAAAAAABIc/B-CrB2U5K0g/w706-h132-no/%25D0%25A1%25D0%25BD%25D0%25B8%25D0%25BC%25D0%25BE%25D0%25BA.PNG

Сами файлы не повреждены, только имена.
Сетевой ресурс находится на машинке с Ubuntu Server 12.04

Помучившись я пришел к такой строчке:
iconv -f utf8 -t cp437 -c

Она конвертирует из этих кракозябр в человеческий вид.
Осталось автоматизировать, с файлами проблем не возникло:

find * -type f | while read line;do
name=`echo $line| awk -F"/" '{print $NF}'`;
fname=`echo $name |iconv -f utf8 -t cp437 -c`;
dname=`echo $line | sed "s/[^/]*$//"`;
fullname="$dname$fname";
echo $fullname;
mv "$line" "$fullname";
done;

С первым уровнем папок тоже проблем не было:
find * -type d | grep -v "/" | while read line;do
name=`echo $line| awk -F"/" '{print $NF}'`;
fname=`echo $name |iconv -f utf8 -t cp437 -c`;
dname=`echo $line | sed "s/[^/]*$//"`;
fullname="$dname$fname";
echo $fullname;
mv "$line" "$fullname";
done;

А вот с вложенными увы проблема.
Число вложенных папок варьируется от 1 до 50+ и результат такого скрипта:

find * -type d | grep "/" | while read line;do
name=`echo $line| awk -F"/" '{print $NF}'`;
fname=`echo $name |iconv -f utf8 -t cp437 -c`;
dname=`echo $line | sed "s/[^/]*$//"`;
fullname="$dname$fname";
echo $fullname;
mv "$line" "$fullname";
done;

Переименование только второго уровня, изначально мне казалось что он сработает только на последний уровень.

Вся проблема в том, что при переборе переименовывается родительская папка, следовательно дочерние не доступны.
https://lh6.googleusercontent.com/-dyZEVvxOlBs/U8knRv3uTVI/AAAAAAAABIs/m6zHbw4CJUk/w500-h361-no/%25D0%25A1%25D0%25BD%25D0%25B8%25D0%25BC%25D0%25BE%25D0%25BA.PNG
А повторное использование iconv либо оставляет вообще непонятные знаки, либо файлы "исчезают" (они становятся безымянными).

Может у кого нибудь был такой опыт?

User001
21-07-2014, 09:30
convmw (https://www.j3e.de/linux/convmv/man/) посмотрите...

Еще как вариант ваш код обернуть циклами и менять кодировку начиная с максимальной глубины, но велосипед получился медленный и некрасивый :)

blackmane
22-07-2014, 12:13
convmw посмотрите... »
Спасибо, добрый человек, выручил, все получилось.
В отличии от моего варианта он выдает ошибку на имена с кодировкой отличной от указанной (-t), т.е. не делает:
А повторное использование iconv либо оставляет вообще непонятные знаки, либо файлы "исчезают" (они становятся безымянными). »
И также он выдает ошибку на такой вариант:
https://lh6.googleusercontent.com/-dyZEVvxOlBs/U8knRv3uTVI/AAAAAAAABIs/m6zHbw4CJUk/w500-h361-no/%25D0%25A1%25D0%25BD%25D0%25B8%25D0%25BC%25D0%25BE%25D0%25BA.PNG
Но с этим мы быстро справились :-)
Еще как вариант ваш код обернуть циклами и менять кодировку начиная с максимальной глубины, но велосипед получился медленный и некрасивый »
Я так и хотел сделать, вот только проблема была в том, что я не мог определить максимальную глубину.

Первый раз я допустил ошибку и прошелся по корню, благо там кириллицы не было

User001
22-07-2014, 12:25
Я так и хотел сделать, вот только проблема была в том, что я не мог определить максимальную глубину. »Ну, сначала поискать методом подсчета "/" :) Вряд ли у вас вложенность больше 10-20...




© OSzone.net 2001-2012