일치하는` " '을 (를) 찾는 중 예기치 않은 EOF-bash 스크립트


37

방금 bash 스크립트를 작성했으며 항상이 EOF 오류가 발생합니다.

그래서 여기 내 스크립트가 있습니다 (OS X에서만 작동합니다).

#!/bin/bash

#DEFINITIONS BEGIN
en_sq() {
    echo -e "Enabling smart quotes..."
    defaults write NSGlobalDomain NSAutomaticQuoteSubstitutionEnabled -bool true
    status=$(defaults read NSGlobalDomain NSAutomaticQuoteSubstitutionEnabled -bool)
            if [ "$status" = "1" ]
                then
                    echo -e "Success! Smart quotes are now enabled."
                    SUCCESS="TRUE"
            else
                echo -e "Sorry, an error occured. Try again."
            fi
}
di_sq() {
    echo -e "Disabling smart quotes..."
    defaults write NSGlobalDomain NSAutomaticQuoteSubstitutionEnabled -bool false
    status=$(defaults read NSGlobalDomain NSAutomaticQuoteSubstitutionEnabled -bool)
            if [ "$status" = "0" ]
                then
                    echo -e "Success! Smart quotes are now disabled."
                    SUCCESS="TRUE"
            else
                echo -e "Sorry, an error occured. Try again."
            fi
}
en_sd() {
    echo -e "Enabling smart dashes..."
    defaults write NSGlobalDomain NSAutomaticDashSubstitutionEnabled -bool true
    status=$(defaults read NSGlobalDomain NSAutomaticDashSubstitutionEnabled -bool)
            if [ "$status" = "1" ]
                then
                    echo -e "Success! Smart dashes are now enabled."
                    SUCCESS="TRUE"
            else
                echo -e "Sorry, an error occured. Try again."
            fi
}
di_sd() {
    echo -e "Enabling smart dashes..."
    defaults write NSGlobalDomain NSAutomaticDashSubstitutionEnabled -bool false
    status=$(defaults read NSGlobalDomain NSAutomaticDashSubstitutionEnabled -bool)
            if [ "$status" = "0" ]
                then
                    echo -e "Success! Smart dashes are now disabled."
                    SUCCESS="TRUE"
            else
                echo -e "Sorry, an error occured. Try again."
            fi
}
#DEFINITIONS END
#---------------

#BEGIN OF CODE with properties
#This is only terminated if the user entered properties (eg ./sqd.sh 1 1)
if [ "$1" = "1" ]
    then
        en_sq
    elif [ "$1" = "0" ]
        then
            di_sq
fi

if [ "$2" = "1" ]
    then
        en_sd
        #exit 0 if both, $1 and $2 are correct entered and processed.
        exit 0
    elif [ "$1" = "0" ]
        then
            di_sd
            #exit 0 if both, $1 and $2 are correct entered and processed.
            exit 0
fi
#END OF CODE with properties
#---------------------------


#BEGIN OF CODE without properties
#This is terminated if the user didn't enter two properties
echo -e "\n\n\n\n\nINFO: You can use this command as following: $0 x y, while x and y can be either 0 for false or 1 for true."
echo -e "x is for the smart quotes, y for the smart dashes."
sleep 1
echo -e " \n Reading preferences...\n"
status=$(defaults read NSGlobalDomain NSAutomaticQuoteSubstitutionEnabled -bool)
if [ "$status" = "1" ]
    then
        echo -e "Smart quotes are enabled."
    elif [ "$status" = "0" ]
    then
        echo -e "Smart quotes are disabled."

    else
        echo -e "Sorry, an error occured. You have to run this on OS X""
fi

status=$(defaults read NSGlobalDomain NSAutomaticQuoteSubstitutionEnabled -bool)
if [ "$status" = "1" ]
    then
        echo -e "Smart dashes are enabled."
    elif [ "$status" = "0" ]
    then
        echo -e "Smart dashes are disabled."

    else
        echo -e "Sorry, an error occured. You have to run this on OS X!"
fi

sleep 3
echo -e "\n\n You can now enable or disable smart quotes."

until [ "$SUCCESS" = "TRUE" ]
do
echo -e "Enter e for enable or d for disable:"
read sq

if [ "$sq" = "e" ]
    then
        en_sq
    elif [ "$sq" = "d" ]
        then
            di_sq
    else
        echo -e "\n\n ERROR! Please enter e for enable or d for disable!"
fi
done
SUCCESS="FALSE"

echo -e "\n\n You can now enable or disable smart dashes."

until [ "$SUCCESS" = "TRUE" ]
do
echo -e "Enter e for enable or d for disable:"
read sq

if [ "$sd" = "e" ]
    then
        en_sd
    elif [ "$sd" = "d" ]
        then
            di_sd
    else
        echo -e "\n\n ERROR! Please enter e for enable or d for disable!"
fi
done

그리고 여기 내 오류가 있습니다 :

./coding.sh: line 144: unexpected EOF while looking for matching `"'
./coding.sh: line 147: syntax error: unexpected end of file

답변:


31

질문을 보면 문제를 볼 수 있습니다. 95 번째 줄 이후에 구문 강조가 어떻게 조여 지는지 주목하십시오 :

echo -e "Sorry, an error occurred. You have to run this on OS X""

오류 메시지에서 알 수 있듯이 일치하지 않습니다 ". "위의 줄 에서 여분의 것을 제거하면 괜찮을 것입니다.

echo -e "Sorry, an error occurred. You have to run this on OS X"

1
이상하게도, 나는 똑같은 문제를 겪었고 그것은 sudo echo ""줄 이 있었기 때문이었다 sudo echo.
vinzee

@vinzee 왜 당신은 echo함께 실행 sudo하시겠습니까? 즉, 당신이 묘사하는 것은별로 의미가 없으며, 다른 일이 있었을 것입니다.
terdon

내가 할 sudo echo스크립트가 필요하기 때문에 sudo나중에 명령에하지만 사용자가 초기에 자신의 비밀번호를 입력합니다 몇 분 동안 그렇게 스크립트가 자신의 입력을 필요로하지 않습니다 더 이상. 그리고 버그의 경우 여기에 표시된 것과 동일한 오류가 있었지만 두 개의 큰 따옴표를 제거하여 해결되었습니다. 다른 일은 없었습니다.
Vinzee

1
@vinzee 스크립트 내에서 'sudo'명령을 어떻게 실행합니까? . 인용문에 대해서는 다른 것이 있어야합니다. 예를 들어 따옴표 다음에 따옴표를 삭제 한 후 인쇄 할 수없는 문자가있을 수 있습니다. 또는 두 개의 작은 따옴표가 있고 이중 ( echo ''") 또는 그와 비슷한 것이 있었지만 그 이후 에는 괜찮은 것이 있어야했습니다 echo "".
terdon

링크 주셔서 감사합니다, 당신이 맞아요. 달리기 sudo echo는 조금 이상하다고 느꼈다. 그리고 나는 오늘 밤에 리눅스 설치에서 다시 시도하고 결과에 대해 다시 언급 할 것이다.
Vinzee

3

이 오류는 실제 상황에서 추적하기 어려울 수 있습니다. 여기서는 실제 상황에 대한 하나의 솔루션을 제공합니다. 스크립트를 예로 사용하겠습니다.

쉘 스크립트를 업데이트했습니다. 그것을 실행할 때 다음과 같은 오류 메시지가 나타납니다.

/somepath/bin/myshellscript: line 1508: unexpected EOF while looking for matching `"'
/somepath/bin/myshellscript: line 1520: syntax error: unexpected end of file

line 1508 elif [ "$project" ]; then

큰 따옴표 쌍이있는 마지막 줄입니다.

일반적으로 쉘 스크립트를 수정할 때마다 확인합니다. 이번에는 하루를 기다렸다가 수정 한 부분을 잊었습니다. 이 줄 앞의 어느 곳에서 문제가 발생했습니다 (1508). 문제는 심지어 1508 줄을 주석 처리했다는 것입니다.

#elif [ "$project" ]; then

쉘 실행자는 여전히 라인 1508에 문제가 있다고 말했다.

다음으로 원래 쉘 스크립트의 사본을 작성했습니다. 하단에서 전체 코드를 삭제합니다. 그런 다음 다음 명령으로 코드를 확인하십시오.

bash -n mysbashscript

mybashscript: line 515: unexpected EOF while looking for matching `"'
mybashscript: line 561: syntax error: unexpected end of file

이제 내 파일은 원래 크기의 1/3입니다. 나는 즉시 문제를 보았다 :

497 prepare_alignment() {
498     local projdir=${1:?"did not give project directory"}
499     local samp=${2:?"did not give sample name"}
500     local merged=${3:?"must give merged bam file name} # here is the problem

어떤 이유로 인해 {} 내부의 일치하지 않는 "}이 (가) 쉘 구문 분석기에 의해 캡처되지 않습니다. 여기서 쉘 구문 분석기가 더 향상 될 수 있습니다.

문제를 찾는 가장 빠른 알고리즘은 하단에서 코드의 절반을 삭제하는 것입니다. 구문 오류가 사라지면이 절반에 속합니다. 구문 오류가 여전히 있으면 상반부에 문제가있는 것입니다.

후반에 문제가 발생하면 삭제를 취소하십시오. 이 과정을 반복하십시오. 문제의 원인을 찾기 위해 더 작은 크기로 좁힐 수 있습니다.

코드를 삭제할 때는 전체 코드 섹션을 삭제해야합니다. 예를 들어 전체 기능.

bash -n scriptname을 사용하거나 직접 스크립트를 실행할 수 있습니다. 둘 다 작동합니다.


1
"몇 가지 이유를 들어, 타의 추종을 불허하는"내부는 {} 쉘 파서에 의해 캡처되지 않습니다. "단지 구문 때문에, 그것은인가요 되어 라인 1508에 일치? 즉, 라인 (500)에 오픈 스트링 라인 1508에 폐쇄하고 다른됩니다 줄은 결코 닫히지 않는 1508 년에 문을 열었습니다
philh

bash의 인용 동작을 조사하지 않았습니다. Bash는 여러 줄로 된 인용 부호 "line1 \ nline2"를 가질 수 있습니다. 쉘에서 << ENDMARK로 여러 줄짜리 인용을하는 것을 기억합니다. 아마도 큰 따옴표를 직접 사용하여 여러 줄을 인용 할 수 있습니다. 이 기능은 디버그를 정말 어렵게 만듭니다.
Kemin Zhou
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.