0

when we run this on remote machine we get

ssh $IP "systemctl disable iptables.service"

and standard error is

echo $?

0

but lets run it with error ( I add wrong syntax )

for example

ssh $IP "systemctl disable_bug iptables.service"

why we get 0 from standard error? in spite command fail!!!

echo $?
0
shalom
  • 461
  • 13
  • 29

1 Answers1

0

You're echoing the results of the ssh command - which completed successfully both times (ie ssh was ok). You're not displaying the results of the command you ran via ssh.

If you direct the output of the command to a file (via tee or just normal redirection), you can collect the results later.

edit

Due to downvotes (I presume from OP who doesn't realize what I've already answered is correct (see comments)), I'm expanding this answer.

When you run echo $?, it will output the exit code of the last run local command. For example:

$ ssh user@host 'ls /tmp' 
lastSubredditNeighborsRun.log
meetupDumper.log
mongodb-27017.sock

$ echo $?
0

That's the return code of ssh - NOT the return code of the ls run remotely.

Running echo $? might also not display anything:

$ ssh user@host 'ls /tp' && echo $?
ls: cannot access /tp: No such file or directory

Or it might display an error return code - if you don't run it chained on the command line:

$ ssh user@host 'ls /tp'
ls: cannot access /tp: No such file or directory
$ echo $?
2

ssh may send back the sent command's error code - it's supposed to - as its own error code ... but it doesn't always.

But running echo $? is always only going to be able to echo the error code of the most recently-run local command. If ssh returns the remote error code as its own, that's awesome. But if it doesn't (or the remote command doesn't send an error code), you're going to get the expected result from echo $? - which is 0 if the previous command ran successfully.

warren
  • 18,369
  • 23
  • 84
  • 135
  • not agree , for example after each ssh on remote machine you can pick the $? – shalom Sep 06 '17 at 13:07
  • for example - ssh root@ip "ls /etc" ; echo $? – shalom Sep 06 '17 at 13:08
  • for bad output - ssh root@ip "ls /ZZZ" ; echo $? - will get 1 ( because no ZZZ folder – shalom Sep 06 '17 at 13:08
  • @shalom you might not agree, but that's what's happening. You're running a command via ssh. Then echoing the results of the last command - which was ssh. Echoing the results of the last command is a local function - and the last local command to run was clearly ssh. – warren Sep 06 '17 at 13:09
  • $? inst ssh standard output , $? will get the last command from ssh – shalom Sep 06 '17 at 13:13
  • You're echoing a status code, not the output of a command when using 'echo $?'. The status code is '0' for success, and a non-0 value for failure (or special cases like rpm which returns as a "failure" the number of packages it didn't install from the list you gave it). – warren Sep 06 '17 at 13:16
  • @warren this is not true. Try it: `ssh user@remote /bin/true` and then `echo $?`, same for `bin/false`, you'll get 0/1 as echo variable. – Lenniey Sep 06 '17 at 13:17
  • yes I agree that $? is status , what I mean is that - we can capture the status from command VIA ssh , and status is always from the last command !!! , so echo $? will get the status from "ls /etc" while its run from ssh – shalom Sep 06 '17 at 13:17
  • why I get "-1" please explain ?? – shalom Sep 06 '17 at 13:20
  • @warren please try to capture the status on your linux machine - try ssh xxx.xxx.xxx.xxx "ls /etc" , and then echo $? , then try ssh xxx.xxx.xxx.xxx "ls /non_folder" and then echo $? in this state you should get 1 or diff then 0 – shalom Sep 06 '17 at 13:23
  • @warren , I hope you understand now the case better , let me know if you have questions ? , but please try to execute your test before your answers , many users can get the wrong feeling that your answer is right but in fact it is not , so please remove your remarks they are wrong!!! , better also your answer – shalom Sep 06 '17 at 13:27
  • @shalom - I appreciate you want to tell me I am wrong. But `echo $?` echoes the exit code of the last *local* command run. Not the results of a *remote* command *started* locally. `echo $?` *might* not display anything (as `ssh host 'ls /non-existent-file'` will show). But it is *never* going to echo the results of the *remote* command run. It's not how it works. – warren Sep 06 '17 at 14:29
  • From the ssh(1) man page: EXIT STATUS ssh exits with the exit status of the remote command or with 255 if an error occurred. – ptman Sep 06 '17 at 14:32
  • I agree with ptman , – shalom Sep 06 '17 at 14:38
  • @ptman - note my expanded answer – warren Sep 06 '17 at 14:39
  • @warren, you are correct in the general case, but since this is about [ssh(1)](https://www.freebsd.org/cgi/man.cgi?query=ssh&sektion=1) specifically, the documentation about ssh exit status is relevant – ptman Sep 06 '17 at 14:44
  • @ptman - I can duplicate OP's issue of getting the correct, incorrect, or no result when doing the echo after ssh, as explained above. – warren Sep 06 '17 at 14:47
  • @warren look , the $? is from the ssh pipe but actually its comes from the last command ( last command in ssh line ) - can you please mark this in your answer !!! – shalom Sep 06 '17 at 15:01