Bash 스크립트 빈 매개변수 테스트

Bash 스크립트 빈 매개변수 테스트

다음 논리를 사용하여 간단한 스크립트를 작성하려고 합니다. 첫 번째 인수가 유효한 일반 파일이면 for 루프를 실행하고, 인수가 제공되지 않으면 "code2"를 실행하고, 그렇지 않으면 "code3"을 실행합니다. 아래 스크립트는 제게는 잘 작동하는 것 같지만 인수 없이 실행하면 중단됩니다.

#!/bin/bash

if [ -f $1 ]; then
  for i in `cat $1`
  do
    <something>
  done
elif [ $# -eq 0 ]; then
  "code2"
else
  "code3"
fi

이것은 디버그 출력이며, 마지막에 멈췄습니다.

bash -x myscript
+ '[' -f ']'
++ cat

매개변수를 제공하지 않았는데 왜 여전히 첫 번째 if-then 흐름에 도달합니까? 저는 bash 스크립팅을 처음 접했습니다. 어떤 도움이라도 대단히 감사하겠습니다.

답변1

변수를 참조하지 않으면 "$1"아무것도 없고 사라집니다. 그런 다음 실행되는 코드는 다음과 같습니다( -x셸 옵션에 보고됨).

[ -f ]

여기서 -f길이가 0이 아닌 문자열로 인해 실제 테스트가 해당 섹션을 실행하게 됩니다 then.

(적어도) 다음과 같이 작성해야 합니다.

[ -f "$1" ]

빈 인수가 있으면 다음과 같습니다.

[ -f "" ]

파일 일치 실패를 보고합니다 "".

또 다른 대안은 매개변수 확장을 사용하는 것입니다(외부 참조가 필요하지 않음).

[ -f ${1:-""} ]

""값이 $1null이거나 비어 있으면 로 확장됩니다.

그리고 파일 줄을 반복하기 위해 for 루프를 수행하지 마십시오. while read루프 사용을 고려해야 합니다

#!/bin/sh

if [ -f ${1:-""} ]; then
  while read -r line; do
      echo '<something>'
  done <"$1"
elif [ "$#" -eq 0 ]; then
  echo "code2"
else
  echo "code3"
fi

답변2

간단한 대답은 존재하지 않는 것에 대해서도 $1인용되지 않았기 때문입니다(또한 문제의 일부). 쉘은 표현식을 다음과 같이 취급하며 [ -f ]여기에 표시되는 -f것은 [플래그로 인식되지 않고 단지 단일 "표현식 ". 실제로는 다음과 같습니다.

$ [ abracadabra  ] && echo "success"
success

그리고 매뉴얼을 인용합니다 test(모르는 경우 별칭임 [).

   An  omitted  EXPRESSION  defaults  to false.  Otherwise, EXPRESSION is true or false and sets exit
   status.  It is one of:

   ( EXPRESSION )
          EXPRESSION is true

표현식을 인용하면 출력을 추적할 때 다음과 같이 보일 것입니다. 즉, 실제로 빈 문자열을 기존 파일 이름으로 평가하려고 시도합니다.

$ (set -x; [ -f "$this_var_doesnt_exist"  ] && echo "hi" )
+ '[' -f '' ']'

관련 정보