Как я перестал бояться cron: таймеры systemd
Много лет все мои периодические задачи жили в crontab. Работало, пока не нужно было понять, почему задача молча не выполнилась ночью. У cron нет журнала, кроме почты, которую на домашнем сервере никто не читает.
Минимальная пара файлов
Таймер состоит из двух юнитов: службы, которая делает работу, и таймера, который её запускает.
# /etc/systemd/system/photos-sync.service
[Service]
Type=oneshot
ExecStart=/usr/local/bin/photos-sync
# /etc/systemd/system/photos-sync.timer
[Timer]
OnCalendar=*-*-* 03:30
Persistent=true
[Install]
WantedBy=timers.target
Persistent=true решает главную боль cron: если в 03:30 машина была выключена, задача выполнится сразу после включения.
Что смотреть, когда что-то пошло не так
systemctl list-timers
journalctl -u photos-sync.service --since today
Код возврата, время запуска и весь вывод лежат в журнале. Это и есть главная причина переехать.
Грабли
Первая: OnCalendar считается в часовом поясе системы, если явно не указать другой. Вторая: служба типа oneshot без TimeoutStartSec может висеть сколько угодно, поэтому для сетевых задач я всегда ставлю разумный предел.