Найти -exec dry run?

Dec 27 2020

Есть ли способ увидеть, каков будет результат find . -exec somecommand {} \;с заменами, без фактического выполнения команд? Нравится пробный прогон (или пробный прогон, или печать)?

Например, предположим, что у меня есть следующая файловая структура:

/a/1.txt
/a/2.txt
/a/b/3.txt

Есть ли способ протестировать find . type f -exec rm {} \;из aкаталога, чтобы вывод выводился на стандартный вывод, но не выполнялся, например:

rm 1.txt
rm 2.txt
rm b/3.txt

Примечание к обновлению : rmэто просто пример команды, меня интересует общий случай

Ответы

18 rAlen Dec 27 2020 at 07:10

Вы можете бежать echo rmвместоrm

find . type f -exec echo rm {} \;

Также findесть -deleteвозможность удалять найденные файлы.

3 l0b0 Dec 27 2020 at 07:28

В rmчастности, вам не нужно -exec: просто запустить find . -type fв список и добавить, -deleteчтобы удалить файлы, перечисленные предыдущей командой (очевидно, запрещая создание / удаление любых совпадающих файлов в это время).

Кроме того , для команд , как rmкоторые принимают произвольное число аргументов , вы хотите заменить \;с , +чтобы работать как несколько команд , как это возможно.

2 CharlesDuffy Dec 28 2020 at 00:38

Это немного сложно, но, в отличие от подходов с использованием echo, приведенный ниже выводит код, который вы можете запустить в своей оболочке без каких-либо изменений, чтобы получить правильный результат, даже если ваши имена файлов содержат кавычки, пробелы, метасимволы оболочки и т. Д.

printcmd() { printf '%q ' "$@"; printf '\n'; } find . -exec bash -c "$(declare -f printcmd); "'printcmd "$@"' _ \
  somecommand {} \;

Обратите внимание, что строка, которую мы добавляем к нашему -execаргументу, в точности bash -c "$(declare -f printcmd); "'printcmd "$@"' _- $(declare -f printcmd)расширяется до кода функции; после этого мы фактически вызываем функцию с аргументами $1и далее и помещаем _в качестве заполнителя для $0.

Вы можете заменить zshили kshвместо bash, если хотите, чтобы вывод был экранирован для этой оболочки.