Bash Tutorial · Linux System Skills · Lesson 28 of 30
Bash Scheduling with cron and systemd Timers
Run scripts on a schedule with cron and systemd timers, and write scripts that behave well when scheduled.
cron
crontab -e edits your scheduled jobs. Each line is minute hour day-of-month month day-of-week command:
# every day at 03:30, append output to a log
30 3 * * * /opt/scripts/backup.sh >> /var/log/backup.log 2>&1
# every 15 minutes on weekdays
*/15 * * * 1-5 /opt/scripts/sync.sh
cron runs with a minimal environment (short PATH, no profile), so use absolute paths and set what you need inside the script.
systemd timers
On modern Linux servers, systemd timers add logging (journalctl -u backup), dependencies and catch-up for
missed runs:
# /etc/systemd/system/backup.timer
[Timer]
OnCalendar=*-*-* 03:30:00
Persistent=true
[Install]
WantedBy=timers.target
Scheduled-script checklist
Use strict mode, absolute paths, a lock so runs don't overlap (flock), and log with timestamps:
cat > nightly.sh <<'EOF'
#!/usr/bin/env bash
set -euo pipefail
exec 9>"$HOME/nightly.lock"
flock -n 9 || { echo "already running, skipping"; exit 0; }
log() { printf '%s %s\n' "$(date -u -d @1768471200 +%FT%TZ)" "$*"; }
log "backup started"
log "backup finished"
EOF
chmod +x nightly.sh
./nightly.sh
flock "$HOME/nightly.lock" sleep 1 & # another run holds the lock
sleep 0.2
./nightly.sh
wait
Output
2026-01-15T10:00:00Z backup started 2026-01-15T10:00:00Z backup finished already running, skipping
Run this on your computer — see “Get Started” for setup.
Test yourself
Why do cron jobs often fail when the same script works in your terminal?
cron can't run bashcron runs with a minimal environment and a short PATHcron needs rootcron ignores the shebang
Show answer
Answer: cron runs with a minimal environment and a short PATH