用 systemd timer 替代 crontab:在华为云 Flexus 服务器上做定时任务的实操小结
为什么考虑 systemd timer
在云服务器上跑定时任务,大多数人第一反应是 crontab。它简单,但有几个痛点:日志分散、任务失败没有状态可查、机器关机期间错过的任务不会补跑。systemd timer 是 systemd 自带的定时机制,能很好地解决这些问题。下面以一台华为云 Flexus 云服务器(Ubuntu 22.04)为例,演示如何把一个每天凌晨备份目录的任务改成 systemd timer。
第一步:写好要执行的脚本
sudo tee /usr/local/bin/backup-www.sh >/dev/null <<'SH'
#!/bin/bash
set -e
DATE=$(date +%F)
tar -czf /data/backup/www-$DATE.tar.gz /var/www
find /data/backup -name 'www-*.tar.gz' -mtime +7 -delete
SH
sudo chmod +x /usr/local/bin/backup-www.sh
sudo mkdir -p /data/backup
脚本做两件事:打包 /var/www,并删除 7 天前的旧备份,防止云硬盘被占满。
第二步:创建 service 单元
# /etc/systemd/system/backup-www.service
[Unit]
Description=Backup /var/www
[Service]
Type=oneshot
ExecStart=/usr/local/bin/backup-www.sh
Type=oneshot 表示这是一次性任务,执行完就退出。
第三步:创建 timer 单元
# /etc/systemd/system/backup-www.timer
[Unit]
Description=Daily backup of /var/www
[Timer]
OnCalendar=*-*-* 03:00:00
Persistent=true
RandomizedDelaySec=300
[Install]
WantedBy=timers.target
几个关键参数:
- OnCalendar:触发时间,这里是每天 03:00。可以用
systemd-analyze calendar "*-*-* 03:00:00"校验写法并查看下次触发时间。 - Persistent=true:如果服务器在 03:00 时处于关机状态,开机后会自动补跑一次,这是 crontab 做不到的。
- RandomizedDelaySec:随机延迟最多 5 分钟,多台机器同时备份到 OBS 时可以错峰,避免带宽打满。
第四步:启用并验证
sudo systemctl daemon-reload
sudo systemctl enable --now backup-www.timer
systemctl list-timers backup-www.timer
list-timers 会显示上次和下次执行时间。想立即测试一次,可以直接运行 sudo systemctl start backup-www.service。
第五步:查看日志和失败状态
journalctl -u backup-www.service -n 50
systemctl status backup-www.service
所有输出都进入 journal,不用再在脚本里手动重定向日志。任务失败时 systemctl --failed 能直接列出来,配合华为云云监控(CES)的主机监控插件或者自定义告警脚本,就能及时发现备份没跑成功。
小结
和 crontab 相比,systemd timer 的优势是:日志统一进 journal、任务有明确的成功/失败状态、支持关机补跑和随机延迟。对于在华为云 Flexus 或 ECS 上长期运行的备份、证书续期、日志清理等任务,非常值得迁移过来。迁移时注意 OnCalendar 使用的是服务器本地时区,华为云镜像默认时区可能是 UTC,可以先用 timedatectl 确认并按需改为 Asia/Shanghai。
- 点赞
- 收藏
- 关注作者
评论(0)