从源脚本扩展getopts

时间:2019-12-09 22:57:57

标签: bash shell

我正在尝试从源脚本扩展getopts,如下所示。 如果传入了除a,b,c,d以外的其他选项,则需要打印“无效选项”并退出。

script_a.sh:

#!/bin/bash
script_a_getopts() {
   while getopts 'a:b:' OPT; do
      case "$OPT" in
         a)
           a=$OPTARG
           ;;
         b)
           b=$OPTARG
           ;;
         *)
           echo "invalid option"
           exit 1
           ;;
      esac
   done
}

script_b.sh

#!/bin/bash
source script_a.sh
while getopts ':c:d:' OPT; do
case "$OPT" in
c)
   c=$OPTARG
   ;;
d)
   d=$OPTARG
   ;;
 [?])
   script_a_getopts $@
esac
done


echo "a=$a"
echo "b=$b"
echo "c=$c"
echo "d=$d"

当我运行脚本时,它没有按预期运行,很明显我在弄错。

$ ./script_b.sh -c cat -d dog -a apple -b boy
a=
b=
c=cat
d=dog

通过-x时不会引发错误。

$ ./script_b.sh -x
a=
b=
c=
d=

1 个答案:

答案 0 :(得分:0)

简短的回答:您必须在调用script_a_getopts之前回退OPTIND。

case "$OPT" in
c)
   c=$OPTARG
   ;;
 ...
 [?])
   let OPTIND--
   script_a_getopts $@
esac
done

长答案:

getopts跟踪使用OPTIND变量处理了哪些参数。当顶部getopts识别出未知项目时,它已经通过将OPTIND移至下一个参数来“消耗”该项目。为了使script_a_getopts处理该参数,需要将OPTIND回滚以指向未处理的参数。

let OPTIND--将允许重新处理无法识别的参数。

旁注,如果要允许按任意顺序放置选项(-c cat -a apple -d dog -b boy),则必须在script_a_getopts中重复相同的内容。这将需要改进script_a_getopts函数中的错误处理。