How to get test command return code in the shell?

17,136

Solution 1

You can use && and || to make these things one-liner. For example, in the following:

ls -l && echo ok

echo ok will run only if the command before && (ls -l) returned 0.

On the other hand, in the following:

ls -l || echo 'not ok'

echo 'not ok' will run only if the command before || returned non zero.

Also, you can make your if..else block one-liner using ;:

if ls -l;then echo ok;else echo 'not ok';fi

But this may make your code hard to read, so not recommended.

Solution 2

The if statement is catching the return value of a command, for example with ls:

if ls -l; then
    echo 'ok'
fi
Share:
17,136
Robber Pen
Author by

Robber Pen

Updated on June 29, 2022

Comments

  • Robber Pen
    Robber Pen almost 2 years

    Is it any better way to get return code from command in one line. eg:

    $ test $(ls -l) ||echo 'ok'
    -bash: test: too many arguments
    ok
    

    the above script have error in test command, because it seems parsing the output "ls - l" not return code.

    I know use the "if" syntax is work fine, But need more then one lines.

    ls -l
    if [ $? -eq 0 ];then
       echo 'ok'
    fi
    
    • fedorqui
      fedorqui almost 8 years
      It is quite unclear what you are asking. Mind to edit and specify what is the exact problem you are facing?
    • gudok
      gudok almost 8 years
      You misunderstand test command. There is no need to use it to simply check return code. One-liner equivalent for second piece of code is ls -l && echo 'ok'.
  • viraptor
    viraptor almost 8 years
    The command execution $(...) makes this check for the output text, not for the return code. Check this for example: [[ $(echo abc && false) ]] && echo ok || echo no - it will print out "ok"
  • jgshawkey
    jgshawkey almost 8 years
    @viraptor, Thank you for the comments. The answer above checks for the return value and not the returned text of the command. You can see this by typing in [[ $(ls -l dirDoesNotExist ) ]] && echo "ok" || echo "not ok" and you will receive the "not ok" response. The command you included [[ $(echo abc && false) ]] successfully executes so it returns a return code of zero as expected. Let me know if you still disagree and we'll continue to pursue it. Thanks!
  • Martin
    Martin almost 8 years
    I just want to add something here, in the short hand if statement using && and || does not equate directly to an if , else. If the command after && fails, the || clause will also run. Example: [[ true ]] && { echo "true"; false; } || echo "false"
  • jgshawkey
    jgshawkey almost 8 years
    @Martin, you are correct. Thank you for clarifying.
  • viraptor
    viraptor almost 8 years
    @jgshawkey That's not why it fails in case of dirDoesNotExist. In that case the error message is printed to stderr, so there's no standard output and that's why the check fails. You can see that [[ $(ls -l dirDoesNotExist 2>&1 ) ]] && echo "ok" || echo "not ok" succeeds. Without redirection, this is equivalent to [[ "" ]] && echo ...
  • jgshawkey
    jgshawkey almost 8 years
    @viraptor. Thank you for taking the time to explain. I see where I was wrong now.
  • Robber Pen
    Robber Pen almost 8 years
    the answer is so clear, and it work fine as my expect.
  • Robber Pen
    Robber Pen almost 8 years
    ls -l xxx && (echo "file xxx not exist" ; exit 1)