При запуске `rm -rf` возможно ли исключить определенные подкаталоги?

Я обычно использую bind mounts, чтобы помочь сделать пространство доступным в нескольких местах без необходимости иметь несколько логических томов / физических разделов / LUN и т. Д.

Например, у меня может быть 200G LV установлен в /space, Оттуда я буду делать такие подкаталоги, как var_opt а также var_log который я могу затем привязать к горе /var/opt а также /var/logсоответственно.

При очистке каталога 'space' возможно ли исключить каталоги из rm -rf работает внутри /space?

Пример:

# pwd
/space
# rm -rf * {except-for-var_opt-and-var_log}

Есть ли другой или лучший (но такой же простой) способ выполнить то, что я пытаюсь сделать, о котором я не думал?

5 ответов

Решение

Может быть, с помощью комбинации find + xargs + rm?

find /space ! -iregex '(var_opt|var_log)' | xargs rm -f

или что-то в этой мелодии. Конечно, было бы разумно сначала проинструктировать xargs выполнить что-то более безвредное, например, echo, прежде чем изменить его на rm ...

Простая концептуально и имеет низкий риск ошибки:

mkdir TO_DELETE
mv * TO_DELETE
mv TO_DELETE/var_opt TO_DELETE/var_log .
rm -rf TO_DELETE

Вы также можете использовать расширенные глобусы ksh:

rm -rf !(var_opt|var_log)

Они также доступны в bash, если вы включите их:

shopt -s extglob
rm -rf !(var_opt|var_log)

То же самое в зш:

setopt ksh_glob
rm -rf !(var_opt|var_log)

У Zsh также есть свои собственные расширенные глобусы:

setopt extended_glob
rm -rf ^var_(opt|log)

Другой вариант:

Проверьте вывод

      env ls -d -1 space/* | grep -E -v 'var_opt|var_log'

Если это похоже на список файлов/папок, которые вы хотите удалить, используйте

      env ls -d -1 space/* | grep -E -v 'var_opt|var_log' | xargs rm -rf

Я предлагаю использоватьenv lsвместо того, чтобы отключить любое сглаживаниеlsв твоей оболочке.

Если ваши имена входных файлов генерируются пользователями, вам нужно иметь дело с неожиданными именами файлов, содержащими пробел, 'или "в имени файла.

Использование xargs может привести к неприятным сюрпризам из-за проблемы с разделителем .

У GNU Parallel такой проблемы нет.

find /space ! -iregex '(var_opt|var_log)' | parallel -X rm -f

Посмотрите вступительное видео для GNU Parallel, чтобы узнать больше.

Если каталоги, которые вы хотите сохранить, являются точками монтирования, вы можете использовать --one-file-system в GNU rm,

Я не исследовал, как это реализовано, но я предполагаю, что это не будет делать то, что вы хотите, если привязка монтируется из той же файловой системы, так что будьте осторожны! rm не имеет --no-act вариант, но вы можете трубу yes no | rm -ir . например.

Другие вопросы по тегам