Flujo de control en Bash


¿No te ha ocurrido nunca el tener que irte y no querer apagar el equipo hasta que termine de ejecutarse algo que estabas haciendo?

A mi suele ocurrirme a menudo y es, con diferencia, una de los motivos por los que tardo más de la cuenta en salir de casa cuando ando sentado en el ordenador 😉

Muchas veces la solución pasa por dejar programado el apagado del ordenador pero, como no solemos ser buenos adivinando el futuro, lo más probable es que dejemos más tiempo del necesario para que el equipo no se apague antes de tiempo con el consumo innecesario de energía que ello supone y el desgaste innecesario del equipamiento informático.

¿Qué te parecería poder apagar el ordenador tan pronto como terminase con lo que está haciendo sin tener que estar sentando delante de él esperando que termine?

Pipelines en Linux

El que más y el que menos conoce (o ha visto) el uso del comando ‘;’ (sin las comillas) para separar distintas instrucciones que queremos ejecutar de una sola vez pero dos grandes olvidados son

  1. el operador AND (&&)
  2. el operador OR (||)

que también pueden ser utilizados en una secuencia de comandos o pipeline.

Comando AND

Se ejecuta si y solo si, el último comando ejecutado finaliza correctamente (devuelve un valor 0 como salida, o exit)

comando 1 && comando2

si comando1 finaliza correctamente (devuelve un valor 0) se ejecutará comando2, en caso contrario no se ejecutará.

Para probarlo lanza un

true && echo "todo ha ido bien"

Comando OR

Se ejecuta si y solo si, el último comando ejecutado finaliza erroneamente (devuelve un valor distinto de cero como valor de retorno)

comando 1 || comando2

Comando2 se ejecutará únicamente si comando1 falla (devuelve un valor distinto de 0).

Si quieres probar lanza

false || echo "algo ha fallado"

Apagar el ordenador

Imaginemos que estamos descargando la última iso de Ubuntu; si queremos desconectar el equipo tan pronto como finalice la descarga ¿qué operador utilizarías?

La respuesta correcta es… depende; depende de cómo quieres que se comporte 😉

Si lo que quieres es

Apagar si todo va bien

Utilizaremos el operador AND del siguiente modo

wget http://ftp.gui.uva.es/sites/ubuntu.com/releases/maverick/ubuntu-10.10-desktop-i386.iso && halt

NOTA: Si se produce algún error el equipo se quedará encendido esperando a que llegemos a casa 🙂

Apagar independientemente del resultado

Si no nos importa cómo ha terminado la descarga, el comando más adecuado sería ; (¿lo habías adivinado?) pues lo único que nos interesa es ejecutar secuencialmente los dos comandos

wget  http://ftp.gui.uva.es/sites/ubuntu.com/releases/maverick/ubuntu-10.10-desktop-i386.iso;  halt

Tratar el error

Si queremos que el ordenador se apague siempre pero queremos hacer algo en caso de error (p.e. enviar un correo electrónico informando del problema) usaremos la siguiente combinación

wget  http://ftp.gui.uva.es/sites/ubuntu.com/releases/maverick/ubuntu-10.10-desktop-i386.iso || echo "Problemas descargando Ubuntu" >> $HOME/procesosDesatendidos.log ; halt 

NOTA: Por simplicidad en el ejemplo he añadido una línea a un fichero (procesosDesatendidos.log) en lugar de enviar un correo (la persona interesada que mire el enlace que he puesto un poco más arriba y sustituya el echo por la instrucción mail oportuna)

NOTA: Observa que he incluido un ;halt al final, dicho comando se ejecutará siempre independientemente de cómo termine el wget. La idea es

  • que el equipo se apague siempre
  • si y solo si se produce un fallo (lo recogerá el ||) se anote en el fichero

Conclusión

Espero que el artículo os haya servido para conocer un poco mejor la gestión del flujo de procesos en la línea de comandos y que el ejemplo de apagar el ordenador, aunque simple os sirva como motivación para profundizar en su estudio.

Personalmente suelo utilizar bastante el comando AND cuando lanzo algo (normalmente una actualización de ArchLinux) y soy consciente que en breve tendré que salir.

15 comentarios en “Flujo de control en Bash

  1. Cuánto me alegra ver que por fin a alguien se le ha ocurrido una solución a éste gran dilema 🙂

    Realmente genial si trabajamos descargando con la terminal. Pero, ¿Y si queremos que funcione con un programa como Jdownloader?

    Me gusta

  2. Aquí sólo hay una pega que es que halt necesita permiso de jefe para que se ejecute, con lo cual si queremos pasarle el halt después de un wget este wget debe ser con permisos de jefe y es un poco rollo luego estar cambiando permisos.

    La pega de esto es que si pasamos wget dirección y luego sudo halt supongo que al ejecutar sudo halt estará esperando a que pongamos la contraseña con lo cual creo que no nos vale para lo que se está proponiendo aquí.

    Corregidme si me equivoco
    Un saludo, Julio.

    Me gusta

  3. Pingback: BlogESfera.com
  4. Hola:

    Apagado automático programable = El comando «shutdown». Para más información en un terminal escribir «man shutdown».

    Un saludo y muy bueno el artículo. Gracias.

    Me gusta

  5. Y porque no utilizas screen , puedes lanzar algo cerrar la session y cuando llegas a tu casa te conectas al servidor y ves si termino bien, haces horas en el curro de menos y tienes mas vida…

    Me gusta

  6. un script, que ejecute que va mirando el nombre de proceso en el «ps -A»que le pasas como argumento, primero confirma que existe, desoues empieza a verificar si sigue vivo, una que vez que no lo ves, pues halt.

    Me gusta

Deja una respuesta

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Salir /  Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Salir /  Cambiar )

Conectando a %s

Este sitio usa Akismet para reducir el spam. Aprende cómo se procesan los datos de tus comentarios.