Comment exécuter des scripts toutes les 5 secondes?

66

J'ai un script qui doit être exécuté toutes les cinq secondes. Je sais que vous cronpouvez effectuer des tâches à la minute près, mais existe-t-il un moyen d'exécuter quelque chose toutes les secondes?

myusuf3
la source
3
Quel problème essayez-vous de résoudre? Êtes-vous sûr que cron est la bonne solution?
andol
1
Je sais que cron n'est pas la bonne solution. Je disais que ce n'était pas dans la question. Lisez s'il vous plaît. J'essaie de faire exécuter un script toutes les 5 secondes.
myusuf3
2
Désolé, je suppose que la question est un peu fausse. Pourtant, vous vous demandez toujours si vous essayez de résoudre le bon problème.
andol
Pour les personnes qui viennent ici cherchent comment faire quelque chose toutes les 5 secondes. Je vous recommande vivement d’explorer comment programmer en temps réel avec des outils tels que socket.io, par exemple.
Brandon Bertelsen
Avez-vous découvert la commande bash sleep? sleep 5fait une pause (peut-être dans une boucle) pendant 5 secondes) ...?
SDsolar

Réponses:

64

Cron ne permet qu'une minute au minimum. Ce que vous pouvez faire est d'écrire un script shell avec une boucle infinie qui exécute votre tâche, puis dort pendant 5 secondes. Ainsi, votre tâche sera exécutée plus ou moins toutes les 5 secondes, en fonction de la durée de la tâche.

#!/bin/bash

while true; do
  # Do something
  sleep 5;
done

Vous pouvez créer un my-task.shfichier avec le contenu ci-dessus et l'exécuter avec sh my-task.sh. Vous pouvez éventuellement le configurer avec supervisorun service afin qu'il démarre au démarrage du système, etc.

On dirait vraiment que vous faites quelque chose que vous ne devriez probablement pas faire cependant. Cela ne va pas .

Tommy Brunn
la source
On peut avoir besoin d’un cron lancé toutes les 5 secondes, voire moins, pour être utilisé dans les scrapers basés sur PHP.
Ravish Kumar
Se sent vraiment mal. Si vous l'incluez dans un travail cron, vos tâches se chevaucheront toutes les minutes. Après une heure, 60 travaux démarreront toutes les 5 secondes. Si vous n'incluez pas dans un travail cron, eh bien, vous ne pourrez peut-être pas savoir comment l'arrêter, ni même savoir qu'il existe.
SeF
35

Vous pouvez avoir un cronjob qui lance un script chaque minute et qui démarre ainsi 12 processus en arrière-plan:

* * * * * ~/dostuff.sh

dostuff.sh:

(sleep 5 && /path/to/task) &
(sleep 10 && /path/to/task) &
(sleep 15 && /path/to/task) &
(sleep 20 && /path/to/task) &
(sleep 25 && /path/to/task) &
(sleep 30 && /path/to/task) &
(sleep 35 && /path/to/task) &
(sleep 40 && /path/to/task) &
(sleep 45 && /path/to/task) &
(sleep 50 && /path/to/task) &
(sleep 55 && /path/to/task) &
(sleep 60 && /path/to/task) &

Ma question, cependant, est la suivante: que pouvez-vous faire sur la Terre et qui doit être exécuté toutes les 5 secondes?


la source
1
Cela m’est bien venu lorsque j’ai créé un script qui vérifie de manière répétée le /mediarépertoire d’un lecteur que je connecte à USB pour des sauvegardes automatiques ...
VF1
32
What on EARTH- statistiques, ramassage des ordures, synchronisation de fichiers, statut en ligne, vous le nommez.
ruX
3
Référencement d'une API externe pour des données en temps quasi réel. Exécuter une demande toutes les 5 secondes est BEAUCOUP mieux que de le faire à chaque vue de page.
Sergey Kudriavtsev
1
Et si crontab exécutait le fichier dostuff.sh deux fois? Par exemple, à la 55e seconde, le script est exécuté mais n'a pas encore fini, mais le cron appelle le script à nouveau, que va-t-il se passer?
TomSawyer
2
C'EST MAUVAIS! Il exécute potentiellement le script plusieurs fois à la fois (si cela prend plus de 5 secondes), ce qui peut conduire à une situation de concurrence critique dans tous les fichiers (même temporaires) auxquels vous accédez. NE PAS FAIRE si faire la même chose deux fois en même temps peut causer un problème! (Et ce sera généralement le cas!)
Nonny Moose
27

Il suffit d'utiliser une boucle:

while true ; do ./your-script & sleep 5; done

Cela lancera votre script en tant que tâche en arrière-plan, dormira pendant 5 secondes, puis effectuera une nouvelle boucle. Vous pouvez utiliser Ctrl-C pour l’abandonner, ou utiliser toute autre condition à la place de true, par exemple, ! test -f /tmp/stop-my-scriptne boucler que lorsque le fichier /tmp/stop-my-scriptn’existe pas.

blueyed
la source
Si j'inclus l'esperluette, ça dit bash: syntax error near unexpected token ';', alors je l'ai sorti. J'ai bash 4.3.11. Ma commande s'exécute rapidement, donc ça va si elle s'exécute au premier plan.
Tyler Collier
1
@TylerCollier Si vous aviez besoin ./your-scriptde courir en arrière-plan (pendant le sommeil de 5 secondes), vous pouvez garder &mais laisser tomber le fichier ;. Comme il &sert à séparer les commandes, il est inutile (et apparemment non autorisé) de les suivre ;après sur la même ligne. Une autre méthode consiste à écrire la boucle sur plusieurs lignes (avec un saut de ligne après &et, éventuellement, des sauts de ligne après doet avant done). Puisque l' ;après &semble être une faute de frappe, je l'ai enlevée. blueyed: S'il vous plaît n'hésitez pas à mettre le ;dos si vous le voulez vraiment; si c'est le cas, je suggère également d'ajouter une explication.
Eliah Kagan
@EliahKagan FWIW, cela fonctionne sur Zsh (pas d'erreur de syntaxe), mais ce n'est pas vraiment nécessaire. Merci pour l'édition!
blueyed
10

Vous pouvez utiliser le paquet GNU mcron , une alternative "Vixie cron".

http://www.gnu.org/software/mcron/manual/mcron.html#Top

"Peut facilement permettre de spécifier des points de temps plus fins, c'est-à-dire des secondes. En principe, cela pourrait être étendu à des microsecondes, mais cela n'est pas implémenté."

David
la source
C'est exactement ce que je cherchais. Je vous remercie!
SDsolar
Merci de poster ceci comme réponse à ma question ici: askubuntu.com/questions/922216/… afin que je puisse accepter votre réponse.
SDsolar
mcronnécessite sendmaild'être installé et activé par défaut. comment le désactiver?
ihsan
2

La configuration minimale dans cron est de quelques minutes, vous ne pouvez pas la définir pendant 5 secondes. Vous pouvez utiliser Quartz qui permet des secondes. http://www.quartz-scheduler.org/docs/tutorials/crontrigger.html

Cody Harlow
la source
Il semble que Quartz n'est pas une source ouverte. Est-ce correct?
txwikinger
Il a une version open source. Il n'a pas de page mais allez simplement à la page de téléchargement. Vous n'êtes pas obligé de remplir le formulaire, il vous suffit de cliquer pour m'emmener au téléchargement.
Cody Harlow
semble être une source ouverte depuis au moins 2018. github.com/quartz-scheduler/quartz
dogmatic69
2

Utilisez cacti pour surveiller le routeur et le commutateur, mais Cron ne permet qu'une minute au minimum. Par conséquent, si un port / périphérique est arrêté, aucun avertissement n'est émis avant deux minutes.

qttty
la source
1
Je recommande de modifier cette réponse pour la développer avec des détails spécifiques sur la façon de procéder. (Voir aussi Comment puis-je écrire une bonne réponse? Pour des conseils généraux sur les types de réponses considérés comme les plus utiles sur Ask Ubuntu.)
David Foerster
2

Vous pouvez utiliser une minuterie SystemD, qui déclenchera un service - que vous auriez configuré pour faire ce que vous voulez - toutes les 5 secondes.

Supposons que votre unité de service soit appelée mystuff.serviceet qu'elle soit installée dans /etc/systemd/system(consultez les services utilisateur SystemD si vous souhaitez remplacer la crontab d'un utilisateur), vous pouvez alors écrire une unité de minuterie pour exécuter le service au démarrage, puis toutes les 5 secondes, comme suit:

/etc/systemd/system/mystuff.timer

[Unit]
Description=my stuff's schedule
[Timer]
OnBootSec=5
OnUnitActiveSec=5
[Install]
WantedBy=timers.target

Rechargez ensuite la configuration de systemd, activez le programmateur et démarrez-le.

Guss
la source
1
C'est la meilleure solution, le seul inconvénient est que cron est beaucoup plus facile à visualiser et à configurer. SystemD est une douleur et il commence par sa structure de répertoires. Toujours le meilleur pour un intervalle de 5 secondes
John
L'extrait ci-dessus ne serait-il pas placé dans /etc/systemd/system/mystuff.timer au lieu de mystuff.service?
Brooks
@ Brooks: oui, mon mauvais - mauvais copier-coller de mon côté. Fixé.
Guss
Merci ... content de savoir que je ne suis pas fou pendant mon apprentissage de systemd :)
Brooks
1

J'ai fait ce genre de chose avec beaucoup de succès (et le résultat final dure plusieurs semaines à la fois, jusqu'à ce que la machine soit redémarrée). En ce qui concerne ce que je faisais actuellement, mettre à jour les informations et les mettre en cache - mises à jour toutes les 10 secondes.

#!/bin/sh

SLEEP=5

# do stuff
sleep $SLEEP

# do stuff
sleep $SLEEP

# do stuff
sleep $SLEEP

# do stuff
sleep $SLEEP

# echo and restart...
exec $0

Le 'exec $ 0' redémarre le script, mais remplace le script en cours d'exécution. Il peut être démarré initialement avec une ligne '@reboot' crontab.

Alister Bulman
la source
8
Pourquoi ne pas utiliser une whileboucle au lieu de redémarrer le script à plusieurs reprises?
David Z