proper way to detect shell exit code when errexit option set
How about this? If you want the actual exit code ...
#!/bin/sh
set -e
cat /tmp/doesnotexist && rc=$? || rc=$?
echo exitcode: $rc
cat /dev/null && rc=$? || rc=$?
echo exitcode: $rc
Output:
cat: /tmp/doesnotexist: No such file or directory
exitcode: 1
exitcode: 0
Keep with errexit. It can help find bugs that otherwise might have unpredictable (and hard to detect) results.
#!/bin/bash
set -o errexit ; set -o nounset
bad_command || do_err_handle
good_command
The above will work fine. errexit
only requires that the line pass, as you do with the bad_command && rc=0
. Therefore, the above with the 'or' will only run do_err_handle if bad_command
fails and, as long as do_err_handle doesn't also 'fail', then the script will continue.
Continue to write solid shell code.
You do it right if bad_command is really a command. But be careful with function calls in if, while, ||, && or !, because errexit will not work there. It may be dangerous.
If your bad_command is actually bad_function you should write this:
set -eu
get_exit_code() {
set +e
( set -e;
"$@"
)
exit_code=$?
set -e
}
...
get_exit_code bad_function
if [ "$exit_code" != 0 ]; then
do_err_handle
fi
This works well in bash 4.0. In bash 4.2 you only get exit codes 0 or 1.