Impidiendo la ejecución de varias instancias del mismo proceso

Fijo que muchos de vosotros alguna vez se vio con la necesidad de controlar que un programa que se ejecute automáticamente, por ejemplo desde cron, lo haga sólo si no hay otra instancia del mismo en ejecución. Dicho de otra forma, si ya se lanzó el script y todavía no ha terminado, que no se vuelva a lanzar. Aunque esto parece trivial, impedir que un script se ejecute dos veces puede llegar a ser complicado y nos obliga a tener partes del código similares a éstas,




#!/bin/bash

FILE_SYNC=/var/run/async.lock
if [ -f $FILE_SYNC ]; then
   exit
else
   touch $FILE_SYNC
   ...
   rm -f $FILE_SYNC
fi
Crear un fichero de control de ejecución, es una de las soluciones más habitualmente empleadas, pero este truco es un arma peligrosa ya que si en alguna parte del código termina la ejecución, o se aborta el programa, y el fichero no se borra el script no se volverá a lanzar, ya que para él seguirá un hermano en ejecución.
Para solucionar este tipo de inconvenientes y hacer el código más legible y con menos comprobaciones tenemos la utilidad flockflock es una herramienta que se encarga por nosotros de crear y manejar el fichero de bloqueo de ejecución. Y por ello, si la ejecución de un script está o no activa, bloqueará el fichero de control. Si dicho fichero existe no se permitirá otra ejecución. En caso contrario sí.
Como la mejor forma es verlo con un ejemplo,
5 * * * * root /usr/local/sbin/act.sh
Este es el típico script que se ejecuta desde cron cada 5 minutos, pero nada impide, a nivel del planificador, que haya varias instancias del mismo al mismo tiempo. Si queremos controlar eso, tendrá que ser empleando el truco de añadir código de control. Ahora vamos a lanzar el mismo script, pero controlado.
5 * * * * root /usr/bin/flock -w 0 /tmp/cron.lock /usr/local/sbin/act.sh
En este caso, la primera ejecución creará un fichero, /tmp/cron.lock, que siempre estará presente hasta que termine o alguien la aborte. Cuando finalice, la siguiente ejecución hará lo mismo y nunca habrá dos ejecuciones simultáneas. El código del script será únicamente para hacer el procesado de datos que tenga que hacer, pero no necesitará controlar si hay un hermano ejecutándose.
El contenido del fichero de bloqueo, por cierto, será similar al que sigue,
shell> fuser -v /tmp/cron.lock
             USER   PID  ACCESS COMMAND
cron.lock:   root   7836 f....  flock
             root   7837 f....  php

La entrada Impidiendo la ejecución de varias instancias del mismo proceso la puedes leer en Puppet Linux.


1 comentario :

  1. tengo este error
    intento reproducir esa linea en el shell
    /usr/bin/flock -w 0 /tmp/cron.lock /opt/miarchivo.php
    y obtuve este error
    flock: timeout cannot be zero
    CentOS Linux release 7.4.1708 (Core)

    ResponderEliminar

Formulario de contacto

Nombre

Correo electrónico *

Mensaje *

Últimos comentarios