set -o xtrace
для отладки,
set -o errexit
для выхода по ошибке или
set -o errunset
для выхода, если вызванная переменная не установлена.
Но есть много других опций. Иногда они слишком путано описаны в манах, поэтому я собрал здесь некоторые из наиболее полезных, с объяснением.
Примечание: на Mac может стоять более старая версия bash (3.x, а не 4.x), где не все эти опции доступны. В этом случае смотрите здесь или здесь.
set
или shopt
?
Есть два способа установки параметров bash: из скрипта или из командной строки. Можно использовать встроенные команды
set
и shopt
. Обе изменяют поведение оболочки, делают во многом одно и тоже (с разными аргументами), а различаются своим происхождением. Параметры set
наследуются или заимствуются из параметров других оболочек, в то время как параметры shopt
созданы в bash.Если хотите посмотреть на текущие опции, запустите:
$ set -o
$ shopt
Для активации опции в
set
используется длинный или короткий синтаксис:$ set -o errunset
$ set -e
Эффект одинаков.
Чтобы отключить опцию, нужно поставить плюс вместо минуса:
$ set +e
Долгое время я не мог запомнить этот синтаксис, поскольку логика кажется неправильной (минус включает опцию, а плюс — отключает).
В
shopt
для включения и отключения опций используются (более логичные) флаги -s
(set) и -u
(unset):$ shopt -s cdspell # <= on
$ shopt -u cdspell # <= off
Изменение каталогов
Есть несколько опций, которые помогают работать с каталогами.
1. cdspell
С такой настройкой bash начнёт понимать опечатки и будет переносить вас в папку, название которой вы набрали с ошибкой.
$ shopt -s cdspell
$ mkdir abcdefg
$ cd abcdeg
abcdefg
$ cd ..
Я использовал эту опцию много лет, и очень редко (возможно, раз в год) она принимает очень странное решение. Но зато в остальные дни
cdspell
экономит время, буквально каждый день.2. autocd
Если вы не готовы мириться с неэффективностью многократного ввода
cd
, то можете установить эту опцию для перемещения в папку Х, если команда Х не существует.$ shopt -s autocd
$ abcdefg
$ cd ..
В сочетании с автозаполнением это позволяет быстро прыгать по папкам:
$ ./abc[TAB][RETURN]
cd -- ./abcdefg
Только не называйте папку
rm -rf *
(да, кстати, это возможно).3. direxpand
Это классная опция, которая расширяет переменные среды по нажатию Tab:
$ shopt -s direxpand
$ ./[TAB] # заменяется на...
$ /full/path/to/current_working_folder
$ ~/[TAB] # заменяется на...
$ /full/path/to/home/folder
$ $HOME/[TAB] # заменяется на...
$ /full/path/to/home/folder
Чистый выход
4. checkjobs
Этот параметр останавливает выход из сеанса, если в фоновом режиме ещё выполняются задания.
Вместо выхода выводится список незавершённых заданий. Если вы всё равно хотите выйти, то ещё раз введите
exit
.$ shopt -s checkjobs
$ echo $$
68125 # <= ID процесса для оболочки
$ sleep 999 &
$ exit
There are running jobs.
[1]+ Running sleep 999 &
$ echo $$
68125 # <= ID процесса для оболочки тот же
$ exit
There are running jobs.
[1]+ Running sleep 999 &
$ exit
$ echo $$
$ 59316 # <= на этот раз ID процесса изменился
Сверхспособности по подстановке
5. globstar
Эта опция даёт вам сверхспособности по подстановке! Если ввести:
$ shopt -s globstar
$ ls **
тогда оболочка покажет рекурсивно все каталоги и подкаталоги.
В сочетании с
direxpand
можно быстро просматривать всё, что ниже в иерархии:$ shopt -s direxpand
$ ls **[TAB][TAB]
Display all 2033 possibilities? (y or n)
6. extglob
Эта опция активирует функции, которые чаще ассоциируются с регулярными выражениями. Иногда это очень полезно:
$ shopt -s extglob
$ touch afile bfile cfile
$ ls
afile bfile cfile
$ ls ?(a*|b*)
afile bfile
$ ls !(a*|b*)
cfile
Здесь шаблоны помещаются в круглые скобки и разделяются вертикальной чертой. Вот доступные операторы:
? = соответствует нулю или одному вхождению заданных шаблонов ! = показать всё, что не соответствует заданным шаблонам * = ноль или более вхождений + = одно или более вхождений @ = ровно одно вхождение
Защита от несчастных случаев
7. histverify
Поначалу может быть немного страшновато использовать использовать быстрый запуск команд из истории сокращениями
!!
и !$
.Опция
histverify
позволяет сначала посмотреть, как Bash интерпретирует команду, прежде он на самом деле запустится:$ shopt -s histverify
$ echo !$ # <= По нажатию Enter команда не запускается
$ echo histverify # <= Она сначала демонстрируется на экране,
histverify # <= а потом запускается
8. Noclobber
Опять же, для защиты от несчастных случаев, а именно от перезаписи файла, который уже существует с оператором редиректа (
>
). Это может стать катастрофой, если у вас нет резервной копии.Опция
set -С
запрещает такую перезапись. В случае необходимости можно обойти защиту с помощью оператора >|
:$ touch afile
$ set -C
$ echo something > afile
-bash: afile: cannot overwrite existing file
$ echo something >| afile
$
Комментарии (13)
bliznezz
20.05.2019 10:40Я когда-то любил читать wiki.bash-hackers.org, и даже немножко переводил xgu.ru/wiki/shopt
SergeiMinaev
20.05.2019 15:02+2С такой настройкой bash начнёт понимать опечатки и будет переносить вас в папку, название которой вы набрали с ошибкой.
Извиняюсь, но не понимаю. В разы быстрее и логичнее набирать названия каталогов с использованием автоподстановки через Tab. В таком случае ошибки исключены. Если кто-то набирает с ошибками, значит он не использует автоподстановку. Но почему?
Tangeman
20.05.2019 15:18+1Похоже, автор оригинала не потрудился проверить о чём пишет…
—set -e
это на самом деле эквивалентset -o errexit
— опцииerrunset
не существует в природе, естьnounset
и её эквивалентset -u
.
ganqqwerty
20.05.2019 15:46+1как гуглить синтаксис баша? В языке настолько много разных знаков препинания, что забываешь половину, стоит только сделать перерыв в пару месяцев.
ganqqwerty
20.05.2019 15:48Еще я бы посоветовал всем утилитку z — это такой cd, который переходит в нужную директорию по неполной информации и с учетом того, как часто вы в этой директории бывали раньше.
ppl2scripts
20.05.2019 17:32Написали бы лучше про 'set -o pipefail'. А то 90% выпендривающихся своим башем об это опции не знают.
denzill
21.05.2019 11:50cdspell
Как по мне — вредная опция.
К примеру:
mkdir abcdefg cd abcdeg rm -rf *
сто раз я удалю файлы из каталога abcdefg, а потом в текущем каталоге окажется папка abcdeg…
Все таки скрипт должен делать то, что я попросил, а не то что имел ввиду.
CaptainFlint
21.05.2019 15:49«Защитные» опции (типа histverify, noclobber) могут быть опасны. Привыкнешь, что такие-то операции у тебя на компе можно выполнять безопасно, а потом где-нибудь на удалённом сервере стартанёшь по привычке sudo !!, чтобы посмотреть и подправить команду, а оно вместо вывода текста возьмёт и сразу всё выполнит…
unclechu
22.05.2019 14:50Чтобы отключить опцию, нужно поставить плюс вместо минуса:
Логично, прямо как vertical/horizontal split в tmux.
saipr
Что-то не увидел опций xv:
set -xv
Zverik
А зачем? Они же для пользователя примерно взаимоисключающие? Та и та выводит запускаемые команды, только немного по-разному.
(ну и set -буква в статье не упоминается потому что она про малоизвестные, а не те, что в каждом скрипте встречаются)