Utilizzo di SSH per avviare in remoto un processo


18

Ho scritto uno script che sto usando per inviare e distribuire un nuovo servizio su più macchine sotto il mio controllo e per eseguire il processo sto usando ssh per avviare il processo da remoto. Sfortunatamente, ogni volta che utilizzo SSH per avviare il processo, il comando SSH non sembra mai tornare, causando lo stallo dello script.

Il comando è specificato come: ssh $ user @ $ host "/ root / command &". Ogni volta che eseguo comandi semplici, come ps o who, il comando SSH ritorna immediatamente, tuttavia quando provo ad avviare il mio processo non ritorna. Ho provato trucchi come avvolgere il mio processo in un semplice script bash che avvia il processo e poi termina, tuttavia questo blocca anche il comando SSH (anche se lo script bash riporta un messaggio di successo ed esce normalmente).

Qualcuno ha qualche idea su cosa sta causando questo comportamento e su come posso ottenere il comando SSH per tornare non appena il processo è stato avviato?

Grazie per le tue opinioni!


Pubblica la riga di comando esatta che stai utilizzando ... ometti password / nomi utente / IP
Joseph Kern,

ssh $ SSH_USER @ $ HOST_ADDR "/ root / AppName &"
rmrobins,

Devo dire che ho impostato le chiavi SSH, quindi non è necessario utilizzare le password per eseguire comandi sui sistemi remoti.
rmrobins,

@rmrobins, un ottimo passo: impostare l'autenticazione della chiave pubblica.
nik,

Risposte:


28

SSH collega stdin, stdout e stderr della shell remota al terminale locale, in modo da poter interagire con il comando in esecuzione sul lato remoto.

Come effetto collaterale, continuerà a funzionare fino a quando queste connessioni non saranno state chiuse, cosa che accade solo quando il comando remoto e tutti i suoi figli (!) Sono terminati (perché i figli, che è ciò che inizia "&", ereditano std * dal loro processo genitore e tenerlo aperto).

Quindi devi usare qualcosa di simile

ssh user@host "/script/to/run < /dev/null > /tmp/mylogfile 2>&1 &"

<,> E 2> e 1 reindirizzano stdin / stdout / stderr lontano dal tuo terminale. Il "&" quindi porta il tuo script in background. Naturalmente in produzione reindirizzeresti stdin / err a un file di log adatto.

Vedere

http://osdir.com/ml/network.openssh.general/2006-05/msg00017.html

Modificare:

Ho appena scoperto che quanto < /dev/nullsopra non è necessario (ma reindirizzare stdout / err lo è ). Non ho idea del perché ...


Grazie, questo è esattamente quello che stavo cercando: non mi è venuto in mente che il processo ereditasse lo std * anche quando lo si utilizzava e lo avviava in background.
rmrobins,

+1! Per me va bene. E puoi anche stampare l'output facendo eco al file di registro: ssh user@host "/script/to/run > /tmp/ssh.stdout 2>&1 && cat /tmp/ssh.stdout && rm -f /tmp/ssh.stdout"
Fishdrowned

5

Potresti provare nohup . Man nohup per maggiori dettagli.

ssh host "nohup script &"

Se vuoi mantenere l'output sul computer remoto, ecco una variante .

ssh user@host 'export REMOTE=myname; nice nohup ./my-restart >
logfile.log 2>&1 &'

5

Un'altra alternativa sarebbe quella di accendere un distaccato screen(1), qualcosa come:

ssh -l user host "screen -d -m mycommand"

Questo avvierà una schermata distaccata (che cattura tutte le interazioni al suo interno) e poi ritornerà immediatamente, terminando la sessione SSH.

Con un po 'più di ingegnosità, puoi risolvere in questo modo chiamate di comando remote piuttosto complesse.


4
 -f      Requests ssh to go to background just before command execution.
         This is useful if ssh is going to ask for passwords or
         passphrases, but the user wants it in the background.  This
         implies -n.  The recommended way to start X11 programs at a
         remote site is with something like ssh -f host xterm.

         If the ExitOnForwardFailure configuration option is set to “yes”,
         then a client started with -f will wait for all remote port for‐
         wards to be successfully established before placing itself in the
         background.

1
Il problema con questo metodo è che il comando SSH non è effettivamente terminato, è semplicemente nascosto in background, quindi l'host che esegue lo script avrà un gran numero di comandi SSH in background che non ritornano mai perché i comandi SSH non ritornano mai ( cioè il problema alla radice che desidero risolvere)
rmrobins,

-1

Penso che il modo corretto sarebbe

ssh user@host exec script.sh &

No, non funziona per me. Perché dovrebbe?
sleske,

Non ho usato lo sfondo push over ssh, stavo provando senza un termine a portata di mano. colpa mia.
nik,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.