2

У меня есть такая запись в моем crontab:

0 0 1-2 * 1-6

Это правильно, что он будет работать в 00:00, 1-го или 2-го числа месяца с понедельника по субботу? Например, если 1-й день будет воскресеньем, он не будет работать, верно? Но вместо этого он будет запускать cronjob во 2-й день месяца, потому что это не будет воскресенье.

1 ответ1

5

Если первый день месяца - воскресенье, он действительно будет работать.

Причина в том, что два условия "день месяца" (третье поле) и "день недели" (пятое поле) связаны не с AND (оба должны встречаться), а с OR (любое из них должно встречаться). От man 5 crontab:

Примечание. День выполнения команды может быть задан двумя полями: день месяца и день недели. Если оба поля ограничены (т. Е. Не *), команда будет запущена, когда любое из полей соответствует текущему времени. Например, `` 30 4 1,15 * 5 '' будет запускать команду в 4:30 утра 1-го и 15-го числа каждого месяца плюс каждую пятницу.

Таким образом, ваш cronjob будет запускаться в полночь каждый 1-й и 2-й месяц месяца, а также каждый понедельник, вторник, четверг, четверг и субботу месяца.

Если вам нужно запускать команду только один раз в месяц, но не в воскресенье, как вы пишете в своем комментарии, вы должны проверить дату в самой команде .

Вот условия для запуска команды:

IF (date is 1st day of month AND date is not Sunday) 
    OR (date is 2nd day of month AND yesterday was Sunday) 
THEN run command

Вы могли бы написать два cronjobs:

0 0 1 * * test $(date +\%u) -eq 7 || echo "today's the 1st day of the month but not Sun"
0 0 2 * * test $(date +\%u) -eq 1 && echo "today's Mon (=yesterday was Sun) and the 2nd day of the month"

Первый cronjob будет запускаться каждый 1-й день месяца в полночь:

  • date +%u возвращает целое число, где 1 - Mon, 2 - Tue и т. д. («%» необходимо экранировать в crontab).

  • test проверяет, равняется ли $(date +%u1) 7 (воскресенье).

  • || является логическим оператором OR, он реагирует на возвращаемое значение предыдущей команды. Если test возвращает FALSE, выполняется остальная часть команды.

Второй cronjob будет запускаться каждый второй день месяца в полночь:

  • Опять же, date +%u возвращает целое число, где 1 - понедельник, 2 - вторник и т.д.

  • test проверяет, равен ли $(date +%u1) 1 (понедельник).

  • && - логический оператор AND, если test возвращает TRUE, то выполняется остальная часть команды.

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .