Si durante un conjunto de veces, ha observado un patrón específico en su dispositivo Linux que activa una alarma por un uso elevado de CPU/memoria, se recomienda analizar el conjunto de procesos que se estaban ejecutando en el momento de la alarma.
Durante el análisis, es posible que encuentre que un proceso o script específico está ejecutando varias instancias simultáneamente debido a una llamada duplicada en un proceso programado (que se configuró mediante trabajos cron).
Para evitar que esto suceda, puedes utilizar dos alternativas:
Configuración de un archivo de bloqueo
Dentro del script, implemente un procedimiento que verifique si existe un archivo. Si no es así, el script lo creará y continuará ejecutándose como se esperaba. Si el archivo no es necesario una vez que se completa el script, puede eliminarlo para asegurarse de que la próxima ejecución del trabajo no lo considere como "en uso".
Configurando un archivo PID en BASH
De manera similar al método mencionado anteriormente, el uso de un archivo de ID de proceso (PID) se basa en la lectura de un archivo, con la diferencia de que dentro de este archivo, se coloca el PID de la instancia en ejecución, esto permitirá validar que el proceso si el proceso se está ejecutando, mientras que el archivo de bloqueo solo verifica que el script comenzó a ejecutarse, sin tener en cuenta si aún se está ejecutando o si se detuvo/finalizó antes de que se eliminara el archivo.
Pasos para configurar esto:
A través del siguiente fragmento de código, puede ver una muestra del código que implementaría dentro de su secuencia de comandos. El texto que comienza con un símbolo de libra (#) es un comentario dentro del código, por lo que puede eliminarse en la implementación final.
# A. Define your PID file using the full path where it'll be located.
# Do not place your code within any /tmp folder as these get cleaned up automatically and might interfere with the expected behaviour of the script.
# B. Check if the PID file exists, if it does, it will run the intended function.
PIDFILE = /var/apps/testscript.pid
# 1. Read the content of our PID file (with cat), and assign it to the PID variable
if [ -f $PIDFILE ] then
# 2. Verify if the content of the file is a running process
PID = $(cat $PIDFILE)
# In here, the '%?' variable obtains the exit code from our previous command
ps -p $PID > /dev/null 2>&1
# 3. If the content of the file is a process (an output equal to 0 means succesful), output a message, and exit the application.
if [ $? -eq 0 ] then
echo "Job is already running"
exit 1
else
# 4. If the exit code was not succesful, we assume the process was not running, so we place the current process ID into the PID File
echo $$ > $PIDFILE
if [ $? -ne 0 ] then
echo "Could not create PID file"
exit 1
fi
fi
# C. If the PID file does not exist, it will attempt to create it, then run the code
else
# 1. This outputs the current PID into the PID file:
# The '$$' value is a variable for the current PID.
# The '>' operand directs the output from echo to a file
echo $$ > $PIDFILE
# 2. If the exit code was not succesful, output an error message, and exit the application.
if [ $? -ne 0 ]
then
echo "Could not create PID file"
exit 1
fi
fi
# *** In here you need to insert the original script code *** #
# D. Remove the PID file so we try to always have a "clean slate"
rm $PIDFILE
Otras soluciones
Además de las dos alternativas anteriores, existen diferentes utilidades que puede implementar.
Rebaño
El comando flock es una utilidad instalada en las distribuciones de Linux más nuevas que administra bloqueos desde scripts de shell
Puede consultar la documentación oficial en la siguiente URL para obtener más información sobre su uso:
- https://manpages.ubuntu.com/manpages/xenial/man1/flock.1.html
Lo útil de flock es que el bloqueo del archivo se mantendrá hasta que se complete el proceso original, en ese momento flock liberará el bloqueo del archivo. Esto es cierto ya sea que el proceso se complete con éxito o sin éxito.
Solo
Solo es un script de Perl que vincula la ejecución del script a un puerto de red en lugar de a un archivo,
Puede consultar el sitio web oficial para obtener más información:
- https://www.timkay.com/solo/.
Similar a otras implementaciones, esto creará un bloqueo que solo se liberará después de que se complete el script asignado:
$ ./solo -port=1234 /var/tmp/script.sh & 1234
$ ./solo -port=1234 /var/tmp/script.sh
solo(1234): Address already in use
La ventaja de vincular un puerto en lugar de un archivo es que no se puede eliminar un puerto. Que con otras implementaciones, "liberaría" el bloqueo existente, permitiendo instancias duplicadas de un trabajo.
Notas adicionales
Si bien las utilidades y prácticas anteriores evitan la ejecución de trabajos duplicados, es importante monitorear la forma en que interactúan sus trabajos cron para evitar la superposición de trabajos o el uso excesivo de recursos que podrían obstaculizar el rendimiento de nuestro dispositivo y operaciones.
Artículos relacionados
- Comando de bandada
- Secuencia de comandos PERL individual.
Use la pestaña Comentarios para hacer cualquier comentario o hacer preguntas. También puede iniciar una conversación con nosotros.