Bash (Bourne Again Shell) — командная оболочка и язык сценариев, используемый в UNIX-подобных системах.
Основное назначение: автоматизация задач, обработка файлов, системное администрирование.
Аналоги:
Скрипт — это обычный текстовый файл с командами Bash.
Комментарии — однострочные и начинаются с символа #.
Отступы игнорируются.
Если строка слишком длинная то её можно разделить на несколько строк с помощью символа \:
tar -cvpzf /backup/archive_$(date +%Y%m%d).tar.gz \
--exclude=/proc \
--exclude=/lost+found \
--exclude=/sys \
/home/user/data
эквивалентно:
tar -cvpzf /backup/archive_$(date +%Y%m%d).tar.gz --exclude=/proc --exclude=/lost+found --exclude=/sys /home/user/data
Несколько команд можно объединить в одну строку с помощью символа ; (пробелы вокруг необязательны):
echo "HELLO" ; echo "WORLD"
эквивалентно:
echo "HELLO"
echo "WORLD"
Запуск скрипта вручную:
bash script.sh
Запуск скрипта как приложения:
#!/bin/bash
chmod +x script.sh
.):
./script.sh
$PATH:
script.sh
Если в shebang указать другой интерпретатор, то можно использовать другой скриптовый язык (Perl, Python, Ruby, PHP и т.д.).
Все переменные — строкового типа.
Объявление переменных (без пробелов вокруг =):
NAME="Ivan"
Подстановка значения переменной:
echo "Hello, $NAME"
Кавычки не обязательны, можно использовать апострофы в качестве кавычек. Следующие выражения эквивалентны:
msg="Hello World"; echo $msgmsg=Hello\ World; echo $msgmsg='Hello World'; echo $msgЕсли кавычки не используются, то специальные символы (включая пробел) надо экранировать с помощью символа \.
Если используются апострофы, то подстановка значений переменных не будет работать, строка используется буквально.
Встроенные переменные:
$0 — имя скрипта$1, $2, ... — аргументы командной строки / аргументы функции$# — количество аргументов$@ — все аргументы$? — код завершения последней вызванной командыДля конкатенации строк достаточно просто поставить значения переменных рядом:
a="Hello"
b="World"
res="$a $b"
Для вычисления целочисленных арифметических выражений (+, -, *, /, %, ++, --) используются конструкции вида:
res=$(( 6 * 7 ))res=$(expr 6 \* 7) (символ * нужно экранировать \, т.к. имеет спец. значение)let res="6 * 7"Если используется (( )) или let то экранирование * не требуется, также не нужно ставить $ перед переменными.
Если используется expr, то нужно экранировать * и ставить $ перед переменными.
Внутри арифметических выражений пробелы необязательны, их можно убирать.
Для вычисления вещественных арифметических выражений используется утилита bc:
# scale - количество знаков после запятой
# a() - арктангенс
# используем факт, что tg(pi/4) = 1
pi=$(echo "scale=10; 4*a(1)" | bc -l)
echo "Pi = $pi"
read VAR
echo "Text"
> — запись в файл потока вывода (перезапись)2> — запись в файл потока ошибок (перезапись)&> — запись в файл потока вывода и ошибок (перезапись)>> — добавление в файл потока вывода2>> — добавление в файл потока ошибок&>> — добавление в файл потока вывода и ошибок< — чтение потока ввода из файла| — конвейер (передача вывода одной команды на вход другой команде)if [ $a -gt $b ]; then
echo "a > b"
elif [ $a -eq $b ]; then
echo "a = b"
else
echo "a < b"
fi
Секции else и elif необязательны.
Секция elif может быть использована несколько раз.
Пробелы вокруг квадратных скобок в логических условия — обязательны.
Отступы слева внутри секций — необязательны.
С помощью символа ; происходит объединение двух операторов в одну строку. То есть:
if [ $a -gt $b ]; then
echo "a > b"
fi
эквивалентно:
if [ $a -gt $b ]
then
echo "a > b"
fi
Логические условия:
-eq (равно), -ne (не равно), -gt (больше), -lt (меньше), -ge (больше или равно), -le (меньше или равно)= (равно), != (не равно), -z (пустая строка), -n (непустая строка)-f — проверка что это обычный файл-d — проверка что это каталог-e — проверка что файл существует-r — проверка что файл можно прочитать-w — проверка что в файл можно записывать-x — проверка что файл можно выполнить / в каталог можно перейтиCOND1 && COND2 — ИCOND1 -a COND2 — И (не рекомендуется, устаревший синтаксис)COND1 || COND2 — ИЛИCOND1 -o COND2 — ИЛИ (не рекомендуется, устаревший синтаксис)! EXPRESSION — НЕВокруг логических выражений можно ставить круглые скобки отделенные пробелом.
Для проверки логических условий также может использовать команда test:
if test -d /tmp; then
cp /etc/motd /tmp/motd
fi
while (работает пока условие выполняется):
while [ $i -lt 5 ]; do
echo $i
((i++))
done
for (арифметический цикл):
for ((i=0; i<5; i++)); do
echo "$i"
done
for (обход элементов коллекции):
for file in *.txt; do
echo "$file"
done
until работает пока условие не выполнится:
until [ $x -eq 10 ]; do
((x++))
done
function greet() {
echo "Hello, $1"
}
greet "World"
Функциям можно передавать произвольное количество аргументов. Аргументы доступны внутри функции по их номеру, а не по имени. Поэтому скобки при объявлении функции всегда пустые или вообще могут быть опущены. Также допускается пропускать ключевое слово function:
function greet() {
echo "Hello, $1"
}
эквивалентно:
function greet {
echo "Hello, $1"
}
эквивалентно:
greet {
echo "Hello, $1"
}
Возврат значения:
return 0
Код завершения функции доступен через встроенную переменную $?.
Запуск с режимом трассировки:
bash -x script.sh
Прерывание при ошибке:
set -e