long options example
:: Code :: #!/bin/bash
PROGNAME=${0##*/} PROGVERSION=0.9.0 usage() { cat << EO Usage: $PROGNAME [options] $PROGNAME -o <version> -c Increase the .deb file's version number, noting the change in the Options: EO cat <<EO | column -s\& -t -h|--help & show this output -V|--version & show version information EO } SHORTOPTS="hvta:" LONGOPTS="help,version,test,longi:" ARGS=$(getopt -s bash --options $SHORTOPTS \ --longoptions $LONGOPTS --name $PROGNAME -- "$@" ) eval set -- "$ARGS" while true; do case $1 in -h|--help) usage exit 0 ;; -v|--version) echo "$PROGVERSION" ;; -a) shift echo "$1" ;; --longi) shift echo "$1" ;; --test) echo "test" ;; --) shift break ;; *) shift break ;; esac shift done Back to top |
Just a reminder:
while getopts abd:eF:gHiJ:klm opt .... Allows near trivial handling and testing and validation of OPTARGS, the extra option arg handler built in from getopts. Not to mention that in most cases: say, -k 23 OR -k23 can be used. This is the reason I realiy like getops, by the way. But I did have a brainstorm the other day: Have an option that supports long opts as OPTARGS-- ie: -L <version|help|something|something-else|and-so-on> Then getopts would happily treat -L as the option and you'd simply handle each long option as an OPTARG for getopts. The real problem here, however, is that getopts itself should be extended to handle both short and long options, and that extension I do not think is rocket science, simply add something like: abE:v[version]vh[help] and use the same : construct to signal that the long opt needs more. Or use something even more intuitive: abE:s[something=]v[version] where the = would mean it needs further data. I think, actually, getopts could be used in an internal function somehow to do this, but I'm not sure. I've really had excellent luck so far using only single letters, it works very well, and with say: -L <something|somethingelse=*> you could simply use: L) case $OPTARG in something)....;; somethingelse=*)....;; esac It's totally absurd that getopts isn't built up to handle all common option types, it really would not be at all hard to do that, it just requires thinking outside their current box a bit. this is so obvious to me, and would be so trivially easy to program in, relatively speaking, that you could at one swoop let everyone in the world suddenly have easy reliable intuitive option handling for bash, heaven forbid... Back to top |
Actually the Bash builtin getopts function can be used to parse long options by putting a dash character followed by a colon into the optspec. For an example script see: stackoverflow.com/questions/402377/using-getopts-in-bash-shell-script-to-get-long-and-short-command-line-options/7680682#7680682
Back to top |
arvid, thanks for updating and suggesting a fix for this issue. I am actually kicking myself for never having tried this, I use a similar method for other non standard characters, so I really should have tried using -: as well.
That's a nice and reasonably elegant solution, I'll have to test it out, I use a lot of options. Sadly this method wouldn't support something like this: d|debug)DEBUG_FLAG=true;; so is essentially a hack to get around a limitation, but for extra args it's a nice simple way to do it. It would really be nice, however, if getopts would simply be extended to support long args natively without hacks. Back to top |
if [ "$opt" == "-" ]; then opt=$OPTARG; fi;
How about using a pattern like the following to enable both long and short options to be processed by the same case statement?
#!/bin/bash while getopts "h-:" opt; do if [ "$opt" == "-" ]; then opt=$OPTARG; fi; case $opt in h|help) echo "You need help I am not trained or licensed to provide." exit 0 ;; *) echo "Invalid option" exit 1 ;; esac done echo You gotta give me some options... Back to top |
All times are GMT - 8 Hours |