예기치 않은 태그 'else' 근처에 구문 오류가 있습니다.

예기치 않은 태그 'else' 근처에 구문 오류가 있습니다.

상태 정보와 기타 다양한 텍스트로 채워진 txt 파일의 특정 부분을 삭제하는 스크립트를 만들려고 합니다. 주요 if 문을 끝낼 수 없습니다. 추가적으로, output.txt를 생성하는 스크립트에 date 명령을 넣어서 가장 오래된 상태 정보를 제거하려고 했습니다. 가장 오래된 정보를 삭제하게 하는 방법이 있나요? 나는 주로 if 문이 끝나기를 원합니다. 감사해요. (또한 원래 else if 를 elif 로 사용했지만 결과는 동일했습니다.)

./count.sh: 30행: else' ./count.sh: line 30:예상치 못한 표시 근처에서 구문 오류가 발생했습니다.

WCOUNT=$(wc -l output.txt $1 | awk '{print $1}')

if [[ $WCOUNT -gt 50 ]]; then 

    if [[ "grep CLIENTSTART output.txt" != null ]]; then
        echo $WCOUNT
        sed -i '/\*\*\*CLIENTSTART/,/CLIENTEND\*\*\*/ d' output.txt
        echo $WCOUNT

    else if [[ -n "grep DHCPSTART output.txt" ]]; then          

        echo $WCOUNT
        sed -i '/\*\*\*DHCPSTART/,/DHCPEND\*\*\*/ d' output.txt     
        echo $WCOUNT

    else if [[ -n "grep DNSSTART output.txt" ]]; then
        echo $WCOUNT
        sed -i '/\*\*\*DNSSTART/,/DNSEND\*\*\*/ d' output.txt
        echo $WCOUNT

    else if [[ -n "grep WEBSTART output.txt" ]]; then
        echo $WCOUNT
        sed -i '/\*\*\*WEBSTART/,/WEBEND\*\*\*/ d' output.txt
        echo $WCOUNT

    else
        echo "Cannot help you"
    fi

else
    echo "You're good, homie.  It's under 500"

fi

답변1

여기서 문제는 else if대신 을 사용하면 elif프로그램에 중첩이 추가되고 fi추가 조건문을 종료하기 위해 더 많은 문을 추가해야 한다는 것입니다.

다음은 내가 의미하는 바를 보여주기 위해 약간 다른 들여쓰기가 포함된 프로그램의 편집된 버전입니다.

WCOUNT=$(wc -l output.txt $1 | awk '{print $1}')

if [[ $WCOUNT -gt 50 ]]; then 
    if [[ "grep CLIENTSTART output.txt" != null ]]; then
        echo $WCOUNT
        sed -i '/\*\*\*CLIENTSTART/,/CLIENTEND\*\*\*/ d' output.txt
        echo $WCOUNT
    else 
        if [[ -n "grep DHCPSTART output.txt" ]]; then          
            echo $WCOUNT
            sed -i '/\*\*\*DHCPSTART/,/DHCPEND\*\*\*/ d' output.txt     
            echo $WCOUNT
        else 
            if [[ -n "grep DNSSTART output.txt" ]]; then
                echo $WCOUNT
                sed -i '/\*\*\*DNSSTART/,/DNSEND\*\*\*/ d' output.txt
                echo $WCOUNT
            else 
                if [[ -n "grep WEBSTART output.txt" ]]; then
                    echo $WCOUNT
                    sed -i '/\*\*\*WEBSTART/,/WEBEND\*\*\*/ d' output.txt
                    echo $WCOUNT
                else
                    echo "Cannot help you"
                fi
            fi
        fi
    fi
else
    echo "You're good, homie.  It's under 500"

fi

또는 다음을 사용할 수 있습니다.elif

WCOUNT=$(wc -l output.txt $1 | awk '{print $1}')

if [[ $WCOUNT -gt 50 ]]; then 

    if [[ "grep CLIENTSTART output.txt" != null ]]; then
        echo $WCOUNT
        sed -i '/\*\*\*CLIENTSTART/,/CLIENTEND\*\*\*/ d' output.txt
        echo $WCOUNT

    elif [[ -n "grep DHCPSTART output.txt" ]]; then          

        echo $WCOUNT
        sed -i '/\*\*\*DHCPSTART/,/DHCPEND\*\*\*/ d' output.txt     
        echo $WCOUNT

    elif [[ -n "grep DNSSTART output.txt" ]]; then
        echo $WCOUNT
        sed -i '/\*\*\*DNSSTART/,/DNSEND\*\*\*/ d' output.txt
        echo $WCOUNT

    elif [[ -n "grep WEBSTART output.txt" ]]; then
        echo $WCOUNT
        sed -i '/\*\*\*WEBSTART/,/WEBEND\*\*\*/ d' output.txt
        echo $WCOUNT

    else
        echo "Cannot help you"
    fi

else
    echo "You're good, homie.  It's under 500"

fi

(또한 약간 까다롭게 말하면 50개 이상의 행이 있는지 확인하고 있지만 출력 메시지에는 500개 행을 확인한다고 나와 있습니다. 기술적으로는 500개 미만의 행이 있지만 이는 약간 오해의 소지가 있습니다. p)

편집: 다른 사람들이 지적했듯이 이렇게 하면 구문 오류가 해결되지만 스크립트에는 여전히 다른 문제가 있습니다. 나는 또한 그들의 의견/답변을 읽는 것이 좋습니다.

답변2

구문 오류가 발생하는 이유는 명령문 else ifelif.

두 개의 파일이 제공되면 wc -l세 줄의 출력이 생성됩니다.

$ wc -l .profile .profile
      30 .profile
      30 .profile
      60 total

이는 따옴표가 없는 첫 번째 iftest에 영향을 미치며 $WCOUNT확장 시 또 다른 구문 오류가 발생합니다.

당신은 원할 수도 있습니다

WCOUNT=$( wc -l <output.txt )

또한 문자열에 대한 여러 가지 테스트가 있습니다 "grep DHCPSTART output.txt".언제나그건 진실이야.

파일에 문자열이 있는지 테스트하려면 다음을 사용하십시오.

if grep -Fq 'fixed string' filename; then

예를 들어

if grep -Fq 'CLIENTSTART' output.txt; then
   # do something
elif grep -Fq 'DHCPSTART' output.txt; then
   # do something
else
   # do something
fi

실제 출력 생성을 중지합니다 -q. grep종료 상태는 문자열이 발견되었는지 알려주며, 이것이 if이 명령문을 작동하게 만듭니다(플래그는 또한 grep첫 번째 일치에서 파일 읽기가 중지되도록 합니다). 이 -F플래그를 사용하면 grep지정된 패턴이 정규 표현식이 아닌 고정 문자열로 처리됩니다.


스크립트 내부 구조에 대한 제안:

tmpfile=$(mktemp)

for string in CLIENT DHCP DNS WEB; do
    if grep -Fq "${string}START" output.txt; then
        sed "/\*\*\*${string}START/,/${string}END\*\*\*/d" \
            output.txt >"$tmpfile"
        break
    fi
done

if [ -s "$tmpfile" ]; then
    mv "$tmpfile" output.txt
else
    echo 'Can not help you'
    rm -f "$tmpfile"
fi

[ -s "$tmpfile" ]파일 $tmpfile크기가 0보다 크면( 호출 시의 크기) sed테스트가 성공합니다 .

forbreak논리 를 모방 if ... then ... elif하지만 보다 간결한 방식으로 루프를 사용합니다.

관련 정보