쉘 스크립트에 대한 특별한 검증이 필요합니다.

쉘 스크립트에 대한 특별한 검증이 필요합니다.

실행 시 많은 옵션을 갖게 되는 bash 스크립트를 만들고 싶습니다.

# script.sh  --dry-run --user <parameter1> --pass <parameter2>

getopt 옵션에 대해 들었지만 그 중 하나만 작성할 수 있거나 --user or --password전부 --dry-run는 작성할 수 없는 것 같습니다. 기본적으로 이것을 --user parameter1input1과 input2로 만들고 싶고 , 옵션이 있는 경우 프로덕션 코드 대신 테스트 실행 코드만 실행되는 --pass parameter2특별한 경우를 만들고 싶습니다.--dry-run

#!/bin/bash
user=$1
pass=$2

help() {
    cat<<EOF
Usage : $0 --dry-run --user <user_id> --pass <password>
you can specify --dry-run or --production
EOF
}

[ ${3} ] || help

function dry_run() {
    // --dry-run code 
}

function production() {
   // --production code 
}

--dry-run옵션이 '예' --dry-run이면 함수를 실행하고 그렇지 않으면 함수를 dry_run()실행하는지 확인하고 싶습니다 . production()하지만 옵션과 유효성 검사를 작성하는 방법은 무엇입니까?

답변1

당신이 하고 있는 일을 내가 이해한다면, 당신은 이것을 할 수 있습니다 getopt:

#!/bin/bash

PARAMS=$(getopt -l dry-run,production,user:,pass: -n $0 "" -- "$@")
if [ $? != 0 ]; then exit 1; fi
eval set -- "$PARAMS"

dryrun=false

while [ -n "$1" ]; do
    case "$1" in
        --dry-run) dryrun=true; shift;;
        --production) dryrun=false; shift;;
        --user) user="$2"; shift 2;;
        --pass) pass="$2"; shift 2;;
        --) shift;;
        *) exit 1;;
    esac
done

if [ $dryrun = true ]; then
    ...
else
    ...
fi

--dry-run동시에 AND 지정을 허용하지 않거나 --productionAND가 필요한 경우 --user처리를 더 추가할 수 있습니다 .--password

답변2

getopt실제로 긴 스크립트 옵션을 처리할 필요는 없습니다 . 내장 getopts함수도 이 작업을 수행할 수 있습니다.(보통 서브쉘 없음). 비결은 -옵션으로 사용하는 것입니다. 그런 식으로--dry-run (예를 들어)되고 .optvar=-OPTARG=-dry-run다음은 이 경우에 구체적으로 이를 수행하는 방법에 대한 기능적 예입니다.

#!/bin/sh
help(){ echo usage; }                       #dummy help
unset   user dryrun pass _o o               #ensure all flag vars are unset
while   getopts :-:u:p:d o              &&  #getopts loop
        o=${o#-}        _o=${o:+$OPTARG}    #empty $o if $o==-
do      case            $o$OPTARG       in  #test concatenated $o$OPTARG
        (u*|-user)      user=${_o:-$2}  ;;  #set $user to $_o or $2
        (p*|-pass)      pass=${_o:-$2}  ;;  #ditto for $pass
        (d*|-dryrun)    o=d dryrun=1    ;;  #no $OPTARG either way - o=d base
        (*)             !  help         ;;  #no usage options met - opt error
        esac || exit                        #quit with error if opt == ! help
        shift "$((!${#o}+(OPTIND-(OPTIND=1))))"  #shift params as they're read
done

이는 그대로 작동합니다. 사실 저는 여러 가지 다른 옵션을 시도했습니다. 예를 들어:

~/getopts.sh -p-user --user me -uyou -d --dry-run

... #!/bin/sh -xbangline으로 실행할 때 이것을 내 stderr에 인쇄합니다.

+ unset user dryrun pass _o o
+ getopts :-:u:p:d o
+ o=p _o=-user
+ pass=-user
+ shift 1
+ getopts :-:u:p:d o
+ o= _o=
+ user=me
+ shift 2
+ getopts :-:u:p:d o
+ o=u _o=you
+ user=you
+ shift 1
+ getopts :-:u:p:d o
+ o=d _o=
+ o=d dryrun=1
+ shift 1
+ getopts :-:u:p:d o
+ o= _o=
+ o=d dryrun=1
+ shift 1
+ getopts :-:u:p:d o

getopts루프를 완료 한 후에는 다음을 수행할 수 있습니다.

[ "$((dryrun))" -eq 0 ] && production || dryrun

production()... 및 함수를 선언한 경우 dryrun(). 필요에 따라 지정 $pass및/또는 할당된 명령줄 값을 찾습니다 . $user명령줄에서 이들 중 하나라도 선언되지 않은 경우 다음과 같이 참조하는 것을 고려할 수 있습니다.

echo "${user=default_username}" "${pass=default_password}"

...모든 기반을 커버하기 위한 것입니다.

관련 정보