arguments - Getopt not parsing well bash -


i wrote script in bash serving template several monitors. choose getopt in order able use long options on cli. however, have problems implementing correctly.

the whole script lot longer, relevant part:

#!/bin/bash # # function #   main # description #   main function. called here # args #   nothing # # return code #   nothing # # main function. called here main() {   # parse options , arguments   parse_options "${@}"    # check if interval set valid number   check_interval }  # # function #   check_interval # description #   checks if number valid # args #   1: number checked # return code #   0: valid #   1: invalid # check_interval() {   # don't have worry if interval set @ all, because getopt doing   if ( ! check_number_pos ${arginterval} );     echo "error: invalid interval: ${arginterval}"     show_usage     exit 2   fi }  # # function #   show_usage # description #   usage section. showing usage according docopt standards # args #   nothing # return code #   nothing # show_usage() {   echo "usage:"                                                                           >&2   echo "  ${this_script_name} -i|--interval=<interval in s> [-r | --random [--randomwait=<wait in s>]] [-v|--verbose] [-d|--debug] [--colors]"  >&2   echo "  ${this_script_name} [-h|--help]"                                                >&2 }  # # function #   check_number_pos # description #   checks if number valid , positive # args #   1: number checked # # return code #   0: valid , positive #   1: invalid or negative # check_number_pos() {   local returnval   if [[ "${1}" =~ ^[0-9]+$ ]];     returnval=0   else     returnval=1   fi   return ${returnval} }  # # function #   parse_options # description #   parse options command line # args #   @: arguments , options given @ cli # return code #   nothing # parse_options() {   # use getopt(1) parse options according posix. if fails, error shown, , we're showing usage , exit   # add new options here , in case-statement below.   # short options must added in 'options'-section   # long options must added in 'longoptions'-section   # short options must have long equivalent   # --name set error-output not show 'getopt'-errors neat <application name>-errors   # options , longoptions have following format:   # <letter>       option without argument   # <letter>:      option mandarory argument   # <letter>::     option optional argument <- broken short options , long options without '='. don't use it!   local -r getopt=$(getopt --name ${0} --options hrvdi: --longoptions help,random,verbose,debug,colors,randomwait:,interval: -- "${@}")    if [ ${?} != 0 ];     echo "error: error while getting arguments"     show_usage     exit 127;   fi    # no options or arguments given. show usage.   if [[ "${getopt}" == " --" ]];     show_usage     exit 127;   fi    # evaluate getopt. need have quotes in output of getopt(1) interpreted.   eval set -- "${getopt}"    # walk through options. don't put code in here, point function or set variable.   # please note, new options need added here in getopt line above.   # note: shift removes first value string, option removed getopt-string, , argument available in $1   # after using argument, please shift again, next option first value in getopt   while true;       case "${1}" in       -i|--interval)         shift         arginterval=${1}         shift         ;;       -r|--random)         shift         flagrandom=1         ;;       --randomwait)         shift         flagrandom=1         argrandom=${1}         shift         ;;       -v|-d|--verbose|--debug)         flagdebug=1         shift         ;;       --colors)         flagcolors=1         shift         ;;       -h|--help)         #show_help         exit 0         ;;       --)         shift         break         ;;       -*)     echo "error: unrecognized option ${1}"         show_usage         exit 127         ;;       *)         show_usage         exit 127         ;;     esac   done }  #call main function after main "${@}" 

now, when call script right way, goes smooth:

$ ./test1.sh -i 10 

when forget argument, want:

$ ./test1.sh -i ./test1.sh: option requires argument -- 'i' usage:    -i|--interval=<interval in s> [-r | --random [--randomwait=<wait in s>]] [-v|--verbose] [-d|--debug] [--colors]    [-h|--help] 

but when forget argument , add one, fails:

$ ./test1.sh -i --colors error: invalid interval: --colors usage:    -i|--interval=<interval in s> [-r | --random [--randomwait=<wait in s>]] [-v|--verbose] [-d|--debug] [--colors]    [-h|--help] 

this happens because check if interval integer, other purposes, dangerous thing how can change case not read options arguments? far getopt not serving me well, because ran bug/feature well: 'optional argument' (::) not working expected works when used '=' between option , argument.

versions:

$ getopt -v getopt (enhanced) 1.1.4 $ bash --version gnu bash, version 4.1.2(1)-release (x86_64-redhat-linux-gnu) 

getopt doesn't know semantics of options. knows, --colors valid argument -i option. have check these kinds of errors yourself, unfortunately, if want handle them.

 while true;       case "${1}" in       -i|--interval)         shift         arginterval=${1}         if [[ $arginterval = -* ]];             printf 'you appear have forgotten interval argument before %s option\n' "$arginterval" >&2             exit 1         fi         shift         ;;      ... 

Comments

Popular posts from this blog

sql - invalid in the select list because it is not contained in either an aggregate function -

Angularjs unit testing - ng-disabled not working when adding text to textarea -

How to start daemon on android by adb -