Если ваша $VARIABLE
строка содержит пробелы или другие специальные символы и используются одинарные квадратные скобки (что является сокращением для test
команды), то строка может быть разбита на несколько слов. Каждый из них рассматривается как отдельный аргумент.
Так что одна переменная разбивается на множество аргументов :
VARIABLE=$(/some/command);
# returns "hello world"
if [ $VARIABLE == 0 ]; then
# fails as if you wrote:
# if [ hello world == 0 ]
fi
То же самое будет верно для любого вызова функции, который записывает строку, содержащую пробелы или другие специальные символы.
Легко исправить
Оберните вывод переменной в двойные кавычки, заставив его остаться как одна строка (следовательно, один аргумент). Например,
VARIABLE=$(/some/command);
if [ "$VARIABLE" == 0 ]; then
# some action
fi
Просто как тот. Но перейдите к пункту «Также будьте осторожны ...» ниже, если вы также не можете гарантировать, что ваша переменная не будет пустой строкой или строкой, которая содержит только пробелы.
Или альтернативным решением является использование двойных квадратных скобок (что является сокращением для new test
команды).
Это существует только в bash (и, по-видимому, korn и zsh), и поэтому может быть несовместимо с оболочками по умолчанию, вызываемыми и /bin/sh
т. Д.
Это означает, что в некоторых системах он может работать с консоли, но не при вызове в другом месте, напримерcron
, в зависимости от того, как все настроено.
Это будет выглядеть так:
VARIABLE=$(/some/command);
if [[ $VARIABLE == 0 ]]; then
# some action
fi
Если ваша команда содержит двойные квадратные скобки, подобные этой, и вы получаете ошибки в журналах, но она работает из консоли, попробуйте заменить [[
альтернативу, предложенную здесь, или убедитесь, что во всех ваших скриптах используется оболочка, которая поддерживает [[
aka new test
.
Также остерегайтесь [: unary operator expected
ошибок
Если вы видите ошибку «слишком много аргументов», скорее всего, вы получаете строку из функции с непредсказуемым выводом. Если также возможно получить пустую строку (или всю строку пробела), это будет рассматриваться как нулевые аргументы даже с указанным выше «быстрым исправлением» и завершится ошибкой с[: unary operator expected
Это то же самое «гоча», если вы привыкли к другим языкам - вы не ожидаете, что содержимое переменной будет эффективно напечатано в коде, подобном этому, до его оценки.
Вот пример, который предотвращает как ошибки, так [: too many arguments
и [: unary operator expected
ошибки: замена вывода значением по умолчанию, если оно пустое (в этом примере, 0
), с двойными кавычками, обернутыми вокруг всего:
VARIABLE=$(/some/command);
if [ "${VARIABLE:-0}" == 0 ]; then
# some action
fi
(здесь действие произойдет, если $ VARIABLE равно 0 или пусто. Естественно, вы должны изменить 0 (значение по умолчанию) на другое значение по умолчанию, если требуется другое поведение)
Последнее замечание: поскольку [
это сокращение test
, все вышесказанное также верно для ошибки test: too many arguments
(и также test: unary operator expected
)