Подтвердить что ты не робот

Оболочка рыбы: проверьте, предоставлен ли аргумент для функции

Я создаю функцию (ниже), с помощью которой вы можете предоставить аргумент, каталог. Я тестирую, если $argv - это каталог с параметром -d, но он, похоже, не работает, он всегда возвращает true, даже если аргументы не указаны. Я также опробовал test -n $argv -a -d $argv, чтобы проверить, что $argv - пустое sting, но возвращает ошибку test: Missing argument at index 1. Как проверить, предоставлен ли какой-либо аргумент функции или нет? Почему test -d $argv не работает, из моего понимания это должно быть ложным, если аргумент не указан, потому что пустая строка не является каталогом.

function fcd
     if test -d $argv
         open $argv
     else
         open $PWD
     end
 end

Спасибо за помощь.

4b9b3361

Ответ 1

count - правильный способ сделать это. Для общего случая проверки наличия аргументов вы можете использовать его статус выхода:

function fcd
    if count $argv > /dev/null
        open $argv
    else
        open $PWD
    end
end

Чтобы ответить на ваш второй вопрос, test -d $argv возвращает true, если $argv пуст, потому что POSIX требует, чтобы, когда test передается один аргумент, он должен "Exit true (0), если $1 не является нулевым, exit false". Поэтому, когда $argv пуст, test -d $argv означает test -d, который должен выйти из true, потому что -d не пуст! Argh!

edit Добавлен недостающий end, благодаря Ismail для заметок

Ответ 2

В рыбе 2.1+, по крайней мере, вы можете назвать свои аргументы, что затем позволяет использовать более семантический код:

function fcd --argument-names 'filename'
    if test -n "$filename"
        open $filename
    else
        open $PWD
    end
end

Ответ 3

$argv - это список, поэтому вы хотите посмотреть на первый элемент, если в нем есть элементы:

if begin; test (count $argv) -gt 0; and test -d $argv[1]; end
    open $argv[1] 
else
    open $PWD
end

Ответ 4

Возможно, это не связано, но я хотел бы добавить еще одну перспективу для вопроса.

Я хочу расширить понимание в более широком круге сферы тестирования кода оболочки с библиотеками, разработанными в группе рыбаков.

С mock вы можете проверить, называется ли команда open безопасно без побочных эффектов.

Пример:

function fcd
    if count $argv > /dev/null
        open $argv
    else
        open $PWD
    end
end
mock open 0 "echo \$args"
fcd "cool" # echoes cool
mock open 0 "echo \$args"
fcd # echoes $PWD

Является недавней библиотекой, но это может помочь проверить вещи, которые могут быть опасны, например, например, rm

mock rm 0 "echo nothing would happen on \$args"
rm "some file" # simply echoes the message with a list of the files that would been affected

Надеюсь, что это даст более точную точку зрения

P.S.: Извините за откровенную рекламу, но я думаю, что это классная идея, которая была бы неплохо принята сценаристами оболочки, чтобы проверить и добавить устойчивость к сценариям оболочки, это орехи.: P

EDIT: Недавно я заметил ошибку, которую я опубликовал. Пожалуйста, не используйте rm *, потому что звездочка не рассматривается как параметр, вместо этого shell shell расширяет звездочку до списка найденных файлов, и команда только извиняет первый вызов, это означает, что первый файл будет игнорироваться макетом, но все последующие файлы будут удалены, поэтому будьте осторожны, если попробуйте образец и используйте один файл для примера, а не подстановочный знак.