¿Cómo programar los trabajos del servidor de manera más inteligente que con cron?

15

Ejecuto un trabajo cada minuto para reindexar el contenido de mi sitio.

Hoy, el motor de búsqueda murió, y cuando inicié sesión había cientos de procesos huérfanos iniciados por cron.

¿Hay otra forma de usar algún tipo de software existente que me permita ejecutar un trabajo cada minuto, pero que no inicie otra instancia si ese trabajo no regresa (es decir, porque el proceso del motor de búsqueda ha fallado)?

John
fuente
44
cron es muy probable que esté haciendo exactamente lo que le está diciendo. Sugiero reescribir el trabajo de manera inteligente.
gparent

Respuestas:

27

El problema no es realmente con cron, es con tu trabajo.

Necesitará que su trabajo interactúe con un candado de alguna descripción. La forma más fácil de hacerlo es hacer que intente crear un directorio y, si tiene éxito, continuar, si no salir. Cuando su trabajo haya finalizado y salga, debería eliminar el directorio listo para la próxima ejecución. Aquí hay un guión para ilustrar.

#!/bin/bash

function cleanup {
    echo "Cleanup"
    rmdir /tmp/myjob.lck
}

mkdir /tmp/myjob.lck ||  exit 1
trap cleanup EXIT
echo 'Job Running'
sleep  60
exit 0

Ejecute esto en una terminal y luego, antes de que transcurran 60 segundos, ejecútelo en otra terminal y saldrá con el estado 1. Una vez que se cierra el primer proceso, puede ejecutarlo desde la segunda terminal ...

EDITAR:

Cuando acabo de enterarme de la bandada, pensé en actualizar esta respuesta. El lote (1) puede ser más fácil de usar. En este caso flock -nparecería apropiado, por ejemplo

* * * * * /usr/bin/flock -n /tmp/myAppLock.lck /path/to/your/job   

Ejecutaría su trabajo cada minuto pero fallaría si el lote no puede obtener un bloqueo en el archivo.

usuario9517
fuente
2
Tal vez una pregunta estúpida, pero ¿hay alguna ventaja en usar un directorio específicamente en lugar de un archivo normal?
gparent
99
El uso de un archivo normal requiere varias operaciones, verifique si existe, si no lo crea, luego cree. Esto deja una ventana de oportunidad para que otro proceso cree el archivo: desordenado. El mkdir es una operación atómica que funciona y obtienes el 'bloqueo' o no, ya que otro proceso ya lo tiene.
user9517
Tiene sentido. Bien pensado en el directorio de bloqueo también. Gracias
John
2

Una forma sería hacer que su script reindex cree un archivo de bloqueo para que pueda verificar si ya hay una instancia del script en ejecución. También puede agregar algún manejo de excepciones para ver si el motor de búsqueda está en funcionamiento.

Una alternativa más complicada sería utilizar algún tipo de tarea queuer como Resque y Resque-Scheduler:

https://github.com/blog/542-introducing-resque

https://github.com/bvandenbos/resque-scheduler#readme

También hay Qu y Sidekiq:

https://github.com/bkeepers/qu

https://github.com/mperham/sidekiq

Sí, todo está orientado a Ruby, pero puede buscar "cosas como resque" en el idioma que elija.

cjc
fuente
0

Otra forma de configurar esto rápidamente es iniciar un script de shell cuando se inicia la máquina (cron puede hacer esto con ' @reboot /path/to/my/script.sh', luego reiniciar el cron para iniciarlo) con algo como esto.

#!/bin/sh
/opt/bin/run-site-index
sleep 60
exec $0

El script sigue ejecutándose, y es que solo ha comenzado uno, es decir, cuántos podrían ejecutarse a la vez, no más que eso. Algunos datos inteligentes también pueden verificar si el indexador se está ejecutando y, de lo contrario, reiniciar o intentar solucionar / notificar a alguien sobre el problema.

Alister Bulman
fuente
-3

En lugar de usar cron para esto, construiría su trabajo más como un servicio que se ejecuta en un bucle y duerme durante 60 segundos como último paso, o tal vez duerme más a menudo durante intervalos más pequeños en varios puntos durante el proceso para ayudar a distribuir la carga más parejo.

Joel Coel
fuente
1
Esto no solucionaría el problema ni sería una mejora de cron.
gparent
Solucionaría el problema, porque solo hay un proceso que se ejecuta alguna vez. Evitaría el cron por completo.
Joel Coel
No soluciona el problema si el 'servicio' no se ve si el motor de búsqueda está funcionando. La lógica de su guión / trabajo es el problema. EDITAR: En realidad, tienes algo de razón, ocultaría el problema de una manera fea.
gparent