Bash throws error, line 8: $1: unbound variable

set -u will abort exactly as you describe if you reference a variable which has not been set. You are invoking your script with no arguments, so get_percent is being invoked with no arguments, causing $1 to be unset.

Either check for this before invoking your function, or use default expansions (${1-default} will expand to default if not already set to something else).


This is the effect of set -u.

You could check $# inside the function and avoid referencing $1 if it is not set.

With $# you can access the number of parameters. In global context it is the number of parameters to the script, in a function it is the number of parameters to the function.

In the context of the question, it is

if [ $# -ge 1 ] && [ -n "$1" ]
then
    df -h $1 | tail -n +2 | awk '{ print $1,"\t",$5 }'
else
    df -h | tail -n +2 | awk '{ print $1,"\t",$5 }'
fi

Note that you have to use [ $# -ge 1 ] && [ -n "$1" ] and not [ $# -ge 1 -a -n "$1" ], because that would first evaluate $1 and then check $#.


Since this is bash you can sidestep the check for $1 being set and just use "$@" ($1 is the first parameter, $@ is all of them; when double-quoted, it disappears completely if it has no values, which avoids it being caught by set -u):

get_percent() {
    df -h "$@" | awk 'NR>1 { printf "%s\t%s\n", $1, $5 }'
}

I've also tweaked the rest of the line slightly so that you don't get {space}{tab}{space} between the two values you output but insead you get just a {tab}. If you really want the two invisible spaces then change the awk to use printf "%s \t %s\n", $1, $5.