Я хочу найти все файлы, которые мне не принадлежат (то есть, не имеют права изменять их). Я пробовал
find . -exec if [[ ! -O {} ]]; then echo {}; fi ;
Но если я поставлю всю команду -exec
в кавычки, например так:
find . -exec 'if [[ ! -O {} ]]; then echo {}; fi' \;
Ни то, ни другое не работает, поскольку ссылка на текущий файл {}
заключена в кавычки и поэтому не расширяется до файла.
Проблема в том, что я не знаю, как встроить {}
текущий файл в более сложный, -exec
чем простой, например find . -exec grep smf {} \;
(который использует {}
только один раз). Как использовать -exec
опцию в find в командах, где вы ссылаетесь на текущий файл более одного раза? (Это использует {}
больше времени).
решение1
Ваш код не работает, поскольку утилита, которую вы просите find
запустить, if
не существует (это ключевое слово в синтаксисе оболочки).
Тест -O
истинен, если аргумент — файл, принадлежащий текущему пользователю. Тот же тест можно выполнить сам по find
себе с помощью -user "$USER"
(предполагая, что $USER
расширяется до текущего пользователя):
find . -type f ! -user "$USER"
Вы также можете использовать test -O
, если ваша внешняя test
утилита поддерживает этот нестандартный тест (проверьте man test
):
find . -type f ! -exec test -O {} \; -print
Если вы все еще хотите или нуждаетесь в использовании -O
теста, встроенного в bash
оболочку, то вам придется создать bash
оболочку для выполнения теста:
find . -type f -exec bash -c '[[ ! -O "$1" ]]' bash {} \; -print
Это запускает один встроенный bash -c
скрипт для каждого найденного файла, который запускает тест на его первом аргументе ( $1
). Аргумент передается в командной строке скрипта find
( bash
строка перед ним {}
будет помещена $0
внутрь скрипта и будет использоваться этой оболочкой для сообщений об ошибках). Если тест истинен (файл не принадлежит вам), -print
вступает в силу и печатает путь к файлу.
Вы можете сделать это немного эффективнее с помощью
find . -type f -exec bash -c '
for pathname do
[[ ! -O "$pathname" ]] && printf "%s\n" "$pathname"
done' bash {} +
Это более эффективно, поскольку в bash -c
скрипт передаются пакеты найденных путей.
... но использование -user "$USER"
было бы лучшим вариантом.
Смотрите также: