Часто существуют времена, что я хочу выполнить команду на всех файлах (включая скрытые файлы) в каталоге. Когда я пытаюсь использовать
chmod g+w * .*
это изменяет полномочия на всех файлах, которые я хочу (в каталоге) и все файлы в родительском каталоге (что я хочу оставленный в покое).
Существует ли подстановочный знак, который делает правильную вещь, или я должен начать использовать, находят?
Вам понадобятся два шаблона глобусов, чтобы охватить все потенциальные «точечные файлы»: . [^.] *
и ..? *
.
Первый соответствует всем записям каталога с двумя или более символами, где первый символ - точка, а второй символ - не точка. Второй выбирает записи с тремя или более символами, которые начинаются с ..
(это исключает ..
, потому что он состоит только из двух символов и начинается с .
, но включает (что маловероятно) такие записи, как .. foo
).
chmod g+w .[^.]* ..?*
Это должно хорошо работать почти во всех оболочках и подходит для скриптов.
При обычном интерактивном использовании шаблоны могут быть слишком сложными для запоминания. В таких случаях в вашей оболочке может быть более удобный способ пропустить .
и ..
.
zsh всегда исключает .
и ..
из таких шаблонов, как . *
.
В bash вы должны использовать переменную оболочки GLOBIGNORE.
# bash
GLOBIGNORE=.:..
echo .*
Вы можете установить GLOBIGNORE в одном из ваших файлов настройки bash (например, .bash_profile
/ .bash_login
или .bashrc
) .
Однако будьте осторожны, привыкая к этой настройке, если вы часто используете другие среды.
Если вы запустите команду типа chmod g + w. *
в среде, в которой отсутствуют ваши настройки, то вы неожиданно получите .
и ..
в вашем подчинении.
Кроме того, вы можете настроить оболочки для включения «файлов точек» в шаблоны, которые не начинаются с явной точки (например, *
).
# zsh
setopt glob_dots
# bash
shopt -s dotglob
# show all files, even “dot files”
echo *
Обычно я просто использую . .[a-zA-Z0-9]*
, поскольку имена моих файлов обычно следуют определенным правилам, но это не может охватить все возможные случаи.
Вы можете использовать:
chmod g+w $(ls -1a | grep -v '^..$')
который в основном перечислит все файлы и каталоги, вычеркнет родительский каталог и обработает остальные. Остерегайтесь пробелов в именах файлов, они будут восприниматься как отдельные файлы.
Конечно, если вам нужны только файлы, вы можете использовать:
find . -maxdepth 0 -type f -exec chmod g+w {} ';'
или другое решение, которое будет обрабатывать все файлы и каталоги, кроме ...
одного:
for i in * .* ; do if [[ ${i} != ".." ]] ; then chmod g+w "$i"; fi done
но теперь вы попадаете на территорию, где могут понадобиться скрипты или псевдонимы.