How can I stop execution of a bash script, whether or not it's invoked with "source"?

Viewed 58

I am trying to get rid of an exit call in a bash script in order to make it sourceable.

At this moment the script contains an exit which is ok if you call the script normally, but if you source it, it will also stop the execution of the calling script which is not desired.

If I replace the exit with a return it will work well when source but it will fail with an error when is not sourced.

return: can only `return' from a function or sourced script

I am looking at a solution what would work with both cases.

2 Answers

You could wrap the script's code in a function which you can then return from.

__main() {
    unset -f __main

    ...
    if whatever; then
        return
    fi
    ...
}

__main "$@"

Try to return, fall back to exit if it fails.

{ retval=$?; return "$retval" 2>/dev/null || exit "$retval"; }

Tested as follows:

cat >one <<'EOF'
#!/usr/bin/env bash
echo "one starting"
source two
echo "one ending"
EOF

cat >two <<'EOF'
#!/usr/bin/env bash
echo "two starting"
echo "two attempting to exit"
{ retval=$?; return "$retval" 2>/dev/null || exit "$retval"; }
echo "two still running after attempted exit
EOF

source one

...which properly/correctly emits:

one starting
two starting
two attempting to exit
one ending

...whereas running chmod +x two; ./two emits:

two starting
two attempting to exit
Related