cron: eseguire un processo ma solo se non è in esecuzione?


11

C'è un modo per dire a cron di eseguire un'app MA non eseguirla se esiste già un processo?

linux  cron 

Vuoi chiarire se l'app non deve essere eseguita se è già in esecuzione o se è già in esecuzione un processo diverso. Grazie
Linker3000,

Risposte:


23

nel modo più semplice, usa pgrep

in crontab:

* * * * * pgrep processname > /dev/null || /path/to/processname -args0 -args1

Adoro la semplicità di questa risposta. Cordiali saluti, dovresti essere in grado di aggiungere il flag -f a pgrep, quindi puoi controllare il nome completo del processo, che è utile se vuoi anche ispezionare gli argomenti nel processo come parte della tua condizione.
Craig Sefton,

6
No, non puoi usare il flag -f con pgrep all'interno di un cronjob. Il motivo è che abbinerai lo script di shell utilizzato per eseguire il cronjob stesso.
CpnCrunch,

Quando si esegue un processo GUI con cron, anteporre a export DISPLAY=:0per evitare Could not connect to displayerrori. * * * * * export DISPLAY=:0 && pgrep processname > /dev/null || /path/to/processname -args0 -args1
Benjam

9

Esegui uno script, anziché direttamente il programma. Ci sono molte possibilità Per esempio :

MYPROG="myprog"
RESTART="myprog params"
PGREP="/usr/bin/pgrep"
# find myprog pid
$PGREP ${MYPROG}
# if not running
if [ $? -ne 0 ]
then
   $RESTART
fi

1
Cordiali saluti - l'utilizzo di variabili scalari per memorizzare elenchi di argomenti è considerato una cattiva pratica. Vedi mywiki.wooledge.org/BashFAQ/050 per un esempio di un caso in cui fallisce.
Charles Duffy,

... allo stesso modo, pgrep myprog; if [ $? -ne 0 ]; then ...sarebbe meglio scritto comeif ! pgrep myprog; then ...
Charles Duffy il

... quest'ultimo stile non è solo più leggibile, ma anche meno soggetto a errori: è facile interrompere involontariamente il valore di $?, ad esempio aggiungendo messaggi di log o gestione degli errori tra le righe.
Charles Duffy,

7

Questo script non verrà eseguito nuovamente se l'istanza precedente non è terminata. Se non si desidera eseguire qualcosa se è in esecuzione un altro processo specifico, consultare lo script di harrymc.

DATE=`date +%c`;
ME=`basename "$0"`;
LCK="./${ME}.LCK";
exec 8>$LCK;

if flock -n -x 8; then
  echo ""
  echo "Starting your script..."
  echo ""

[PUT YOUR STUFF HERE]

  echo ""
  echo "Script started  $DATE";
  echo "Script finished `date +%c`";
else
  echo "Script NOT started - previous one still running at $DATE";
fi

3

È possibile utilizzare un file di blocco nello script, ma consultare Gestione processi .

flock è un'utilità che può essere utilizzata.


bravo! ora rsync su questa linea lenta può richiedere tutto il tempo necessario, attivando entro 5 minuti dall'host client in linea senza intervento manuale:*/5 * * * * root flock /run/shm rsync -auhx --numeric-ids -e "ssh -T -c arcfour128 -o Compression=no -x" [source] [user]@[host]:[dest]
eMPee584

1

Questo è di solito gestito dal programma stesso piuttosto che da cron. Esistono due tecniche standard per questo:

1) grepl'output di psper vedere se esiste già un processo con quel nome in esecuzione

2) All'avvio, verificare innanzitutto l'esistenza di un file pid (ID processo), di solito in /var/run/program_name.pid, e, se esiste, leggere il pid dal file e verificare se quel processo esiste ancora; se lo fa, rifiuta di iniziare. Se il file pid non esiste o il pid nel file è scomparso, quindi creare un file pid, scrivere l'ID del processo in esso e continuare con l'avvio normale.

Mentre è tecnicamente possibile scrivere pipe di bash che faranno una di queste direttamente nel tuo crontab, è meglio aggiungerle al programma avviato (in modo che si applichino indipendentemente da come viene avviato) o scrivere uno script wrapper in gestirlo, come suggerito da harrymc.


0

* * * * * pgrep -f "[p]attern" > /dev/null || /path/to/processname -args0 -args1

Ho riutilizzato la risposta di cui sopra con un miglioramento nella corrispondenza dei modelli. pgrep senza l'opzione f non corrisponde al modello di processo. Tuttavia c'è un problema con l'uso dell'opzione f. Con l'opzione f, la shell che genera il cron è sempre abbinata e restituisce il suo pid, quindi il processo non viene mai riavviato.

L'aggiunta di un [] attorno a uno dei pattern delle lettere corrisponde solo al processo e il pid della cron shell non viene restituito.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.