Помощь с -maxdepth в команде ‘find -exec mv’

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

Я работаю над скриптом cron для сортировки/фильтрации, чтобы обрабатывать входящие файлы на основе набора постоянных строк (logfile, history, dataset и т. д.). Файлы, которые нужно отсортировать, находятся в общей папке: некоторые в основной папке, а некоторые в подпапках. Я работаю над этим на Debian/bash (MX Linux), и это моя основная забота на данный момент, но в итоге это будет перенесено на систему Debian/ash (dCore Linux).

  • имена файлов и папок всегда содержат STRING, и STRING может содержать смешанный регистр.
  • имя файла и подпапка, в которой он находится, могут оба содержать STRING.
  • папки с STRING могут содержать файлы без STRING. Они должны перемещаться вместе с их родительскими папками.
  • имена файлов и папок могут содержать пробелы, скобки, скобки.

пример:

/main/                                  # папка, в которой идет поиск
/main/filename.log                      # не должен быть перемещен 
/main/filename containing-STRING.log    # должен быть перемещен 
/main/subfolder/                        # не должен быть перемещен 
/main/subfolder/file.txt                # не должен быть перемещен 
/main/subfolder.with STRING in-name/    # должен быть перемещен 
/main/subfolder.with STRING in-name/STRING-file.log # должен быть перемещен вместе с родительской папкой
/main/subfolder.with STRING in-name/file.txt        # должен быть перемещен вместе с родительской папкой

Моя отправная точка:

find . -iname '*STRING*' -exec mv {} ../offload/ \;

Это работает, хотя и выдает ошибки “файл не найден”, предположительно потому, что файлы уже были перемещены, когда их родительские папки были перемещены. Поскольку любые подпапки всегда будут содержать STRING, мне не обязательно нужно или я не хочу ‘искать’ их содержимое. Мне нужно переместить только родительские папки. Поэтому я пытаюсь использовать ‘-maxdepth 0’, чтобы ‘найти’ STRING только в основной папке.

find . -maxdepth 0 -iname '*STRING*' -exec mv {} ../offload/ \;

Добавление переключателя -maxdepth не работает. Предупреждений “файл не найден” нет, но ничего не перемещается. Есть ли какие-то предложения, в чем я ошибаюсь?

РЕДАКТИРОВАНИЕ:
У меня есть доступ только к оболочке bash и в конечном итоге к системе dCore с ее стандартной оболочкой ash. Это мини-система только с интерфейсом командной строки; нет места для добавления другой оболочной среды.

Я пробовал:

find . -maxdepth 0 -type d -iname '*STRING*' -exec mv {} ../offload/ \;

Когда я запускаю его, он возвращает меня к приглашению без ошибок, но ничего не перемешается.

@cas Да, мне нужно сохранить структуру каталогов, но ни один из ваших примеров не должен удовлетворять поиску. Я хочу только найти и переместить файлы и каталоги, которые соответствуют STRING в основной папке. Таким образом:

/main/filename-with-STRING              # соответствует 
/main/folder-with-STRING/               # соответствует 
/main/folder-with-STRING/foo/           # перемещен вместе с родителем
/main/subfolder/filename-with-STRING    # не соответствует 
/main/subfolder/folder-with-STRING/     # не соответствует 

Похоже, вы сначала захотите переместить все соответствующие директории, а затем все файлы, символические ссылки и т. д., которые остались и соответствуют.

Вы можете сделать это, указав -type d для директорий в первом запуске find и '(' -not -type d ')' для второго запуска find.

Однако, вы можете сделать это и без find, используя современную оболочку:

#!/usr/bin/zsh

# возможно, уже включено! Так что, просто для справки:
setopt extended_glob
# также учитывать "скрытые" файлы, т.е., такие, которые начинаются с точки
setopt dotglob
# нам не важен регистр!
setopt nocaseglob

# переместить все директории.
mv **/*STRING*(/) ../offload/
# переместить все, что не директории
mv **/*STRING*(^/) ../offload/

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

В целях решения вашей задачи по перемещению файлов и папок, содержащих определённую подстроку (STRING), давайте подробно разберём, как оптимально использовать команду find с параметром -maxdepth в вашем сценарии.

Теория

Ваша цель заключается в том, чтобы перемещать только те файлы и папки, которые содержат подстроку "STRING" в их именах и расположены в основном каталоге. Недостаток вашего начального подхода состоит в том, что, используя -maxdepth 0, вы ограничиваете поиск только текущей директорией (.), что приводит к полному исключению всех подкаталогов и их содержимого из поиска. Параметр -maxdepth 0 означает, что поиск будет ограничен текущей директорией, и любые вложенные папки или файлы из другого уровня не будут найдены.

Пример

Рассмотрим, как нужно использовать команду find. Исходя из вашего описания, вам нужно переместить папки, содержащие "STRING", и находящиеся в основном каталоге, а также файлы в основном каталоге, которые содержат "STRING".

Пример использования:

# Сначала перемещаем директории из корневого каталога, содержащие "STRING" в имени
find . -maxdepth 1 -type d -iname '*STRING*' -exec mv {} ../offload/ \;

# Затем перемещаем файлы из корневого каталога, содержащие "STRING" в имени
find . -maxdepth 1 -type f -iname '*STRING*' -exec mv {} ../offload/ \;

Применение

Данный подход позволяет сначала перемещать все директории, соответствующие критерию поиска, а затем — все файлы в основном каталоге. Команда find с опцией -maxdepth 1 ограничивает глубину поиска, тем самым предотвращая перемещение объектов внутри подкаталогов. Использование -type d и -type f позволяет различать директории и обыкновенные файлы, отдельно обрабатывая их перемещение.

Важно убедиться, что в целевой директории ../offload/ у вас достаточно места и прав для записи, так как при большом объёме перемещаемых данных могут возникнуть ошибки, связанные с доступностью ресурсов.

Аппаратное окружение Debian/Bash позволит вам корректно использовать эти команды. В случае перехода на dCore Linux с оболочкой ash, убедитесь, что она поддерживает заданные параметры, или используйте аналогичные скрипты, обеспечивающие указанную функциональность.


Таким образом, внимательно настроив параметры команды find, вы сможете эффективно выполнять сортировку и перемещение требуемых файлов и папок по заданным условиям.

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

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