Search code examples
regexbashif-statementspace

bash match regexp in IF statement


Please help me to understand what is wrong. The script below all the time returns "doesn't match"

while true
do
        PING_OUTPUT="64 bytes from 8.8.8.8: icmp_seq=1 ttl=119 time=35.2 ms"  #`ping -c 1 $PING_HOST |sed -n 2p`
        echo "$PING_OUTPUT"
        if [[ "$PING_OUTPUT" =~ 64\sbytes\sfrom\s8.8.8.8:\sicmp_seq=1\sttl=119\stime=35.2\sms ]]
        then
                echo "Match"
        else
                echo "Doesn't match"
        fi
        read -p "Where to ping?" PING_HOST
done

I tried different format of regexp:

if [[ "$PING_OUTPUT" =~ 64[ ]bytes[ ]from[ ]8.8.8.8:[ ]icmp_seq=1[ ]ttl=119[ ]time=35.2[ ]ms ]]

This time it shows syntax error:

./main_script.sh: line 10: syntax error in conditional expression
./main_script.sh: line 10: syntax error near `]bytes['
./main_script.sh: line 10: `    if [[ "$PING_OUTPUT" =~ 64[ ]bytes[ ]from[ ]8.8.8.8:[ ]icmp_seq=1[ ]ttl=119[ ]time=35.2[ ]ms ]]'

It looks like right side of =~ is not being interpreted as regexp, but I can't understand why.


Solution

  • Bash does not support \s since it uses POSIX regex library, this is why your first attempt failed.


    In bash manual it reads:

    ... Any part of the pattern may be quoted to force the quoted portion to be matched as a string...

    So, just quote those spaces and it'll work. E.g:

    PING_OUTPUT="64 bytes from 8.8.8.8: icmp_seq=1 ttl=119 time=35.2 ms"  #`ping -c 1 $PING_HOST |sed -n 2p`
    if [[ "$PING_OUTPUT" =~ 64" "bytes" "from" "8.8.8.8:" "icmp_seq=1" "ttl=119" "time=35.2" "ms ]]; then
        echo "Match"
    else
        echo "Doesn't match"
    fi