跳转到主内容
websoft网络软件专家 - 深耕网络技术,打造实用软件!

systemd timer 延迟执行或错过的精度与 OnCalendar 配置注意

systemd timer 默认不保证精确触发,因设计侧重负载均衡与可靠性而非实时性;OnCalendar 受 AccuracySec(默认60s)和RandomizedDelaySec影响,weekly/monthly基于日历计算首个匹配时刻;Persistent=true可补漏单次错过,配合OnUnitInactiveSec=1d实现每日至少执行一次。

systemd timer 的延迟执行和精度问题,主要源于其设计目标并非实时调度,而是兼顾系统负载、电源管理与服务可靠性。默认情况下,timer 不会严格按秒级甚至分钟级触发,尤其在系统休眠、高负载或服务未激活时,容易出现延迟甚至跳过执行。

OnCalendar 时间表达式的精度陷阱systemd 的OnCalendar支持类似 cron 的时间语法,但底层实现不同:它基于 monotonic 和 realtime 时钟混合判断,且受AccuracySec和RandomizedDelaySec影响。

写成*-*-* 02:00:00并不等于“每天凌晨2点整触发”——实际可能延后最多AccuracySec(默认60秒)

若省略秒字段(如02:00),systemd 会自动补为02:00:00,但依然受 AccuracySec 约束使用weekly、monthly等关键词时,触发时间是基于日历计算的“首个匹配时刻”,不是固定偏移;例如weekly总在周一 00:00 触发,哪怕 timer 是周三启用的错过执行(Missed Trigger)的常见原因与应对当 timer unit 被禁用、系统关机/休眠、或对应 service 处于 failed 状态时,下一次 OnCalendar 到达前若条件不满足,该次触发即被跳过——systemd 默认不“补跑”。

启用Persistent=true可让 timer 在下次启动时检查是否遗漏了最近一次触发,并立即运行对应 service(仅对已过期的单次有效,不累积多次)

注意:

Persistent对OnUnitActiveSec或OnBootSec类型无效,只作用于OnCalendar和OnClockChange若需强保证“至少每日执行一次”,建议搭配OnUnitInactiveSec=1d作为兜底(配合 Persistent),避免因某天完全 missed 导致断更提升定时精度的关键配置项真正影响“准点度”的不是 OnCalendar 写法本身,而是 timer unit 中几个易被忽略的选项:AccuracySec=1s:将最大容忍延迟从默认 60s 降至 1 秒(仍非硬实时,但对多数运维任务足够)

RandomizedDelaySec=0:关闭随机抖动(默认关闭,但显式设为 0 更明确)

StartLimitIntervalSec=0:避免因频繁失败触发速率限制,间接导致延迟确保对应 service 的Type=oneshot且无RemainAfterExit=yes冗余设置,否则 timer 可能误判 service 仍在运行而跳过下次启动验证与调试技巧不要只看systemctl list-timers显示的 “NEXT” 时间——它只是预测值,未必反映真实行为。

用systemctl status your.timer查看 Last Trigger 和 Triggered 字段,确认是否真有执行记录

启用日志追踪:

systemctl enable --now your.timer后,执行journalctl -u your.service -u your.timer -f实时观察触发与启动过程测试 missed 行为:手动停用 timer → 等待 OnCalendar 时间过去 → 重新 enable → 检查是否触发(需 Persistent=true 才生效)

相关文章