модуль iconv (для использования с rsync), чтобы избежать недопустимых для Windows имен файлов в локальном разделе NTFS

Вопрос или проблема

Я хотел бы локально прикрепить объем NTFS к своему компьютеру под управлением Unix (Ubuntu) и скопировать (реплицировать) некоторые директории Unix на него, используя rsync, так, чтобы результат был читаем под Windows.

Меня не интересует владение и разрешения. Было бы хорошо, если бы даты модификации сохранялись. Мне нужны только директории и файлы (символические ссылки тоже было бы неплохо; но если их нельзя скопировать, это не проблема).

Две очевидные проблемы: чувствительность к регистру и символы, которые являются запрещенными в именах файлов Windows. Например, в Linux я могу иметь два файла “a” и “A”; я могу скопировать их на объем NTFS, но в Windows я смогу получить доступ (возможно?) только к одному из них. Но я готов игнорировать эту проблему. Меня интересуют запрещенные символы в именах файлов Windows, которые это <,>,:,”,/,\,|,?, и * (на самом деле, также ascii 0-31, но меня это не беспокоит. Возможно, также могут быть проблемы с файлами, заканчивающимися на “.”).

Я хотел бы, чтобы rsync автоматически “переименовывал”, например, файл с именем “a:” в, скажем, a(COLON), чтобы в итоге получить законное имя (и, в идеале, преобразовывать a(COLON) обратно в a:)

Можно ли сделать так, чтобы rsync автоматически переименовывал файлы, чтобы избежать символов, запрещенных в Windows?

  • Насколько я понимаю, rsync может использовать iconv для выполнения таких задач; существует ли стандартный модуль iconv для имен файлов Windows? (Я кратко смотрел в программирование собственного модуля gconv, но, не имея знаний по C, это кажется слишком сложным).
  • Мне сказали, что rdiff-backup может выполнять некоторые такие преобразования, но на домашней странице только упоминается о том, что что-то делается “автоматически”, и я не уверен, вызовет ли локально смонтированный объем NTFS надежное переименование?
  • Я знаю, что есть fuse-posixovl, но это кажется излишним для моей цели, и также, похоже, это плохо документировано (какие символы будут преобразованы каким образом? Будут ли все имена файлов сокращены до 8.3 или что-то еще? Могу ли я избежать дополнительных файлов, содержащих информацию о владельцах/разрешениях, которая мне не нужна, и т.д.).
  • Я осведомлен о том, что могу избежать всех этих проблем, используя, например, файл tar; но это не то, что я хочу. (В частности, я хотел бы в Windows дополнительно реплицировать с объема NTFS на другой резервный раздел, копируя только измененные файлы)
  • Я знаю о опции “windows_names” при монтировании NTFS; но это предотвратит создание запрещенных файлов, а не переименует их.

Обновление: Поскольку, кажется, мой вопрос был не совсем понятен, позвольте привести более явный пример: Например, WINDOWS-1251 мне не подходит. iconv -f utf-8 -t WINDOWS-1251//TRANSLIT преобразует

123 abc ABC äö &:<!|

в

123 abc ABC ao &:<!|

Мне нужна кодовая страница, windows-файлы, скажем (которая не существует), которая преобразует строку в что-то вроде

123 abc ABC äö &(COLON)(LT)!(PIPE)

Обновление 2: Я теперь сдался и переименовал запрещенные файлы “вручную” (т.е. с помощью скрипта). С тех пор, каждый раз перед запуском rsync, я запускаю скрипт, который проверяет, существуют ли запрещенные имена файлов (но не переименовывает автоматически); я просто использую

# находим объекты, содержащие запрещенные символы
find $MYDIR -regex '.*/[^/]*[<>:*"\\|?][^/]*'
# находим объекты, заканчивающиеся точкой (предположительно плохо для windows)
find $MYDIR -regex '.*\.'
# находим объекты, идентичные независимо от регистра
find $MYDIR -print0 | sort -z | uniq -diz | tr '\0' '\n'

(последняя строка взята из поиска дубликатов имен файлов независимо от регистра)

Прагматичным решением было бы воспроизвести исходные директории с желаемыми преобразованными именами файлов локально, используя жесткие ссылки на оригинальные файлы, а затем rsync эту копию как есть на файловую систему ntfs.

Например, этот демонстрационный скрипт на perl дублирует иерархию /tmp/a/ в /tmp/b/ и кодирует (с помощью % и 2 шестнадцатеричных цифр) нежелательные символы, так что file:b становится file%3ab (жесткая ссылка), а директория %b<ha> становится директорией %25b%3cha%3e и так далее:

#!/usr/bin/perl
use strict;
use File::Find;
my $startdir="/tmp/a";
my $copydir="/tmp/b";
sub handlefile{
    my $name = substr($File::Find::name,1);
    my $oldname = $startdir.$name;
    $name =~ s/([;, \t+%&<>:\"\\|?*])/sprintf('%%%02x',ord($1))/ge;
    $name = $copydir.$name;
    printf "from %s to %s\n",$oldname,$name;
    if(!-l and -d){ mkdir($name) or die $!; }
    else{ link($oldname,$name) or die $!; }
}
chdir($startdir) or die;
find(\&handlefile, '.');

Вы можете затем rsync /tmp/b на ваш ntfs. Это всего лишь демонстрация и требует доработки для учета unicode и других ограничений ntfs, таких как максимальная длина имени файла. Вы также можете проверить наличие конфликтов между строчными и прописными буквами и использовать ваше предпочтительное кодирование (: на COLON и так далее). Вы можете сделать еще один проход, чтобы исправить временные метки на директориях. Если у вас нет миллионов файлов, работа, необходимая для создания этой копии структуры каталогов с жесткими ссылками на файлы, не должна быть такой обременительной.

Ответ или решение

Учитывая ваш запрос о том, как использовать модуль iconv с rsync для копирования данных на локально смонтированный NTFS-том с учетом недопустимых для Windows имен файлов, важно рассмотреть несколько аспектов, чтобы обеспечить успешное решение вашей задачи.

Введение в проблему

Системы Linux и Windows имеют разные подходы к именованию файлов. В частности, Windows имеет набор символов, которые считаются недопустимыми при создании имен файлов, среди которых: <, >, :, ", /, \, |, ?, * и символы ASCII с кодом от 0 до 31. Это может вызвать проблемы при копировании файлов и директорий с Linux на NTFS.

Использование rsync с модулем iconv

  1. Модуль iconv: Стандартного модуля iconv для обработки недопустимых имен файлов в контексте Windows не существует. Вы не сможете найти готовый кодек, который готов бы автоматически преобразовывать недопустимые символы в допустимые при использовании rsync. Однако, вы можете самостоятельно написать скрипт, который предварительно преобразует имена файлов в необходимый вам формат.

  2. Преобразование имен: Для замены недопустимых символов вы можете использовать различные подходы. Например, вы можете создать скрипт на Perl, Python или даже на Bash, который будет проходить по файловой системе, находить недопустимые символы и заменять их на допустимые. Например, a: может быть преобразовано в a(COLON).

  3. Ракурс к rsync: Используйте rsync для синхронизации с NTFS томом после того, как вы создали предварительно обработанные копии файлов с допустимыми именами. Например:

    rsync -av --progress /path/to/processed/files /mnt/ntfs/

Практическое решение

В качестве примера, вот базовый Perl-скрипт, который рекурсивно дублирует директорию, заменяя недопустимые символы.

#!/usr/bin/perl
use strict;
use warnings;
use File::Find;

my $src_dir = "/path/to/source";
my $dest_dir = "/path/to/destination";

sub handle_files {
    my $name = substr($File::Find::name, 1);
    my $oldname = $src_dir . $name;
    $name =~ s/[<>:"\/\\|?*]/sprintf("(%s)", $&)/ge;  # Замена недопустимых символов
    my $newname = $dest_dir . $name;

    if (-d $oldname) {
        mkdir($newname) or die $!;
    } else {
        link($oldname, $newname) or die $!;
    }
}

chdir($src_dir) or die;
find(\&handle_files, '.');

Альтернативные подходы

  1. Использование fuse-posixovl: Если вы хотите более автоматизированное решение, возможно, стоит рассмотреть использование fuse-posixovl, хотя это может быть избыточным для вашей задачи. Однако его документация может быть не вполне понятной и требует знаний о том, как он обрабатывает имена файлов.

  2. Ручная проверка: Как упомянуто вами, вы можете выполнять ручную проверку на недопустимые имена файлов перед копированием. Это может занимать больше времени, но позволяет вам иметь полный контроль над процессом.

  3. Пакетные преобразования: Вы можете создавать пакетные сценарии для выполнения всех замен перед каждой операцией rsync.

Заключение

На данный момент нет универсального или автоматического решения для обработки недопустимых символов имен файлов при копировании данных с Linux на NTFS с помощью rsync. Однако, создание предварительно обработанных копий с использованием пользовательских скриптов, как указано выше, позволит вам достичь нужного результата и избежать проблем с совместимостью в Windows. Если вам необходима дополнительная помощь в реализации, буду рад предложить более подробные инструкции по каждой части процесса.

Оцените материал
Добавить комментарий

Капча загружается...