Monday, October 25, 2021

[SOLVED] Execute a script through ssh and store its pid in a file on the remote machine

Issue

I am not able to store any PID in a file on the remote machine when running a script in background through ssh.

I need to store the PID of the script process in a file in purpose to kill it whenever needed. When running the exact command on the remote machine it is working, why through ssh it is not working so ?

What is wrong with the following command:

ssh user@remote_machine "nohup ./script.sh > /dev/null 2>&1 & echo $! > ./pid.log"

Result: The file pid.log is created but empty.

Expected: The file pid.log should contain the PID of the running script.


Solution

Use

ssh user@remote_machine 'nohup ./script.sh > /dev/null 2>&1 & echo $! > ./pid.log'

OR

ssh user@remote_machine "nohup ./script.sh > /dev/null 2>&1 & echo \$! > ./pid.log"

Issue: Your $! was getting expanded locally, before calling ssh at all.

Worse, before calling the ssh command, if there was a process stared in the background, then $! would have expanded to that and complete ssh command would have got expanded to contain that PID as argument to echo.

e.g.

$ ls &
[12342] <~~~~ This is the PID of ls
$ <~~~~ Prompt returns immediately because ls was stared in background. 
myfile1 myfile2 <~~~~ Output of ls.
[1]+  Done                    ls
#### At this point, $! contains 12342
$ ssh user@remote "command & echo $! > pidfile"
# before even calling ssh, shell internally expands it to:
$ ssh user@remote "command & echo 12342 > pidfile"

And it will put the wrong PID in the pidfile.



Answered By - anishsane