Last active
September 9, 2024 14:13
-
-
Save deshion/10d3cb5f88a21671e17a to your computer and use it in GitHub Desktop.
Parse command line options for a shell script (POSIX)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/sh | |
# POSIX | |
# Reset all variables that might be set | |
file= | |
verbose=0 # Variables to be evaluated as shell arithmetic should be initialized to a default or validated beforehand. | |
while :; do | |
case $1 in | |
-h|-\?|--help) # Call a "show_help" function to display a synopsis, then exit. | |
show_help | |
exit | |
;; | |
-f|--file) # Takes an option argument, ensuring it has been specified. | |
if [ -n "$2" ]; then | |
file=$2 | |
shift | |
else | |
printf 'ERROR: "--file" requires a non-empty option argument.\n' >&2 | |
exit 1 | |
fi | |
;; | |
--file=?*) | |
file=${1#*=} # Delete everything up to "=" and assign the remainder. | |
;; | |
--file=) # Handle the case of an empty --file= | |
printf 'ERROR: "--file" requires a non-empty option argument.\n' >&2 | |
exit 1 | |
;; | |
-v|--verbose) | |
verbose=$((verbose + 1)) # Each -v argument adds 1 to verbosity. | |
;; | |
--) # End of all options. | |
shift | |
break | |
;; | |
-?*) | |
printf 'WARN: Unknown option (ignored): %s\n' "$1" >&2 | |
;; | |
*) # Default case: If no more options then break out of the loop. | |
break | |
esac | |
shift | |
done | |
# if --file was provided, open it for writing, else duplicate stdout | |
if [ -n "$file" ]; then | |
exec 3> "$file" | |
else | |
exec 3>&1 | |
fi | |
# Rest of the program here. | |
# If there are input files (for example) that follow the options, they | |
# will remain in the "$@" positional parameters. |
Does this require options to be specified before positional arguments?
Yes
Actually, POSIX does not allow long options: "Each option name should be a single alphanumeric character". Besides, "One or more options without option-arguments, followed by at most one option that takes an option-argument, should be accepted when grouped behind one '-' delimiter." (reference)
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Does this require options to be specified before positional arguments?