- Команда exit в Bash и коды выхода
- Статус выхода
- Команда exit
- Примеры
- Выводы
- Как использовать коды завершения в Bash-скриптах
- Что такое коды завершения
- Что происходит, когда коды завершения не определены
- Как использовать коды завершения в Bash-скриптах
- Проверяем коды завершения
- Создаём собственный код завершения
- Как использовать коды завершения в командной строке
- Дополнительные коды завершения
- Exit a Bash Script: Exit 0 and Exit 1 Explained
- Exit a Bash Script With Error
- What Are Exit 0 and Exit 1 in a Bash Script?
- More About The Status of the Bash Exit Command
- An Example of Script Failure
- Bash If Else Applied to $? Variable
- Conclusion
Команда exit в Bash и коды выхода
Часто при написании сценариев Bash вам необходимо завершить сценарий при выполнении определенного условия или выполнить действие на основе кода выхода команды.
В этой статье мы рассмотрим встроенную команду exit Bash и статусы выхода выполненных команд.
Статус выхода
Каждая команда оболочки возвращает код выхода, когда она завершается успешно или безуспешно.
По соглашению нулевой код выхода указывает, что команда завершилась успешно, а ненулевое значение означает, что произошла ошибка.
Специальная переменная $? возвращает статус выхода последней выполненной команды:
Команда date завершена успешно, код выхода равен нулю:
Если вы попытаетесь запустить ls в несуществующем каталоге, код выхода будет отличным от нуля:
Код состояния можно использовать для выяснения причины сбоя команды. На странице руководства каждой команды содержится информация о кодах выхода.
При выполнении многокомандного конвейера статус выхода конвейера соответствует состоянию последней команды:
В приведенном выше примере echo $? напечатает код выхода команды tee .
Команда exit
Команда exit закрывает оболочку со статусом N Он имеет следующий синтаксис:
Если N не задано, код состояния выхода — это код последней выполненной команды.
При использовании в сценариях оболочки значение, указанное в качестве аргумента команды exit возвращается оболочке как код выхода.
Примеры
Статус выхода команд может использоваться в условных командах, таких как if . В следующем примере grep завершит работу с нулем (что означает истину в сценариях оболочки), если «строка поиска» найдена в filename :
При запуске списка команд, разделенных && (И) или || (ИЛИ), статус выхода команды определяет, будет ли выполнена следующая команда в списке. Здесь команда mkdir будет выполнена, только если cd вернет ноль:
Если сценарий завершается exit без указания параметра, код выхода из сценария — это код последней команды, выполненной в сценарии.
Использование только exit — это то же самое, что и exit $? или пропуская exit .
Вот пример, показывающий, как завершить сценарий, если он запущен пользователем без полномочий root:
Если вы запустите сценарий как root, код выхода будет нулевым. В противном случае скрипт выйдет со статусом 1 .
Выводы
Каждая команда оболочки возвращает код выхода при завершении. Команда exit используется для выхода из оболочки с заданным статусом.
Если у вас есть какие-либо вопросы или отзывы, не стесняйтесь оставлять комментарии.
Источник
Как использовать коды завершения в Bash-скриптах
Инструменты автоматизации и мониторинга удобны тем, что разработчик может взять готовые скрипты, при необходимости адаптировать и использовать в своём проекте. Можно заметить, что в некоторых скриптах используются коды завершения (exit codes), а в других нет. О коде завершения легко забыть, но это очень полезный инструмент. Особенно важно использовать его в скриптах командной строки.
Что такое коды завершения
В Linux и других Unix-подобных операционных системах программы во время завершения могут передавать значение родительскому процессу. Это значение называется кодом завершения или состоянием завершения. В POSIX по соглашению действует стандарт: программа передаёт 0 при успешном исполнении и 1 или большее число при неудачном исполнении.
Почему это важно? Если смотреть на коды завершения в контексте скриптов для командной строки, ответ очевиден. Любой полезный Bash-скрипт неизбежно будет использоваться в других скриптах или его обернут в однострочник Bash. Это особенно актуально при использовании инструментов автоматизации типа SaltStack или инструментов мониторинга типа Nagios. Эти программы исполняют скрипт и проверяют статус завершения, чтобы определить, было ли исполнение успешным.
Кроме того, даже если вы не определяете коды завершения, они всё равно есть в ваших скриптах. Но без корректного определения кодов выхода можно столкнуться с проблемами: ложными сообщениями об успешном исполнении, которые могут повлиять на работу скрипта.
Что происходит, когда коды завершения не определены
В Linux любой код, запущенный в командной строке, имеет код завершения. Если код завершения не определён, Bash-скрипты используют код выхода последней запущенной команды. Чтобы лучше понять суть, обратите внимание на пример.
Этот скрипт запускает команды touch и echo . Если запустить этот скрипт без прав суперпользователя, команда touch не выполнится. В этот момент мы хотели бы получить информацию об ошибке с помощью соответствующего кода завершения. Чтобы проверить код выхода, достаточно ввести в командную строку специальную переменную $? . Она печатает код возврата последней запущенной команды.
Как видно, после запуска команды ./tmp.sh получаем код завершения 0 . Этот код говорит об успешном выполнении команды, хотя на самом деле команда не выполнилась. Скрипт из примера выше исполняет две команды: touch и echo . Поскольку код завершения не определён, получаем код выхода последней запущенной команды. Это команда echo , которая успешно выполнилась.
Если убрать из скрипта команду echo , можно получить код завершения команды touch .
Поскольку touch в данном случае — последняя запущенная команда, и она не выполнилась, получаем код возврата 1 .
Как использовать коды завершения в Bash-скриптах
Удаление из скрипта команды echo позволило нам получить код завершения. Что делать, если нужно сделать разные действия в случае успешного и неуспешного выполнения команды touch ? Речь идёт о печати stdout в случае успеха и stderr в случае неуспеха.
Проверяем коды завершения
Выше мы пользовались специальной переменной $? , чтобы получить код завершения скрипта. Также с помощью этой переменной можно проверить, выполнилась ли команда touch успешно.
После рефакторинга скрипта получаем такое поведение:
- Если команда touch выполняется с кодом 0 , скрипт с помощью echo сообщает об успешно созданном файле.
- Если команда touch выполняется с другим кодом, скрипт сообщает, что не смог создать файл.
Любой код завершения кроме 0 значит неудачную попытку создать файл. Скрипт с помощью echo отправляет сообщение о неудаче в stderr .
Создаём собственный код завершения
Наш скрипт уже сообщает об ошибке, если команда touch выполняется с ошибкой. Но в случае успешного выполнения команды мы всё также получаем код 0 .
Поскольку скрипт завершился с ошибкой, было бы не очень хорошей идеей передавать код успешного завершения в другую программу, которая использует этот скрипт. Чтобы добавить собственный код завершения, можно воспользоваться командой exit .
Теперь в случае успешного выполнения команды touch скрипт с помощью echo сообщает об успехе и завершается с кодом 0 . В противном случае скрипт печатает сообщение об ошибке при попытке создать файл и завершается с кодом 1 .
Как использовать коды завершения в командной строке
Скрипт уже умеет сообщать пользователям и программам об успешном или неуспешном выполнении. Теперь его можно использовать с другими инструментами администрирования или однострочниками командной строки.
В примере выше && используется для обозначения «и», а || для обозначения «или». В данном случае команда выполняет скрипт ./tmp.sh , а затем выполняет echo «bam» , если код завершения 0 . Если код завершения 1 , выполняется следующая команда в круглых скобках. Как видно, в скобках для группировки команд снова используются && и || .
Скрипт использует коды завершения, чтобы понять, была ли команда успешно выполнена. Если коды завершения используются некорректно, пользователь скрипта может получить неожиданные результаты при неудачном выполнении команды.
Дополнительные коды завершения
Команда exit принимает числа от 0 до 255 . В большинстве случаев можно обойтись кодами 0 и 1 . Однако есть зарезервированные коды, которые обозначают конкретные ошибки. Список зарезервированных кодов можно посмотреть в документации.
Адаптированный перевод статьи Understanding Exit Codes and how to use them in bash scripts by Benjamin Cane. Мнение администрации Хекслета может не совпадать с мнением автора оригинальной публикации.
Источник
Exit a Bash Script: Exit 0 and Exit 1 Explained
Why would you exit from a Bash script?
Let’s say you are writing a script…there’s one thing that is almost certain…
At some point, your script is likely to break because of unexpected conditions you might have not considered.
So, what can you do about it?
How can you exit a Bash script in case of errors?
Bash provides a command to exit a script if errors occur, the exit command. The argument N (exit status) can be passed to the exit command to indicate if a script is executed successfully (N = 0) or unsuccessfully (N != 0). If N is omitted the exit command takes the exit status of the last command executed.
In this guide you will learn how to use the exit command in your scripts to make them more robust and to provide a great experience to those who are using your scripts.
Let’s get started.
Exit a Bash Script With Error
What can you do to write robust scripts that don’t break in unexpected ways in case of errors?
The answer to this question is: don’t forget error handling.
Instead of “hoping” that nothing will go wrong with your program, you can predict possible failures and decide how your program will react to those.
How will you handle a failure if it occurs? What will the user see?
We will have a look at how error handling works in Bash scripting (or Shell scripting in general).
These concepts apply to all programming languages even if the way error handling is implemented varies between programming languages.
To handle errors in Bash we will use the exit command, whose syntax is:
Where N is the Bash exit code (or exit status) used to exit the script during its execution.
Different values of N are used to indicate if the script exits with success or failure.
But, why different exit codes depending on the success or failure of a script?
Because often other programs will be calling your script and they will need to be able to understand if everything goes well with the execution of your script or not as part of their error handling.
Let’s have a look at what exit 1 means.
What Are Exit 0 and Exit 1 in a Bash Script?
How do you exit a Bash script on error?
The standard convention is the following:
Bash exit code | Meaning |
Zero (0) | Success |
Non-zero (1, 2, 3, etc…) | Failure |
As you can see from the table above, failures can be represented with any non-zero exit codes.
For instance:
- 1 may be used if incorrect arguments are passed to the script
- 2 if the script cannot find a file it needs
- 3 if the file it needs has an incorrect format
- And so on…
You can be creative and use non-zero Bash exit codes to be very clear about the reason why your script has failed.
So, going back to the exit command.
What happens when it gets executed?
The exit command returns an exit code back to the shell.
Here’s an example…
Let’s write a script called exit_status.sh:
So, here we are passing the exit code 0 to the exit command.
How can we verify that this is actually the code passed by the script back to the shell?
We use the $? variable. Remember it, this is very important!
$? is a variable that contains the exit code of the last command executed.
And how can we read its value?
Using the echo command, in the same way we print the value of any variable:
Voilà, here is the 0 exit code.
And what happens if we remove “exit 0” from the script?
Run the script again and check the value of $?:
We still get the 0 exit code back…
So, nothing changed…why?
Because every command we execute, including the echo command (the only command in our script) returns an exit code.
And in this case the echo command executed as part of the script is returning a 0 exit code because the echo “Exit command test” command is executed successfully.
More About The Status of the Bash Exit Command
I will show you an example of how the exit code is applied to the execution of any commands.
This is really important in your Bash knowledge and I want to make sure it’s clear to you.
Here is an example with the cat command (this applies to all commands)…
I open a shell on my computer and in the current directory I have the following files:
If I use the cat command to see the content of the file test_file1 the exit code stored in the variable $? after the execution of the cat command is 0 because the execution of the cat command is successful:
If by mistake I try to print the content of the file test_file3 (that doesn’t exist), the value of the variable $? is not 0.
In this case it’s 1, but it can have other values different than zero. This is useful to represent multiple types of errors for a given command:
If you have any questions please let me know in the comments below.
An Example of Script Failure
Now let’s modify the echo command in the simple script we have used before.
We want run it with an incorrect syntax and see if it exits with a non-zero exit code.
Remove the double quotes at the end of the echo command as shown below:
If we execute the script we see the message “syntax error: unexpected end of file“:
And the exit code is 2. So a non-zero exit code as we expected.
As mentioned before, remember the $? variable because it makes a big difference in the way you handle errors and you make your scripts robust.
The Bash if else statement can also be used to write more complex logic that checks the value of the $? variable and takes different actions based on that.
Bash If Else Applied to $? Variable
Let’s see how you can use a Bash if else statement together with the $? variable.
The following script tries to create a subdirectory tmp/project in the current directory.
In the condition of the if statement we verify if the value of the variable $? is different than 0. If that’s the case we print an error message and exit the script with exit code 1.
The else branch prints a successful message and it’s executed only if the value of $? is 0.
Let’s run the script:
The mkdir command fails because the tmp directory doesn’t exist and as expected the exit status of the script is 1.
I want to see what happens if I update the mkdir command in the script to include the -p flag that creates the tmp directory if it doesn’t exist:
And here is the output of the script:
This time the directory gets created successfully and the exit code returned by the script is zero as expected (the else branch of the if else statement gets executed).
Conclusion
We went through quite a lot!
Now you know:
- Why exit 0 and exit 1 are used in Bash scripts.
- How you can use the variable $? to read the exit code returned by a command (or script)
- The way to use a Bash if else statement together with the $? variable.
And now it’s your turn…
What kind of failures do you want to handle in your script?
Let me know in the comments! 😀
Related FREE Course: Decipher Bash Scripting
Источник