source

Bash 스크립트에 대한 매개 변수 유효성 검사

ittop 2023. 4. 27. 22:44
반응형

Bash 스크립트에 대한 매개 변수 유효성 검사

저는 많은 폴더가 필요하지 않게 되었을 때 폴더를 제거하는 프로세스를 자동화하는 데 도움이 되는 기본적인 방법을 생각해 냈습니다.

#!/bin/bash
rm -rf ~/myfolder1/$1/anotherfolder
rm -rf ~/myfolder2/$1/yetanotherfolder
rm -rf ~/myfolder3/$1/thisisafolder

이는 다음과 같이 유발됩니다.

./myscript.sh <{id-number}>

문제는 만약 당신이 입력하는 것을 잊는다면.id-number (내가 바로 그때 했던 것처럼), 그러면 정말로 삭제하고 싶지 않은 많은 것들이 잠재적으로 삭제될 수 있습니다.

명령줄 매개 변수에 유효성 검사 형식을 추가할 수 있는 방법이 있습니까?저의 경우, 스크립트를 계속하기 전에 a) 매개 변수가 하나 있고, b) 숫자이고, c) 폴더가 있는지 확인하는 것이 좋습니다.

#!/bin/sh
die () {
    echo >&2 "$@"
    exit 1
}

[ "$#" -eq 1 ] || die "1 argument required, $# provided"
echo $1 | grep -E -q '^[0-9]+$' || die "Numeric argument required, $1 provided"

while read dir 
do
    [ -d "$dir" ] || die "Directory $dir does not exist"
    rm -rf "$dir"
done <<EOF
~/myfolder1/$1/anotherfolder 
~/myfolder2/$1/yetanotherfolder 
~/myfolder3/$1/thisisafolder
EOF

편집: 처음에 디렉터리가 있는지 확인하는 부분을 놓쳐서 스크립트를 완성하면서 추가했습니다.또한 코멘트에서 제기된 문제를 해결했습니다. 정규 표현을 수정하고, 에서 전환했습니다.==eq.

. 바시즘을; 않면왜그사실중바다하하냐요이로제것은다는지시용것즘떠한도어하은는스대용휴▁as▁thisix왜면하▁because▁actually▁important냐▁is이,▁it▁shouldisms▁which,것▁any▁be▁bash▁pos▁script;▁portable▁aix,다중▁compliant하실요▁tell▁doesn'이로./bin/sh는 Ubuntu입니다.dash즘은아가 .bash.

위의 답변만큼 방탄은 아니지만 여전히 효과적입니다.

#!/bin/bash
if [ "$1" = "" ]
then
  echo "Usage: $0 <id number to be cleaned up>"
  exit
fi

# rm commands go here

sh에 의한 .Brian Campbell고귀하고 잘 실행되었지만, 몇 가지 문제가 있어서, 나는 내 것을 제공하려고 생각했습니다.bash해결책

sh아래쪽:

  • 의기기울의 ~/foo병원 내부의 홈 디렉토리로 확장되지 않습니다.그리고 그것이 그것에 의해 읽혀질 때도.read에 됨.rm진술.그 말은 당신이 받을 수 있다는 것을 의미합니다.No such file or directory오류
  • grep기본적인 운영을 위한 것들은 멍청합니다.특히 바시의 "무거운" 무게를 피하기 위해 쓰레기 껍질을 사용할 때는 더욱 그렇습니다.
  • 예를 들어 그의 매개 변수 확장과 관련하여 몇 가지 인용 문제도 발견했습니다.echo.
  • 줄이 수 없습니다. ( new line이 포함된 파일 이름에는 .)sh그것들에 대처할 수 있습니다 - 그것이 제가 거의 항상 선호하는 이유입니다.bash그것은 훨씬 더 방탄이고 잘 사용하면 활용하기가 어렵습니다).

예, 용을 사용합니다./bin/sh당신의 해시방은 당신이 피해야 한다는 것을 의미합니다.bash어떤 대가를 치르더라도, 당신은 모든 것을 사용할 수 있습니다.bash우분투에서조차 당신이 좋아하는 것이 아닙니다. 당신이 정직하고 표현할 때.#!/bin/bash맨 위에

자, 여기 있습니다.bash더 작고, 더 깨끗하고, 더 투명하고, 아마도 "무결"하며, 더 방탄이 가능한 솔루션입니다.

[[ -d $1 && $1 != *[^0-9]* ]] || { echo "Invalid input." >&2; exit 1; }
rm -rf ~/foo/"$1"/bar ...
  1. 주변의 인용문을 확인합니다.$1에 시대에rm진술!
  2. -d다음과 같은 경우에도 검사가 실패합니다.$1비어 있습니다. 그래서 그것은 두 개의 수표를 하나로 묶은 것입니다.
  3. 저는 어떤 이유로 정규 표현을 피했습니다.사해야하경우를 해야 하는 =~ 합니다. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ?어쨌든, 저와 같은 글러브는 항상 선호되고 훨씬 더 많은 버전의 bash에서 지원됩니다.

의 저는사것입다니할를용▁bash것을 사용할 것입니다.[[:

if [[ ! ("$#" == 1 && $1 =~ ^[0-9]+$ && -d $1) ]]; then 
    echo 'Please pass a number that corresponds to a directory'
    exit 1
fi

는 이 FAQ가 좋은 정보원이라는 을 알게 되었습니다.

페이지 (man )man test할 수 "bash"는 "bash"와 같습니다.다른 프로그래밍 언어에서와 마찬가지로 입력 유효성 검사를 위해 스크립트(또는 함수)의 시작 부분에 이러한 플래그를 사용합니다.예:

if [ -z $1 ] ; then
  echo "First parameter needed!" && exit 1;
fi

if [ -z $2 ] ; then
  echo "Second parameter needed!" && exit 2;
fi

사용하다set -u이로 인해 설정되지 않은 인수 참조가 스크립트에 즉시 실패합니다.

다음 기사를 참조하십시오.강력한 Bash Shell 스크립트 작성 - David Pashley.com

빈 문자열을 테스트하려면 '-z'를 사용하고 디렉터리를 확인하려면 '-d'를 사용합니다.

if [[ -z "$@" ]]; then
    echo >&2 "You must supply an argument!"
    exit 1
elif [[ ! -d "$@" ]]; then
    echo >&2 "$@ is not a valid directory!"
    exit 1
fi

디렉토리 유효성 검사를 사용하거나 사용하지 않는 하나의 라이너 Bash 인수 유효성 검사

여기 저에게 효과가 있었던 몇 가지 방법이 있습니다.글로벌 스크립트 네임스페이스에서 사용할 수 있습니다(글로벌 네임스페이스에 있는 경우 기본 제공 함수 변수를 참조할 수 없음).

빠르고 더러운 원 라이너

: ${1?' You forgot to supply a directory name'}

출력:

./my_script: line 279: 1: You forgot to supply a directory name

팬시어 - 공급 기능 이름 및 사용

${1? ERROR Function: ${FUNCNAME[0]}() Usage: " ${FUNCNAME[0]} directory_name"}

출력:

./my_script: line 288: 1:  ERROR Function: deleteFolders() Usage:  deleteFolders directory_name

현재 기능을 복잡하게 만들지 않고 복잡한 검증 로직 추가

인수를 수신하는 함수 또는 스크립트 내에 다음 행을 추가합니다.

: ${1?'forgot to supply a directory name'} && validate $1 || die 'Please supply a valid directory'

그런 다음 다음 다음과 같은 작업을 수행하는 유효성 검사 기능을 만들 수 있습니다.

validate() {

    #validate input and  & return 1 if failed, 0 if succeed
    if [[ ! -d "$1" ]]; then
        return 1
    fi
}

실패 시 스크립트를 중단시키는 다이 함수

die() { echo "$*" 1>&2 ; exit 1; }

추가 인수의 경우 형식을 복제하여 줄을 추가합니다.

: ${1?' You forgot to supply the first argument'}
: ${2?' You forgot to supply the second argument'}

다음과 같은 작업을 수행하여 지점 a와 b를 압축적으로 검증할 수 있습니다.

#!/bin/sh
MYVAL=$(echo ${1} | awk '/^[0-9]+$/')
MYVAL=${MYVAL:?"Usage - testparms <number>"}
echo ${MYVAL}

그래서 우리는...

$ ./testparams.sh 
Usage - testparms <number>

$ ./testparams.sh 1234
1234

$ ./testparams.sh abcd
Usage - testparms <number>

이 방법은 sh에서 잘 작동할 것입니다.

오래된 게시물이지만 어쨌든 기여할 수 있다고 생각했습니다.

스크립트는 거의 필요하지 않으며 명령줄에서 와일드카드를 어느 정도 허용하여 수행할 수 있습니다.

  1. 야성적인 어디서나 일치합니다.하위 "폴더"가 발생하면 제거합니다.

    $ rm -rf ~/*/folder/*
    
  2. 셸 반복.한 줄로 특정 사전 및 사후 폴더를 제거합니다.

    $ rm -rf ~/foo{1,2,3}/folder/{ab,cd,ef}
    
  3. 셸 반복 + var(BASH 테스트 완료)

    $ var=bar rm -rf ~/foo{1,2,3}/${var}/{ab,cd,ef}
    

언급URL : https://stackoverflow.com/questions/699576/validating-parameters-to-a-bash-script

반응형