0

I need that awk would return exit code 1 if:

  • no input from grep to awk was provided
  • second field is empty or does not exist

It is working when grep finds "SOME_PHRASE", but if this phrase does not exit, return code ($?) is 0.

grep -m1 -i '^SOME_PHRASE' test.txt | awk '{ if (length($val)==0 || $val=="" || length($2)==0) exit 1; else print $2; }'

example of test.txt

Test1 1234  
Phrase 214324

Expected output:

$ echo $?  
1
  • You are right, I can do it only with awk. For example I tried awk '/SOME_PHRASE/ {if (val=="" || $2=="") exit 1; else print $2;}' test.txt, but still does not work – Rokas.ma Mar 1 '17 at 13:32
  • add sample input and expected output for various cases... – Sundeep Mar 1 '17 at 13:55
  • There seems to be some issue with the if condition. I tried "grep -m1 -i '^SOME_PHRASE' test.txt | awk '{ if (0) exit 1; else exit 5 }'" and this is returning 5.. I tried $ cat test.txt test.txt SOME_PHRASE SOME_PHRASEerewte awk '/SOME_PHRASE/ {if (val=="" || $2=="") exit 1; else print $2;}' test.txt and it is returning 1 .echo $? 1. May be val is getting populated from somewhere. – Forever Learner Mar 1 '17 at 13:57
  • Added example of input and expected output – Rokas.ma Mar 1 '17 at 14:15
  • The examples could be made a lot clearer. I couldn't tell what you were trying to do at all until I read your self-answer. – Wildcard Mar 2 '17 at 5:30
2

You can indeed combine awk and grep:

awk 'BEGIN{rv=1}                      # Default return value is 1
     tolower($0) ~ /^some_phrase/{    # Case insensitive search 
         if($2 != ""){                # If $2 is not empty,
            print $2                  # print the value,
            rv=0                      # and set the return value
         } 
         exit                         # one match, do not process any more line 
     } 
     END{exit rv}
' test.txt
1

I managed to achieve what I wanted.

grep -m1 -i 'SOME_PHRASE' test.txt | awk 'END { if (NR==0 || $2=="")  exit 1; else print $2;}'
1

More straight forward:

$ awk 'toupper($1) ~ /^SOME_PHRASE/ { if ($2) { print $2; exit 0 } else { exit 1 } } END { exit 1 }' test.txt

The first field is changed to uppercase and compared against the uppercase pattern. If matching, and if there exist a second field, that field will be printed and the script exits with a zero exit status, otherwise (no second field) it will exit with an exit status of 1. If the pattern never matches, the script will exit with an exit status of 1 once it reaches the end of input.

  • 1
    Saved me the trouble of writing it. :) That's exactly what I was thinking when I finally understood the question. – Wildcard Mar 2 '17 at 5:30
1

Aside from the fact that awk is perfectly capable of doing what grep does here, you could also explicitly check for empty input in awk and then return a one. Here an END block checks the number of lines (records) processed:

$ echo foo | grep bar | awk 'END {if (NR == 0) exit  }' ; echo "exit value $?"
exit value 1

Or, use the shell to get the return code of the failing process in the pipeline, even if it's not the last one. I don't think the standard shell can do that, but e.g. in Bash, set -o pipefail:

$ set -o pipefail 
$ echo foo | grep bar | awk '{exit 0}' ; echo "exit value $?"
exit value 1

(Bash also has PIPESTATUS if you want to look at the return values from all the processes in the pipeline.)

0

You should consider moving everything inside one roof/tool to make it simple:

grep -qE '^SOME_PHRASE.*[^[:space:]]' yourfile

perl -0777ne 'exit !/^SOME_PHRASE.*?\S/m' yourfile

sed -ne '/^SOME_PHRASE.*[^[:space:]]/q;$q1' yourfile

Output

For the data shown, immediately after running either of the above commands, we run:

echo "$?"
1

Brief

Perl slurps the whole of yourfile and looks for the keyword at the beginning of a line, which is enabled for multiline strings using //m modifier. The ! is there to account for the fact that SUCCESS in Perl & Unix worlds is complementary.

Sed is operated in don't print unless asked for mode -n and assuming GNU sed which has the q command that includes the exit status as well.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.