<p>This is a follow-on question to the <a href="https://stackoverflow.com/questions/29061/how-do-you-use-ssh-in-a-shell-script">How do you use ssh in a shell script?</a> question.  If I want to execute a command on the remote machine that runs in the background on that machine, how do I get the ssh command to return?  When I try to just include the ampersand (&amp;) at the end of the command it just hangs.  The exact form of the command looks like this:</p>
<pre><code>ssh user@target &quot;cd /some/directory; program-to-execute &amp;&quot;
</code></pre>
<p>Any ideas?  One thing to note is that logins to the target machine always produce a text banner and I have <strong>SSH</strong> keys set up so no password is required.</p>

[{'answer_id': 29172, 'author': 'Jax', 'author_id': 23, 'author_profile': 'https://Stackoverflow.com/users/23', 'pm_score': 10, 'selected': True, 'text': '<p>I had this problem in a program I wrote a year ago -- turns out the answer is rather complicated. You\'ll need to use nohup as well as output redirection, as explained in the wikipedia artcle on <a href="http://en.wikipedia.org/wiki/Nohup" rel="noreferrer">nohup</a>, copied here for your convenience. </p>\n\n<blockquote>\n  <p>Nohuping backgrounded jobs is for\n  example useful when logged in via SSH,\n  since backgrounded jobs can cause the\n  shell to hang on logout due to a race\n  condition [2]. This problem can also\n  be overcome by redirecting all three\n  I/O streams:</p>\n\n<pre><code>nohup myprogram &gt; foo.out 2&gt; foo.err &lt; /dev/null &amp;\n</code></pre>\n</blockquote>\n'}, {'answer_id': 30638, 'author': 'hometoast', 'author_id': 2009, 'author_profile': 'https://Stackoverflow.com/users/2009', 'pm_score': 5, 'selected': False, 'text': '<p>If you don\'t/can\'t keep the connection open you could use <a href="http://www.gnu.org/software/screen/" rel="noreferrer">screen</a>, if you have the rights to install it.</p>\n\n<pre><code>user@localhost $ screen -t remote-command\nuser@localhost $ ssh user@target # now inside of a screen session\nuser@remotehost $ cd /some/directory; program-to-execute &amp;\n</code></pre>\n\n<p>To detach the screen session: <kbd>ctrl-a</kbd> <kbd>d</kbd></p>\n\n<p>To list screen sessions:</p>\n\n<pre><code>screen -ls\n</code></pre>\n\n<p>To reattach a session:</p>\n\n<pre><code>screen -d -r remote-command\n</code></pre>\n\n<p>Note that screen can also create multiple shells within each session.  A similar effect can be achieved with <a href="http://tmux.sourceforge.net/" rel="noreferrer">tmux</a>.</p>\n\n<pre><code>user@localhost $ tmux\nuser@localhost $ ssh user@target # now inside of a tmux session\nuser@remotehost $ cd /some/directory; program-to-execute &amp;\n</code></pre>\n\n<p>To detach the tmux session: <kbd>ctrl-b</kbd> <kbd>d</kbd></p>\n\n<p>To list screen sessions:</p>\n\n<pre><code>tmux list-sessions\n</code></pre>\n\n<p>To reattach a session:</p>\n\n<pre><code>tmux attach &lt;session number&gt;\n</code></pre>\n\n<p>The default tmux control key, \'<kbd>ctrl-b</kbd>\', is somewhat difficult to use but there are several example tmux configs that ship with tmux that you can try.</p>\n'}, {'answer_id': 56693, 'author': 'Community', 'author_id': -1, 'author_profile': 'https://Stackoverflow.com/users/-1', 'pm_score': 3, 'selected': False, 'text': '<p>I think you\'ll have to combine a couple of these answers to get what you want. If you use nohup in conjunction with the semicolon, and wrap the whole thing in quotes, then you get:</p>\n\n<pre><code>ssh user@target "cd /some/directory; nohup myprogram &gt; foo.out 2&gt; foo.err &lt; /dev/null"\n</code></pre>\n\n<p>which seems to work for me. With nohup, you don\'t need to append the &amp; to the command to be run. Also, if you don\'t need to read any of the output of the command, you can use</p>\n\n<pre><code>ssh user@target "cd /some/directory; nohup myprogram &gt; /dev/null 2&gt;&amp;1"\n</code></pre>\n\n<p>to redirect all output to /dev/null.</p>\n'}, {'answer_id': 2831449, 'author': 'Russ', 'author_id': 340853, 'author_profile': 'https://Stackoverflow.com/users/340853', 'pm_score': 8, 'selected': False, 'text': '<p>This has been the cleanest way to do it for me:-</p>\n\n<pre><code>ssh -n -f user@host "sh -c \'cd /whereever; nohup ./whatever &gt; /dev/null 2&gt;&amp;1 &amp;\'"\n</code></pre>\n\n<p>The only thing running after this is the actual command on the remote machine</p>\n'}, {'answer_id': 4566447, 'author': 'Randy Wilson', 'author_id': 558746, 'author_profile': 'https://Stackoverflow.com/users/558746', 'pm_score': 0, 'selected': False, 'text': '<p>I was trying to do the same thing, but with the added complexity that I was trying to do it from Java.  So on one machine running java, I was trying to run a script on another machine, in the background (with nohup).</p>\n\n<p>From the command line, here is what worked: (you may not need the "-i keyFile" if you don\'t need it to ssh to the host)</p>\n\n<pre><code>ssh -i keyFile user@host bash -c "\\"nohup ./script arg1 arg2 &gt; output.txt 2&gt;&amp;1 &amp;\\""\n</code></pre>\n\n<p>Note that to my command line, there is one argument after the "-c", which is all in quotes.  But for it to work on the other end, it still needs the quotes, so I had to put escaped quotes within it.</p>\n\n<p>From java, here is what worked:</p>\n\n<pre><code>ProcessBuilder b = new ProcessBuilder("ssh", "-i", "keyFile", "bash", "-c",\n "\\"nohup ./script arg1 arg2 &gt; output.txt 2&gt;&amp;1 &amp;\\"");\nProcess process = b.start();\n// then read from process.getInputStream() and close it.\n</code></pre>\n\n<p>It took a bit of trial &amp; error to get this working, but it seems to work well now.</p>\n'}, {'answer_id': 6464547, 'author': 'Kevin Duterne', 'author_id': 752109, 'author_profile': 'https://Stackoverflow.com/users/752109', 'pm_score': -1, 'selected': False, 'text': '<p>First follow this procedure: </p>\n\n<p>Log in on A as user a and generate a pair of authentication keys. Do not enter a passphrase:</p>\n\n<pre><code>a@A:~&gt; ssh-keygen -t rsa\nGenerating public/private rsa key pair.\nEnter file in which to save the key (/home/a/.ssh/id_rsa): \nCreated directory \'/home/a/.ssh\'.\nEnter passphrase (empty for no passphrase): \nEnter same passphrase again: \nYour identification has been saved in /home/a/.ssh/id_rsa.\nYour public key has been saved in /home/a/.ssh/id_rsa.pub.\nThe key fingerprint is:\n3e:4f:05:79:3a:9f:96:7c:3b:ad:e9:58:37:bc:37:e4 a@A\n</code></pre>\n\n<p>Now use ssh to create a directory ~/.ssh as user b on B. (The directory may already     exist, which is fine):</p>\n\n<pre><code>a@A:~&gt; ssh b@B mkdir -p .ssh\nb@B\'s password: \n</code></pre>\n\n<p>Finally append a\'s new public key to b@B:.ssh/authorized_keys and enter b\'s password one last time:</p>\n\n<pre><code>a@A:~&gt; cat .ssh/id_rsa.pub | ssh b@B \'cat &gt;&gt; .ssh/authorized_keys\'\nb@B\'s password: \n</code></pre>\n\n<p>From now on you can log into B as b from A as a without password:</p>\n\n<pre><code>a@A:~&gt; ssh b@B\n</code></pre>\n\n<p>then this will work without entering a password </p>\n\n<p>ssh b@B "cd /some/directory; program-to-execute &amp;"</p>\n'}, {'answer_id': 9748364, 'author': 'AskApache Webmaster', 'author_id': 1472950, 'author_profile': 'https://Stackoverflow.com/users/1472950', 'pm_score': 5, 'selected': False, 'text': '<h2>Redirect fd\'s</h2>\n\n<p>Output needs to be redirected with <code>&amp;&gt;/dev/null</code> which redirects both stderr and stdout to /dev/null and is a synonym of <code>&gt;/dev/null 2&gt;/dev/null</code> or <code>&gt;/dev/null 2&gt;&amp;1</code>.</p>\n\n<h2>Parantheses</h2>\n\n<p>The best way is to use <code>sh -c \'( ( command ) &amp; )\'</code> where command is anything.</p>\n\n<pre><code>ssh askapache \'sh -c "( ( nohup chown -R ask:ask /www/askapache.com &amp;&gt;/dev/null ) &amp; )"\'\n</code></pre>\n\n<h2>Nohup Shell</h2>\n\n<p>You can also use nohup directly to launch the shell:</p>\n\n<pre><code>ssh askapache \'nohup sh -c "( ( chown -R ask:ask /www/askapache.com &amp;&gt;/dev/null ) &amp; )"\'\n</code></pre>\n\n<h2>Nice Launch</h2>\n\n<p>Another trick is to use nice to launch the command/shell:</p>\n\n<pre><code>ssh askapache \'nice -n 19 sh -c "( ( nohup chown -R ask:ask /www/askapache.com &amp;&gt;/dev/null ) &amp; )"\'\n</code></pre>\n'}, {'answer_id': 12288730, 'author': 'cmcginty', 'author_id': 64313, 'author_profile': 'https://Stackoverflow.com/users/64313', 'pm_score': 4, 'selected': False, 'text': '<p>I just wanted to show a working example that you can cut and paste:</p>\n\n<pre><code>ssh REMOTE "sh -c \\"(nohup sleep 30; touch nohup-exit) &gt; /dev/null &amp;\\""\n</code></pre>\n'}, {'answer_id': 17863122, 'author': 'fs82', 'author_id': 2272538, 'author_profile': 'https://Stackoverflow.com/users/2272538', 'pm_score': 3, 'selected': False, 'text': '<p>This worked for me may times:</p>\n\n<pre><code>ssh -x remoteServer "cd yourRemoteDir; ./yourRemoteScript.sh &lt;/dev/null &gt;/dev/null 2&gt;&amp;1 &amp; " \n</code></pre>\n'}, {'answer_id': 21348923, 'author': 'MLSC', 'author_id': 2515498, 'author_profile': 'https://Stackoverflow.com/users/2515498', 'pm_score': -1, 'selected': False, 'text': '<p>I think this is what you need:\nAt first you need to install <code>sshpass</code> on your machine.\nthen you can write your own script:</p>\n\n<pre><code>while read pass port user ip; do\nsshpass -p$pass ssh -p $port $user@$ip &lt;&lt;ENDSSH1\n    COMMAND 1\n    .\n    .\n    .\n    COMMAND n\nENDSSH1\ndone &lt;&lt;____HERE\n    PASS    PORT    USER    IP\n      .      .       .       .\n      .      .       .       .\n      .      .       .       .\n    PASS    PORT    USER    IP    \n____HERE\n</code></pre>\n'}, {'answer_id': 24696479, 'author': 'neil', 'author_id': 3829191, 'author_profile': 'https://Stackoverflow.com/users/3829191', 'pm_score': 3, 'selected': False, 'text': '<p>Quickest and easiest way is to use the \'at\' command:</p>\n<pre class="lang-sh prettyprint-override"><code>ssh user@target &quot;at now -f /home/foo.sh&quot;\n</code></pre>\n'}, {'answer_id': 44525428, 'author': 'PaulT', 'author_id': 8155537, 'author_profile': 'https://Stackoverflow.com/users/8155537', 'pm_score': 1, 'selected': False, 'text': '<p>Actually, whenever I need to run a command on a remote machine that\'s complicated, I like to put the command in a script on the destination machine, and just run that script using ssh.</p>\n\n<p>For example:</p>\n\n<pre><code># simple_script.sh (located on remote server)\n\n#!/bin/bash\n\ncat /var/log/messages | grep &lt;some value&gt; | awk -F " " \'{print $8}\'\n</code></pre>\n\n<p>And then I just run this command on the source machine:</p>\n\n<pre><code>ssh user@ip "/path/to/simple_script.sh"\n</code></pre>\n'}, {'answer_id': 55239462, 'author': 'user889030', 'author_id': 889030, 'author_profile': 'https://Stackoverflow.com/users/889030', 'pm_score': 2, 'selected': False, 'text': '<p>You can do it like this...</p>\n\n<pre><code>sudo /home/script.sh -opt1 &gt; /tmp/script.out &amp;\n</code></pre>\n'}, {'answer_id': 56222587, 'author': 'zebrilo', 'author_id': 1057470, 'author_profile': 'https://Stackoverflow.com/users/1057470', 'pm_score': 2, 'selected': False, 'text': '<p>It appeared quite convenient for me to have a <em>remote</em> tmux session using the <code>tmux new -d &lt;shell cmd&gt;</code> syntax like this:</p>\n\n<pre class="lang-sh prettyprint-override"><code>ssh someone@elsewhere \'tmux new -d sleep 600\'\n</code></pre>\n\n<p>This will launch new session on <code>elsewhere</code> host and ssh command on local machine will return to shell almost instantly. You can then ssh to the remote host and <code>tmux attach</code> to that session. Note that there\'s nothing about local tmux running, only remote!</p>\n\n<p>Also, if you want your session to persist after the job is done, simply add a shell launcher after your command, but don\'t forget to enclose in quotes:</p>\n\n<pre class="lang-sh prettyprint-override"><code>ssh someone@elsewhere \'tmux new -d "~/myscript.sh; bash"\'\n</code></pre>\n'}, {'answer_id': 60342175, 'author': 'richprice316', 'author_id': 12075255, 'author_profile': 'https://Stackoverflow.com/users/12075255', 'pm_score': 0, 'selected': False, 'text': '<pre><code>YOUR-COMMAND &amp;&gt; YOUR-LOG.log &amp;    \n</code></pre>\n\n<p>This should run the command and assign a process id you can simply tail -f YOUR-LOG.log to see results written to it as they happen.  you can log out anytime and the process will carry on</p>\n'}, {'answer_id': 60437534, 'author': 'ijt', 'author_id': 484529, 'author_profile': 'https://Stackoverflow.com/users/484529', 'pm_score': 4, 'selected': False, 'text': '<p>You can do this without nohup:</p>\n\n<pre class="lang-sh prettyprint-override"><code>ssh user@host \'myprogram &gt;out.log 2&gt;err.log &amp;\'\n</code></pre>\n'}, {'answer_id': 69708739, 'author': 'Sathesh', 'author_id': 689956, 'author_profile': 'https://Stackoverflow.com/users/689956', 'pm_score': 0, 'selected': False, 'text': '<p>If you are using zsh then use <code>program-to-execute &amp;!</code> is a zsh-specific shortcut to both background and disown the process, such that exiting the shell will leave it running.</p>\n'}]
['https://Stackoverflow.com/questions/29142', 'https://Stackoverflow.com', 'https://Stackoverflow.com/users/171/']