Frequently Asked Question

How do I parse command-line options with getopts?

getopts is bash's built-in option parser, designed for short options of the form -v, -h, -o file. You pass it a spec string and a variable name, and call it in a loop: each call shifts the parser one option forward and sets the variable to the option letter. A colon after a letter in the spec means that option takes an argument, which getopts puts in $OPTARG. A typical loop looks like while getopts ":hvo:" opt; do case $opt in h) usage ;; v) verbose=1 ;; o) outfile="$OPTARG" ;; esac; done followed by shift $((OPTIND - 1)) to consume the parsed options.

The advantages of getopts are that it is POSIX, ships with every shell, handles grouped flags (-hv parses as -h -v), and reports errors with a clean state machine. Its main limitation is that it only does single-letter short options; for long options like --verbose you need the external getopt (note: different program, behaves differently across systems and is GNU-specific in its useful form) or a hand-rolled while [[ $# -gt 0 ]]; do case $1 in --verbose) ...; shift ;; esac; done loop. For scripts that need long options and complex argument handling, this is one of the clearest signs you should reach for Python's argparse instead.

Further reading and video