web-dev-qa-db-fra.com

comment configurer cronjob pendant 2 jours?

Nous aimerions utiliser un cronjob pour créer une sauvegarde de base de données.

La sauvegarde doit avoir lieu tous les deux jours. Peut-on utiliser les entrées cron suivantes?

0 0 2 * * * backup-command

Si cela ne va pas, dites-moi la commande correcte pour configurer le cron pendant 2 jours.

36
someone

De ici :

Cron prend également en charge les valeurs de "pas".

Une valeur de */2 dans le champ dom signifierait que la commande s'exécute tous les deux jours et de même, */5 dans le champ des heures signifie que la commande s'exécute toutes les 5 heures. par exemple.

* 12 10-16/2 * * root backup.sh

est le même que:

* 12 10,12,14,16 * * root backup.sh

Je pense donc que vous voulez 0 0 */2 * *.

Ce que vous avez (0 0 2 * *) exécutera la commande le 2 du mois à minuit, chaque mois.

p.s. Vous semblez avoir un astérisque supplémentaire dans votre réponse. Le format doit être:

minute hour dom month dow user cmd

Votre astérisque supplémentaire serait donc dans le champ user. Est-ce prévu?

65
Dominic Rodger

Disclaimer: ceci est une copie de ma deleted réponse ici . Je crois que cette question est plus canonique , et ma réponse convient mieux ici.

Il y a deux façons d'interpréter cette question.

  • Je voudrais planifier un travail cron tous les deux jours du mois.
  • Je voudrais planifier un travail cron tous les deux jours.

Ce sont deux cas complètement différents en raison du nombre de jours qu'il y a dans un mois.

Je voudrais planifier un cronjob tous les deux jours du mois.

Pour cela, nous utilisons la combinaison de la définition d'une plage et d'une valeur de pas:

man 5 crontab: Les valeurs de pas peuvent être utilisées conjointement avec des plages. Suite à une plage avec /<number> spécifie les sauts de la valeur du nombre dans la plage. Par exemple, 0-23/2 peut être utilisé dans le champ 'heures' pour spécifier l'exécution des commandes toutes les deux heures (l'alternative dans la norme V7 est 0,2,4,6,8,10,12,14,16,18,20,22). Les valeurs d'étape sont également autorisées après un astérisque. Par conséquent, si vous spécifiez un travail à exécuter toutes les deux heures, vous pouvez utiliser */2.

Voir les exemples suivants:

# Example of job definition:
# .-------------------- minute (0 - 59)
# |  .----------------- hour (0 - 23)
# |  |  .-------------- day of month (1 - 31)
# |  |  |      .------- month (1 - 12) OR jan,feb,mar,apr ...
# |  |  |      |  .---- day of week (0 - 6) (Sunday=0 or 7)
# |  |  |      |  |
# *  *  *      *  *   command to be executed
  0  0  */2    *  *   command1
  0  0  2-31/2 *  *   command2
  *  *  */2    *  *   command3
  • command1 sera exécuté à 00:00 tous les jours impairs (plage par défaut avec l'étape 2, c'est-à-dire 1,3,5,7, ..., 31)
  • command2 sera exécuté à 00h00 tous les jours pairs (c'est-à-dire 2,4,6,8, ..., 30)
  • command3 est une erreur souvent commise. Cela fonctionnera à chaque minute de chaque jour impair.

Remarque: Il faut comprendre que dans cette approche command1 se déroulera les 31 janvier et 1er février (2 jours consécutifs)

Remarque: Il faut comprendre que dans cette approche command2 sautera le 31 janvier et le 1er février et ne fonctionnera que 3 jours plus tard.

Je voudrais planifier un cronjob tous les deux jours (à partir du jour X)

Ici, cela devient plus intéressant. Les notes ci-dessus ont déjà démontré le problème des mois ayant un nombre impair de jours.

La manière la plus rapide de penser serait d'évaluer le jour de l'année:

% date -d "2018-01-31" '+%j'
031
% date -d "2018-02-01" '+%j'
032

et vous pourriez facilement rechercher s'il s'agit d'un nombre pair ou impair. Cependant, lorsque vous faites cela, vous avez à nouveau un problème le 31 décembre et le 1er janvier d'une année commune (365 jours; les années bissextiles ont 366 jours). Cela peut être résolu lorsque vous disposez d'un compteur continu à partir d'un jour donné. Entrez l’horodatage UNIX, le nombre total de secondes écoulées depuis 1970-01-01 00:00:00 UTC.

% date -d "2018-12-31" '+%s %j'                                                                                                                                                                                                               
1546214400 365
% date -d "2019-01-01" '+%s %j' 
1546300800 001
% date -d "2019-12-31" '+%s %j'                                                                                                                                                                                                               
1577750400 365
% date -d "2020-01-01" '+%s %j'                                                                                                                                                                                                               
1577836800 001

Pour un cronjob à exécuter command4 uniquement tous les deux jours à 00:00 et command5 tous les trois jours à 00:00 à partir du "14/03/2018", la crontab ressemblerait à ceci:

# Example of job definition:
# .---------------- minute (0 - 59)
# |  .------------- hour (0 - 23)
# |  |  .---------- day of month (1 - 31)
# |  |  |  .------- month (1 - 12) OR jan,feb,mar,apr ...
# |  |  |  |  .---- day of week (0 - 6) (Sunday=0 or 7)
# |  |  |  |  |
# *  *  *  *  *   command to be executed
  0  0  *  *  *   daytestcmd 2 && command4
  0  0  *  *  *   daytestcmd 3 20180314 && command5

avec daytestcmd défini comme

#!/usr/bin/env bash
# get start time in seconds
start=$(date -d "${2:-@0}" '+%s')
# get current time in seconds
now=$(date '+%s')
# get the amount of days (86400 seconds per day)
days=$(( (now-start) /86400 ))
# set the modulo
modulo=$1
# do the test
(( days >= 0 )) && (( days % modulo == 0))

Remarque: L'heure UNIX est donnée en UTC. Si votre cron fonctionne dans un fuseau horaire différent qui est influencé par l'heure d'été, il est conseillé de ne pas exécuter la commande entre 2 et 3 heures. Cela pourrait ignorer la commande ou l'exécuter deux fois (selon que le temps passe en avant ou en arrière)

Remarque: L'heure UNIX n'est pas influencée par les secondes intercalaires

8
kvantour