Systemd Timer sind die moderne Alternative zu Cron-Jobs. Sie bieten bessere Integration, Logging und Flexibilität für geplante Aufgaben.

Vorteile gegenüber Cron

Vergleich

| Feature | Cron | Systemd Timer | |---------|------|---------------| | Logging | Minimal | Journald | | Abhängigkeiten | Keine | Ja | | Ressourcen-Limits | Keine | Ja | | Verpasste Jobs | Ignoriert | Nachholen möglich | | Status-Abfrage | Umständlich | Einfach | | Zufällige Verzögerung | Nein | Ja |

Grundstruktur

Timer + Service

Ein Timer benötigt zwei Dateien:
1. name.timer  - Wann ausführen
2. name.service - Was ausführen

Timer-Typen

| Typ | Beschreibung | |-----|--------------| | OnCalendar | Zu bestimmten Zeiten | | OnBootSec | Nach dem Boot | | OnUnitActiveSec | Nach letzter Aktivierung | | OnStartupSec | Nach Systemd-Start |

Timer erstellen

Einfacher Timer

# /etc/systemd/system/backup.timer

[Unit]
Description=Daily Backup Timer

[Timer]
OnCalendar=daily
Persistent=true

[Install]
WantedBy=timers.target
# /etc/systemd/system/backup.service

[Unit]
Description=Daily Backup Service

[Service]
Type=oneshot
ExecStart=/usr/local/bin/backup.sh

Aktivieren

systemctl daemon-reload
systemctl enable --now backup.timer

OnCalendar-Syntax

Beispiele

# Täglich um 02:00
OnCalendar=*-*-* 02:00:00

# Stündlich
OnCalendar=hourly
OnCalendar=*-*-* *:00:00

# Alle 15 Minuten
OnCalendar=*:0/15

# Montag bis Freitag um 08:00
OnCalendar=Mon..Fri *-*-* 08:00:00

# Erster des Monats
OnCalendar=*-*-01 00:00:00

# Jeden Sonntag um 03:00
OnCalendar=Sun *-*-* 03:00:00

# Alle 6 Stunden
OnCalendar=*-*-* 0,6,12,18:00:00

Kurzformen

minutely    # Jede Minute
hourly      # Jede Stunde
daily       # Täglich um 00:00
weekly      # Montag um 00:00
monthly     # Erster des Monats
yearly      # 1. Januar

Syntax prüfen

# Nächste Ausführungen anzeigen
systemd-analyze calendar "Mon..Fri *-*-* 08:00:00"
systemd-analyze calendar "daily"

Intervall-Timer

Nach Boot

# /etc/systemd/system/cleanup.timer

[Unit]
Description=Cleanup after boot

[Timer]
OnBootSec=5min
OnUnitActiveSec=1h

[Install]
WantedBy=timers.target

Wiederholend

[Timer]
# Erstmals 10 Minuten nach Start
OnStartupSec=10min

# Dann alle 30 Minuten
OnUnitActiveSec=30min

Praktische Beispiele

Log-Rotation

# /etc/systemd/system/logrotate.timer

[Unit]
Description=Daily log rotation

[Timer]
OnCalendar=daily
AccuracySec=1h
Persistent=true

[Install]
WantedBy=timers.target
# /etc/systemd/system/logrotate.service

[Unit]
Description=Rotate log files

[Service]
Type=oneshot
ExecStart=/usr/sbin/logrotate /etc/logrotate.conf
Nice=19
IOSchedulingClass=best-effort
IOSchedulingPriority=7

Datenbank-Backup

# /etc/systemd/system/mysql-backup.timer

[Unit]
Description=MySQL Backup Timer

[Timer]
OnCalendar=*-*-* 03:00:00
RandomizedDelaySec=900
Persistent=true

[Install]
WantedBy=timers.target
# /etc/systemd/system/mysql-backup.service

[Unit]
Description=MySQL Backup
Wants=mysql.service
After=mysql.service

[Service]
Type=oneshot
User=backup
ExecStart=/usr/local/bin/mysql-backup.sh
PrivateTmp=true

Zertifikat-Erneuerung

# /etc/systemd/system/certbot-renew.timer

[Unit]
Description=Certbot renewal timer

[Timer]
OnCalendar=*-*-* 00,12:00:00
RandomizedDelaySec=1h
Persistent=true

[Install]
WantedBy=timers.target
# /etc/systemd/system/certbot-renew.service

[Unit]
Description=Certbot renewal service

[Service]
Type=oneshot
ExecStart=/usr/bin/certbot renew --quiet
ExecStartPost=/bin/systemctl reload nginx

Optionen

Timer-Optionen

[Timer]
# Genauigkeit (Standard: 1min)
AccuracySec=1s

# Zufällige Verzögerung
RandomizedDelaySec=5min

# Verpasste Ausführungen nachholen
Persistent=true

# Timer aktivieren wenn Unit startet
OnActiveSec=0

# Nächste Ausführung relativ berechnen
FixedRandomDelay=true

Service-Optionen

[Service]
Type=oneshot

# Benutzer
User=backup
Group=backup

# Arbeitsverzeichnis
WorkingDirectory=/var/backups

# Umgebungsvariablen
Environment="BACKUP_DIR=/var/backups"
EnvironmentFile=/etc/backup.conf

# Ressourcen-Limits
CPUQuota=50%
MemoryLimit=512M

# Sicherheit
PrivateTmp=true
ProtectSystem=strict
ProtectHome=true

Timer verwalten

Status

# Alle Timer anzeigen
systemctl list-timers
systemctl list-timers --all

# Timer-Status
systemctl status backup.timer

# Service-Status
systemctl status backup.service

# Logs anzeigen
journalctl -u backup.service
journalctl -u backup.service --since today

Steuern

# Timer aktivieren
systemctl enable backup.timer
systemctl start backup.timer

# Timer deaktivieren
systemctl disable backup.timer
systemctl stop backup.timer

# Service manuell ausführen
systemctl start backup.service

Nächste Ausführung

# Zeigt wann Timer feuert
systemctl list-timers backup.timer

Monitoring und Fehlerbehandlung

Bei Fehler benachrichtigen

# /etc/systemd/system/backup.service

[Service]
Type=oneshot
ExecStart=/usr/local/bin/backup.sh
OnFailure=notify-failure@%n.service
# /etc/systemd/system/notify-failure@.service

[Unit]
Description=Send failure notification for %i

[Service]
Type=oneshot
ExecStart=/usr/local/bin/notify.sh "Job %i failed"
User=nobody
Group=systemd-journal

Timeout

[Service]
Type=oneshot
ExecStart=/usr/local/bin/long-task.sh
TimeoutStartSec=1h

Restart bei Fehler

[Service]
Type=oneshot
ExecStart=/usr/local/bin/task.sh
Restart=on-failure
RestartSec=5min
StartLimitInterval=30min
StartLimitBurst=3

Cron zu Systemd migrieren

Cron-Job

0 2 * * * /usr/local/bin/backup.sh

Entsprechender Timer

# backup.timer
[Timer]
OnCalendar=*-*-* 02:00:00
Persistent=true

# backup.service
[Service]
Type=oneshot
ExecStart=/usr/local/bin/backup.sh

Konvertierungs-Tabelle

| Cron | Systemd OnCalendar | |------|-------------------| | 0 | hourly oder :00 | | 0 0 | daily | | 0 0 0 | weekly oder Sun | | 0 0 1 | monthly | | /15 | :0/15 | | 0 6,18 | -- 06,18:00 |

Transiente Timer

Einmalige Ausführung

# In 5 Minuten ausführen
systemd-run --on-active=5m /usr/local/bin/task.sh

# Um bestimmte Zeit
systemd-run --on-calendar="2024-12-31 23:59:00" /usr/local/bin/newyear.sh

# Mit Unit-Name
systemd-run --unit=mytask --on-active=1h /usr/local/bin/task.sh

Wiederholend (temporär)

systemd-run --on-calendar="*:0/30" --timer-property=AccuracySec=1s /usr/local/bin/check.sh

Zusammenfassung

| Befehl | Funktion | |--------|----------| | systemctl list-timers | Timer auflisten | | systemctl status name.timer | Timer-Status | | journalctl -u name.service | Logs anzeigen | | systemd-analyze calendar | Zeitangabe prüfen | | systemd-run --on-active | Einmalig planen |

| Option | Beschreibung | |--------|--------------| | OnCalendar | Zeitbasiert | | OnBootSec | Nach Boot | | OnUnitActiveSec | Nach Aktivierung | | Persistent | Verpasste nachholen | | RandomizedDelaySec | Zufällige Verzögerung |

Fazit

Systemd Timer bieten deutliche Vorteile gegenüber Cron: besseres Logging, Abhängigkeiten, Ressourcen-Limits und Status-Abfragen. Die OnCalendar-Syntax ist flexibler als die Cron-Syntax. Für neue Installationen sind Systemd Timer die bessere Wahl. Bestehende Cron-Jobs können schrittweise migriert werden.