Как передать аргумент командной строки в сценарий оболочки?

243

Я знаю, что сценарии оболочки просто запускают команды, как если бы они выполнялись в командной строке. Я хотел бы иметь возможность запускать сценарии оболочки, как если бы они были функциями ... То есть, принимая входное значение или строку в сценарий. Как мне подойти к этому?

Павел
источник

Ответы:

199

Командная оболочка и любые аргументы этой команды отображаются в виде нумерованных переменных оболочки: $0имеет строковое значение самой команды, что - то вроде script, ./script, /home/user/bin/scriptили любой другой . Любые аргументы появляются как "$1", "$2", "$3"и так далее. Количество аргументов находится в переменной оболочки "$#".

Обычные способы борьбы с этим включают команды оболочки getoptsи shift. getoptsочень похоже на getopt()функцию библиотеки C. shiftперемещает значение $2в $1, $3в $2и т. д .; $#уменьшается Код заканчивает тем, что смотрит на значение "$1", делает что-то, используя case…, esacчтобы принять решение о действии, а затем делает, shiftчтобы перейти $1к следующему аргументу. Это только когда-либо нужно исследовать $1, и, может быть $#.

Брюс Эдигер
источник
6
C getopt()является чрезвычайно установленным стандартом, но getoptисполняемый файл не является одинаковым для всех дистрибутивов / платформ. Я теперь полностью преобразованный getoptsпользователь, так как это стандарт POSIX. Он также отлично работает с dashмоей предпочитаемой скриптовой оболочкой
JM Becker
165

Вы можете получить доступ к переданным аргументам с помощью $nгде nномер аргумента - 1, 2, 3, .... Вы передаете аргументы так же, как и при использовании любой другой команды.

$ cat myscript
#!/bin/bash
echo "First arg: $1"
echo "Second arg: $2"
$ ./myscript hello world
First arg: hello
Second arg: world
Kevin
источник
27
$/shellscriptname.sh argument1 argument2 argument3 

Вы также можете передать вывод одного сценария оболочки в качестве аргумента другому сценарию оболочки.

$/shellscriptname.sh "$(secondshellscriptname.sh)"

В сценарии оболочки вы можете получить доступ к аргументам с номерами, такими как $1первый аргумент, $2второй аргумент и так далее.

Подробнее об аргументах оболочки

Баласвами Ваддеман
источник
18

Форма

$ ./script.sh "$@" 

является наиболее удобным для argv. Разделитель аргументов является пробелом, но его можно изменить. Не помню, как с рук. Тогда используйте

 $1, $2, shift, if [ $# -ne 3 ] 

контролировать поток. Я обычно не принимаю getopts, если case ... esacбудет достаточно.

user400344
источник
14

В bash-скрипте мне лично нравится использовать следующий скрипт для установки параметров:

#!/bin/bash

helpFunction()
{
   echo ""
   echo "Usage: $0 -a parameterA -b parameterB -c parameterC"
   echo -e "\t-a Description of what is parameterA"
   echo -e "\t-b Description of what is parameterB"
   echo -e "\t-c Description of what is parameterC"
   exit 1 # Exit script after printing help
}

while getopts "a:b:c:" opt
do
   case "$opt" in
      a ) parameterA="$OPTARG" ;;
      b ) parameterB="$OPTARG" ;;
      c ) parameterC="$OPTARG" ;;
      ? ) helpFunction ;; # Print helpFunction in case parameter is non-existent
   esac
done

# Print helpFunction in case parameters are empty
if [ -z "$parameterA" ] || [ -z "$parameterB" ] || [ -z "$parameterC" ]
then
   echo "Some or all of the parameters are empty";
   helpFunction
fi

# Begin script in case all parameters are correct
echo "$parameterA"
echo "$parameterB"
echo "$parameterC"

С этой структурой мы не полагаемся на порядок параметров, так как мы определяем ключевые буквы для каждого из них. Кроме того, функция справки будет напечатана всегда, когда параметры определены неправильно. Это очень полезно, когда у нас много сценариев с различными параметрами для обработки. Это работает следующим образом:

$ ./myscript -a "String A" -b "String B" -c "String C"
String A
String B
String C

$ ./myscript -a "String A" -c "String C" -b "String B"
String A
String B
String C

$ ./myscript -a "String A" -c "String C" -f "Non-existent parameter"
./myscript: illegal option -- f

Usage: ./myscript -a parameterA -b parameterB -c parameterC
    -a Description of what is parameterA
    -b Description of what is parameterB
    -c Description of what is parameterC

$ ./myscript -a "String A" -c "String C"
Some or all of the parameters are empty

Usage: ./myscript -a parameterA -b parameterB -c parameterC
    -a Description of what is parameterA
    -b Description of what is parameterB
    -c Description of what is parameterC
Рафаэль Муйнарск
источник
13
./myscript myargument

myargumentстановится $1внутри myscript.

vimdude
источник
5

В сценарии оболочки; это становится именем переменной $ 1. Второе слово становится именем переменной $ 2 и так далее.

cat << 'EOF' > test
echo "First arg: $1"
echo "Second arg: $2"
echo "List of all arg: $@"
EOF
sh test hello world

Более подробную информацию можно найти в руководстве по shell (sh) по адресу http://heirloom.sourceforge.net/sh/sh.1.html.

FireInTheSky
источник
2
добро пожаловать в U & L, это вряд ли что-то добавит к уже данному ответу
Архемар
0
#!/bin/bash
echo "First arg: $1"
echo "Second arg: $2"
echo "Your First Argument was $1 & Second Argument was $2" 2> /dev/null

------------------------------------------------------------------------

./scriptname.sh value1 value2
Yogesh
источник
3
1) ненужный 2> /dev/null, 2) ничего не добавляет к существующим ответам.
ксеноид