Проблема в том, что ~
-расширение не выполняется при раскрытии переменной (когда вы ссылаетесь на этот $ SRCDIR
без кавычек) или внутри двойных кавычек (когда вы назначаете это SRCDIR
переменная).
Оставляя $ SRCDIR
без кавычек, вы вызываете оператор split + glob. Это строка, которая хранится в этой скалярной $ SRCDIR
переменной ( ~ / PI / tutos / * ~ / scripts / *
), сначала разделяется согласно $ IFS
(по умолчанию пробелы), а затем каждое слово подвергается подстановке, которая обрабатывается как шаблоны, которые расширяются до списка совпадающих файлов.
Поскольку ~
не расширяется до вашего домашнего каталога, этот ~
обрабатывается как любой другой символ, поэтому он просто ищет файлы в ~ / PI Каталог / tutos
, где ~
будет каталогом в текущем каталоге, которого в вашем случае не существует.
Лучше всего сделать $ SRCDIR
массивом и расширить глобусы во время присваивания:
SRCDIR=(~/PI/tutos/* ~/scripts/*) # ~ and globs expanded at this point
tar cvpzf "$FILENAME" "${SRCDIR[@]}"
Обратите внимание, что применение оператора split + glob к $ FILENAME
] не имеет смысла, поэтому мы отключаем его, цитируя $ FILENAME
.
Обратите внимание, что если ~ / PI / tutos / *
не соответствует, он будет оставлен как есть, поэтому вы все равно получите сообщение об ошибке из tar
.Чтобы избежать этого, вы можете сделать:
shopt -s nullglob # remove non-matching globs
SRCDIR=(~/PI/tutos/* ~/scripts/*)
if ((${#SRCDIR[@]} != 0)); then
tar cvpzf "$FILENAME" "${SRCDIR[@]}"
fi
У вас может возникнуть соблазн сделать:
SRCDIR="$HOME/PI/tutos/* $HOME/scripts/*"
tar cvpzf "$FILENAME" $SRCDIR
Поскольку переменные (например, $ HOME
) раскрываются в двойных кавычках, но я бы не советовал этого делать, поскольку это не не работает должным образом, если $ HOME
содержит глобальные символы или символы $ IFS
.
~
раскрываются в присвоениях переменных, если они не указаны в кавычках и в начале или после :
(это значит, что он работает при назначении переменных, таких как $ PATH
, $ LD_LIBRARY_PATH
... например, ПУТЬ = ~ / bin: ~ / sbin
). Так что у вас может возникнуть соблазн сделать:
SRCDIR=~/PI/tutos/*:~/scripts/* # ~ (not globs) expanded here
IFS=:
tar cvpzf "$FILENAME" $SRCDIR
Но это то же самое, что и выше, это не будет работать должным образом, если $ HOME
содержит $ IFS
символов (на этот раз :
, что очень маловероятно, поскольку / etc / passwd
определяет, что ваш домашний каталог представляет собой таблицу, разделенную двоеточиями) или глобальные символы.