sviluppo-web-qa.it

Posso eseguire un cron job più frequentemente di ogni minuto?

È possibile eseguire un processo cron ogni 30 secondi senza un comando sleep?

48
user15336

Se la tua attività deve essere eseguita di frequente, cron è lo strumento sbagliato. A parte il fatto che semplicemente non avvierà i lavori così frequentemente, rischi anche alcuni seri problemi se il lavoro impiega più tempo per l'esecuzione rispetto all'intervallo tra i lanci. Riscrivi la tua attività per demonizzare ed eseguire in modo persistente, quindi avviala da cron se necessario (assicurandoti che non si riavvierà se è già in esecuzione).

38

Candidato per l'abuso più creativo di un comando Linux:

Nohup watch -n 30 --precise yourprog >/dev/null &

Se yourprog è costituito da:

date +%M.%S.%N >> yourprog.out

poi yourprog.out potrebbe apparire come:

50.51.857291267
51.21.840818353
51.51.840910204
52.21.840513307
52.51.842455224
53.21.841195858
53.51.841407587
54.21.840629676

indicando un livello abbastanza buono di precisione.

Ecco una spiegazione delle parti del comando:

  • Nohup - Questo impedisce al comando che lo segue, watch in questo caso, di uscire quando il terminale esce.
  • watch - Questo programma esegue ripetutamente un comando. Normalmente la prima schermata di output dal comando viene visualizzata ogni volta che watch esegue il comando.
  • -n 30 - L'intervallo in cui eseguire il comando. In questo caso è ogni trenta secondi.
  • --precise - Senza questa opzione, watch esegue il comando dopo intervallo secondi. Con esso, ogni inizio del comando inizia su l'intervallo, se possibile. Se questa opzione non fosse specificata nell'esempio, i tempi sarebbero più tardi e più tardi di più di 30 secondi ogni volta a causa del tempo impiegato per avviare ed eseguire il comando (yourprog).
  • yourprog - Il programma o la riga di comando per l'esecuzione di watch. Se la riga di comando contiene caratteri speciali per Shell (ad es. Spazio o punto e virgola) dovrà essere citato.
  • >/dev/null - Il maggiore di reindirizza l'output del comando eseguito da watch su un file, /dev/null. Quel file scarta qualsiasi dato scritto su di esso. Ciò impedisce che l'output venga scritto sullo schermo o, poiché viene utilizzato Nohup, impedisce che l'output venga inviato a un file chiamato Nohup.out.
  • & - Il comando watch viene eseguito in background e il controllo viene restituito al processo terminale o padre.

Si noti che Nohup, il reindirizzamento dell'output e il & L'operatore di controllo in background non è specifico di watch.

Ecco una spiegazione dell'esempio yourprog script:

  • date - Visualizza la data e/o l'ora correnti. Può anche impostarli.
  • +%M.%S.%N - Questo specifica il formato di output che date deve usare. %M è il minuto corrente, %S è il secondo corrente e %N è l'attuale nanosecondo.
  • >> yourprog.out - Questo reindirizza l'output del comando date su un file chiamato yourprog.out. Il doppio maggiore di fa sì che l'output venga aggiunto al file su ogni invocazione anziché sovrascrivere il contenuto precedente.

Modifica :

Forse un'altra cosa che potrebbe essere abusata (o forse è un uso legittimo) sono i timer di sistema.

Vedi systemd/Timer come cron sostitutivo e Cron vs systemd timer .

Proverò a pubblicare un esempio presto.

Cron è progettato per svegliarsi ad ogni minuto, quindi non è possibile farlo senza un po 'di hacking, ad esempio dormire come hai detto.

14
Balázs Pozsár
* * * * * /path/to/program
* * * * * sleep 30; /path/to/program

Non dimenticare di scrivere qualcosa nel tuo programma in modo che esca se un'istanza precedente è già in esecuzione.

#!/bin/sh

if ln -s "pid=$$" /var/pid/myscript.pid; then
  trap "rm /var/pid/myscript.pid" 0 1 2 3 15
else
  echo "Already running, or stale lockfile." >&2
  exit 1
fi

Naturalmente, ciò lascia ancora una piccola opportunità di fallimento, quindi cerca su Google una soluzione migliore applicabile al tuo ambiente.

13
ghoti

Puoi farlo con software di terze parti.

Un'opzione che ha funzionato bene per me è frequent-cron

Permette la precisione in millisecondi e ti dà la possibilità di rinviare l'esecuzione successiva fino a quando quella attuale è uscita.

8
thatjuan

Avrei un paio di preoccupazioni:

(1) a volte un sistema si impegna e non può iniziare esattamente le cose sul punto di 30 secondi, è quindi possibile che nello stesso momento in cui si esegue un lavoro venga visualizzato un altro lavoro e quindi si abbiano 2 (o più) lavori che fanno lo stesso cosa. A seconda della sceneggiatura, potrebbero esserci delle interferenze significative qui. Pertanto, la codifica in uno script di questo tipo dovrebbe contenere un po 'di codice per assicurare che sia in esecuzione solo un'istanza di un determinato script.

(2) Lo script potrebbe avere un sacco di sovraccarico e consumare più risorse di sistema di quanto tu possa desiderare. Questo è vero se si è in competizione con molte altre attività di sistema.

Quindi, come ha scritto un poster, in questo caso prenderei seriamente in considerazione l'idea di inserire un demone in esecuzione con processi aggiuntivi per assicurarmi che rimanga in esecuzione se è di importanza cruciale per le tue operazioni.

2
mdpc

la mia soluzione più semplice e preferita per questo compito:

voce cron:
* * * * * flock -w0 /path/to/script /path/to/script

script:
while true;do echo doing something; sleep 10s;done

alternativa pigra: :)

* * * * * flock -w0 /path/to/log watch -n 10 echo doing >> /path/to/log

o

* * * * * flock -w0 /path/to/log watch -n 10 /path/to/script

professionisti

  • l'uso del comando flock evita di eseguire lo script da più istanze contemporaneamente. Può essere molto importante nella maggior parte dei casi.
  • I comandi flock e watch sono disponibili sulla maggior parte delle installazioni di Linux

cons

  • l'arresto di questo tipo di "Servizio" richiede due passaggi
    • commentare la voce cron
    • uccide lo script o il comando watch
1
asvany

Una soluzione, se è per il tuo script o se puoi avvolgerlo:

  1. Ottieni e ricorda l'ora di inizio.
  2. Se è presente un file di blocco, che toccherai in seguito, e lo script non è in esecuzione da 60 secondi, attendi un secondo e ricontrolla. (ad es. while/sleep) *
  3. Se il file di blocco è ancora presente dopo che sono trascorsi 60 secondi, uscire con un avviso di blocco non aggiornato.
  4. Tocca il file di blocco.
  5. Mentre lo script non è in esecuzione da 60 secondi, esegui il ciclo dell'attività effettiva con la durata del sonno desiderata.
  6. Elimina il file di blocco.
  7. Aggiungi minutamente cron.
  8. Bob e `tuo zio.

Meno mal di testa rispetto alla creazione e al monitoraggio di un demone.

* Se stai usando PHP, ricorda clearstatcache ().

0
Someone