症状:跑错时间或根本没跑
排班“每天 8 点跑批”,结果凌晨 0 点跑了,或者干脆没动静。先查两处:调度服务是否在跑、服务器现在几点了。服务正常但时间不对,九成是表达式或时区问题,接着往下对。
提示:先确认“服务时区”,再怀疑表达式,顺序反了会浪费一小时。
第一关:字段,Quartz 与 Linux 别混
Quartz 表达式 7 位(秒 分 时 日 月 周 年),Linux crontab 5 位(分 时 日 月 周),直接复制是翻车头号原因。用在线 Cron 生成器点选生成,选对格式再复制,常见排班一次写对:
每天 8:00(Quartz):0 0 8 * * ? *
每 5 分钟(Quartz):0 0/5 * * * ? *
工作日 9:30(Quartz):0 30 9 ? * MON-FRI *
注意:Quartz 里“日”和“周”只能一处取值,另一处必须写问号,两处都写具体日期是非法表达式。
第二关:时区,容器里的隐形坑
本机 8 点准时,容器里差 8 小时:镜像默认 UTC,而业务要按北京时间跑。解法二选一:容器挂载宿主机时区,或调度统一按 UTC 写表达式(北京时间 8 点即 0 0 0 * * ? *)。用时间计算工具换算对照,排班前先对表。
排班前验证下次执行时间
表达式写完别直接上线,解析出未来 5 次执行时间逐个核对:工作日是否含周末、月末 31 号的月份会不会跳过、闰年 2 月 29 日怎么办。验证通过再发布,比半夜被报警叫醒划算得多。
运维:幂等、重叠与日志
任务必须可重入:上次没跑完下次又触发,叠加执行会把数据跑坏,加分布式锁或单实例约束。每次执行记开始结束时间与影响行数,出问题按时间线回查,排班事故复盘才有依据。