iwantcoding.com
🔥 Daily 👥 Rooms 🏆 Top Log in Sign up

Functions

Bash functions: defining, scoping, returning, local variables, and the patterns for reusable shell code.

Linux — Bash functions

EXAMPLE
# ===== Define =====
greet() {
  echo "Hello, $1"
}

# Or:
function greet { echo "Hello, $1"; }

greet 'Alex'   # Hello, Alex

# ===== Arguments =====
# $1, $2, ... positional
# $@ all args as separate words
# $* all args as one string
# $# count of args
# $0 script / function name

sum() {
  local total=0
  for n in "$@"; do
    total=$((total + n))
  done
  echo $total
}

sum 1 2 3 4    # 10

# ===== Local variables (CRUCIAL) =====
# Without 'local', variables are GLOBAL by default — bites every Bash newbie.
process() {
  local count=0      # scoped to this function
  for f in *; do
    count=$((count + 1))
  done
  echo $count
}

# ===== Return values =====
# Bash functions return a STATUS CODE (0-255), not arbitrary values.
# To 'return' data:
# 1. echo the value, capture with $()
get_user() {
  echo "alex"
}
name=$(get_user)

# 2. Use a global variable (works but messy):
get_user2() {
  user='alex'
}
get_user2
echo $user

# 3. Use nameref (Bash 4.3+):
get_user3() {
  local -n out=$1
  out='alex'
}
get_user3 name
echo $name

# ===== Return status =====
is_root() {
  [ "$(id -u)" = '0' ]   # returns 0 if root, 1 if not
}

if is_root; then
  echo 'running as root'
else
  echo 'not root'
fi

# Explicit return:
check() {
  if [ -z "$1" ]; then
    return 1
  fi
  return 0
}

# ===== Recursion =====
factorial() {
  if [ "$1" -le 1 ]; then echo 1; return; fi
  echo $(($1 * $(factorial $(($1 - 1)))))
}
factorial 5    # 120

# ===== Default values =====
greet_user() {
  local name="${1:-world}"
  echo "Hello, $name"
}
greet_user       # Hello, world
greet_user Alex  # Hello, Alex

# ===== Library files =====
# common.sh:
log() { echo "[$(date +%F)] $*"; }
fatal() { echo "ERROR: $*" >&2; exit 1; }

# In your script:
source ./common.sh    # or: . ./common.sh
log 'starting'
[ -f config.txt ] || fatal 'no config'

# ===== Patterns =====
# - 'local' on every variable inside a function
# - echo for return data; capture with $()
# - Source library files for shared helpers
# - Default values with ${1:-default}
# - return for status codes only

# ===== Pitfalls =====
# - Forgetting 'local' -> globals leak
# - return 256 -> wraps to 0; status codes 0-255 only
# - echo + return at same time -> ambiguous; pick one
# - Functions returning unparseable data via echo (newlines, special chars)

Why it matters

Bash functions: define, accept positional args via \$1/\$@, ALWAYS use local for scoped vars, return status codes only, echo + \$() for data. Source shared libraries with common helpers. The discipline saves the hours later when scripts grow past 100 lines.

Tip: Tweak the snippet with Try it Yourself », then sit the quiz at the bottom of the page.

Example

Example
greet() { echo "Hello, $1"; }
greet Ada
Try it Yourself »

Discussion

Loading…