Back to site

Scheduled tasks with cron

Schedule backups, scripts, and maintenance on a HolyCloud VPS with crontab, field syntax, logging, and best practices.

Scheduled tasks with cron

Cron runs commands at regular intervals on your HolyCloud Linux VPS: rsync backups, log rotation, report delivery, or nightly apt upgrade. This guide explains crontab syntax, execution environment, logging, and common pitfalls (paths, timezone).

Prerequisites

  • HolyCloud VPS Ubuntu/Debian with cron installed (cron package by default)
  • sudo access for system tasks (/etc/cron.d/, /etc/cron.daily/)
  • Scripts tested manually before scheduling
  • Timezone configured (see « Timezone and NTP ») — cron uses the server local time

Tip: always redirect stdout and stderr to a log file or explicit /dev/null to avoid spamming root by email.

Step 1: check the cron service

systemctl status cron
which crontab

Install if missing:

sudo apt update
sudo apt install -y cron
sudo systemctl enable --now cron

Step 2: crontab line syntax

┌───────────── minute (0-59)
│ ┌─────────── heure (0-23)
│ │ ┌───────── jour du mois (1-31)
│ │ │ ┌─────── mois (1-12)
│ │ │ │ ┌───── jour de la semaine (0-7, 0 et 7 = dimanche)
│ │ │ │ │
* * * * * commande

Examples:

| Expression | Meaning |

|------------|---------------|

| 0 3 * | Every day at 03:00 |

| /15 * | Every 15 minutes |

| 0 0 0 | Every Sunday at midnight |

| @daily | Alias for 0 0 * |

Step 3: user crontab

Edit your crontab:

crontab -e

Example — web directory backup at 02:30:

30 2 * * * /usr/bin/rsync -a /var/www/ /var/backups/www/ >> /var/log/rsync-cron.log 2>&1

List and save:

crontab -l
crontab -l > ~/crontab-backup-$(date +%F).txt

Remove all entries:

crontab -r

Step 4: environment variables

Cron does not always load .bashrc. At the top of the crontab:

SHELL=/bin/bash
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
[email protected]

0 4 * * * /opt/scripts/backup.sh

Example script /opt/scripts/backup.sh:

#!/bin/bash
set -euo pipefail
DATE=$(date +%F)
tar -czf "/var/backups/app-$DATE.tar.gz" /var/www/exemple.fr
find /var/backups -name 'app-*.tar.gz' -mtime +7 -delete
sudo chmod +x /opt/scripts/backup.sh
sudo chown root:root /opt/scripts/backup.sh

Step 5: system tasks (/etc/cron.d)

Dedicated file (must include a user in the line):

sudo nano /etc/cron.d/monapp-backup
# m h dom mon dow user  command
15 3 * * * root /opt/scripts/backup.sh >> /var/log/monapp-backup.log 2>&1
sudo chmod 644 /etc/cron.d/monapp-backup
sudo systemctl reload cron

Pre-packaged Debian daily scripts:

ls -la /etc/cron.daily/
sudo run-parts --test /etc/cron.daily

Step 6: logging and debugging

System logs (recent Ubuntu/Debian):

grep CRON /var/log/syslog | tail -20
journalctl -u cron -n 30 --no-pager

Test a command soon (in 2 minutes):

*/2 * * * * echo "test $(date)" >> /tmp/cron-test.log

Wait then:

cat /tmp/cron-test.log

Step 7: restrictions and security

Limit who can use cron:

cat /etc/cron.allow 2>/dev/null || echo "Pas de cron.allow"
ls /etc/cron.deny 2>/dev/null

Never schedule curl | bash from the Internet; prefer versioned scripts under /opt/.

Verification

crontab -l
sudo ls -la /etc/cron.d/
systemctl is-active cron
grep "$(whoami)" /var/log/syslog | grep CRON | tail -5

After the scheduled time, the log file or expected output should exist.

Need help?

  • Task does not run: absolute path (which rsync), execute permission, MAILTO / logs
  • Wrong timezone: timedatectl status
  • Permission denied on /etc/cron.d: root owner, mode 644, user field required
  • HolyCloud support: crontab -l, grep CRON /var/log/syslog excerpt, script and scheduled time