04 mayo 2012

3 formas de ejecutar comandos en segundo plano en linux

En algunas ocasiones puede ser necesario ejecutar un script en segundo plano; ya sea porque tarde mucho en finalizar o porque el programa tiene que ejecutarse de forma indefinida y al mismo tiempo se quieren analizar sus salidas/salidas en tiempo real, o cuando, en el caso de conexiones remotas, por el motivo que sea, se pueda producir una desconexión.

Analizaremos 3 posibilidades:

& y bg
Si añadimos un ampersand (&) al final del comando o del script que queremos ejecutar, éste se ejecutará en segundo plano.
$ ./my-shell-script.sh &
[1] 10233
Si ejecutamos un comando de la forma habitual (en primer plano o foreground) y, después de pasado un cierto tiempo, nos damos cuenta que hubiera sido mejor ejecutarlo en segundo plano o background, lo podemos hacer sin necesidad de tener que matar el proceso y volver a ejecutarlo de nuevo con el ampersand. Esto se hace presioando "CTRL+Z" para suspender la ejecución del comando actual, y después invocando el comando bg.
$ ./my-shell-script.sh
^Z
[2]+  Detenido                my-shell-script.sh

$ bg
[2]+ my-shell-script.sh &
Este proceso que se acaba de pasar al segundo plano, también se puede volver al primer plano con el comando fg.
$ fg 2
my-shell-script.sh
nohup y &
Al finalizar una sesion en un terminal se envía un signal (SIGHUP) a todos los procesos que esté ejecutando nuestro usuario. Como resultado, dichos procesos se mueren (aunque les hayamos puesto & al final)

Para evitar esto utilizamos el comando nohup. Este comando hace que un proceso ignore la señal SIGHUP, y redirige la salida de nuestro script a un archivo nohup.out que es creado en el directorio actual.
$ nohup ./my-shell-script.sh &
Una buena practica sería redireccionar stdin, stdout y stderr. Básicamente, por dos razones: i) rastrear la salida de nuestro script en caso de producirse algún error, y ii) evitar problemas al terminar nuestra sesión ssh, si es que la ejecutamos en un servidor remoto.
$ nohup ./my-shell-script.sh > foo.out 2> foo.err < /dev/null &
Esta opcion es muy útil cuando necesitamos ejecutar un proceso largo y no nos interesa saber nada de él hasta que finalice. Podemos desconectarnos irnos, regresar al día siguiente y analizar el resultado del proceso.

screen
Si invocamos un comando en segundo plano (usando nohup y &), éste se ejecutará incluso después de que cerremos nuestra sesión. Pero, en ninguno de los casos anteriores, podemos conectarnos a la misma sesión otra vez y ver exactamente qué es lo que está pasando en la pantalla, como si no nos hubieramos desconectado. Para lograr esto, usaremos el comando screen.

El primer paso es ejecutar el script que necesitamos como parametro del comando screen.
$ screen ./my-shell-script.sh
Si después de ejecutar la linea anterior tecleamos “CTRL+A d”, el sistema nos separara de la sesión actual (en la que estamos ejecutando my-shell-script.sh) y nos retornará a la terminal a la espera de teclear un nuevo comando.

Llegados a este punto, podemos cerrar la sesión, irnos, regresar, iniciar una nueva sesión y recuperar la pantalla (screen) que esta corriendo nuestro script. Para ello, invocaremos el comando screen con el parámetro -ls para obtener un listado de las sesiones actuales:
$ screen -ls
[detached from 1788.ttys000.milleniumfalcon]
A continuación, mediante el parámetro -r y el identificador de la sesión recuperamos la pantalla que necesitemos:
$ screen -r 1788.ttys000.milleniumfalcon
¿Qué opcion usar?
Bueno, pues eso dependerá de cada caso, habrá veces que con el ampersand será suficiente y otras en las que tenemos que optar por una opción diferente. Para saber más acerca de nohup y screen recomiendo leer las páginas del manual.

10 comentarios:

Cicklow dijo...

Gracias, me sirvió de mucho saber esto :)... ya que renegaba siempre con que al cerrar SSH o perder la conexión de internet, perder los procesos ejecutados.

Saludos :)

gurzaf dijo...

Estaba buscando como hacer esto mismo en Mac, porque con ampersand, no funcionaba... afortunadamente ambos son sistemas tipo UNIX y screen venía preinstalado. Gracias!

Unknown dijo...

Gracias por la aportación, me ayudó bastante...

sangreaurinegra dijo...

Me fue muy util !!!
Muchas Gracias Jesus

Hernán Elizalde dijo...
Este comentario ha sido eliminado por el autor.
Unknown dijo...

Un aporte magnífico, salu2.

Camila dijo...

Como siempre me ha interesado las cuestiones que tienen que ver con la informática trato de seguir aprendiendo mucho cada vez que tengo tiempo para entrar a esta clase de paginas. Cuando suelo quedarme en casa disfruto pasar tiempo investigando sobre estas cuestiones mientras dejo algo cocinándose en el horno

Unknown dijo...

Muchas gracias por este estupendo aporte, guardado en mis notas está porque me ha servido de mucha ayuda.

Anónimo dijo...

gracias! saludos!

Anónimo dijo...

VAYA PUTA MIERDA