Причина, по которой это не удается, связана с разрешениями и подстановочным знаком *
. Мы можем воспроизвести это в локальной файловой -системе, подобной этой:
Настройте сценарий, дерево каталогов в/tmp/top
:
sudo -s <<'x'
mkdir -p /tmp/top/{a,b}/dir/sub/
touch /tmp/top/{a,b}/dir/sub/file
chown root /tmp/top/?/dir
chmod go= /tmp/top/?/dir
x
Обратите внимание, что у нас, как у обычного пользователя, нет разрешения опускаться ниже/tmp/top/*/dir
:
find /tmp/top/?/dir -type f
find: ‘/tmp/top/a/dir’: Permission denied
find: ‘/tmp/top/b/dir’: Permission denied
Попробуйте спуститься с привилегиями root из каталога, который мы не можем получить как обычный пользователь:
sudo find /tmp/top/*/dir/sub -type f
find: ‘/tmp/top/*/dir/sub’: No such file or directory
Помните, что оценка подстановочных знаков оболочки происходит до выполнения команды. Итак, здесь происходит расширение пути, содержащего подстановочный знак *
. Ваша обычная учетная запись пользователя не может проверить существование sub
, поэтому весь путь не может быть проверен. Подстановочный знак остается в виде звездочки (— поведение по умолчанию, когда совпадение не удается )и привилегированному пользователю root find
предоставляется буквальный путь /tmp/top/*/dir/sub
для нисхождения. Этот путь не существует, отсюда и ошибка.
Попробуйте спуститься с привилегиями root из каталога, к которому мы можем получить доступ как обычный пользователь:
sudo find /tmp/top/*/dir -type f
/tmp/top/a/dir/sub/file
/tmp/top/b/dir/sub/file
Здесь происходит то же самое, но с более полезными последствиями. Путь /tmp/top/*/dir
можно полностью оценить как обычного пользователя, в результате чего получится два пути /tmp/top/a/dir
и /tmp/top/b/dir
. Они передаются корневому привилегированному find
, и он может впоследствии спуститься по ним -через корневой -только подкаталог -и составить список обнаруженных файлов.
В вашей ситуации весьма вероятно, что каталоги .local
в вашем пути с подстановочными знаками не могут быть доступны без привилегий суперпользователя, но каталоги более высокого уровня вполне доступны. Пока вы указываете путь, который можно оценить как вашу обычную учетную запись пользователя, find
может продолжить работу с расширенным набором путей. Как только вы укажете путь, который не может быть оценен в контексте вашей обычной учетной записи пользователя, раскрытие завершится ошибкой, и find
будет передан путь, содержащий буквальный символ *
. Это, конечно, не совпадает, и find
не работает.
Чтобы решить эту проблему, вам просто нужно отложить оценку пути, пока ваша команда не будет запущена от имени пользователя root:
sudo bash -c "find /nfshome/*/.local/ -type f -size +1G -exec ls -lh {} \;"
Это похоже на ошибку Nix, вот похожая ошибка дляnix eval
.
Пока это не будет исправлено, вы можете использовать nix-shell -E "$(curl $url)"
. Или просто с помощью Nix, nix-shell -E "import (builtins.fetchurl $url)"
.
Просто убедитесь, что вы можете доверять выражению перед его выполнением — выражение shellHook
может содержать произвольный код bash, и оболочка nix -запустит его.