部署两个实例,定时任务为什么执行了两遍?ShedLock 是怎么保证只跑一次的?lockAtMostFor 和 lockAtLeastFor 各有什么用?任务比锁时间长会怎样?实例崩了多久能恢复?这篇用两个进程和真实的 MySQL 锁表逐项实测。
前 10 秒:A 执行 9 次,B 执行 9 次,合计 18 次(单实例应该是 10 次)
两个实例各跑一遍,翻倍。
运行中 shedlock 表里的行(name, locked_by):(('locked', 'ws-MacBook-Pro.local'),);A、B 是同一台机器上的两个进程,locked_by 都是这台机器的主机名
20 秒里 A 执行 5 次,B 执行 2 次,合计 7 次;相邻两次执行的间隔(秒)[2.9, 2.0, 3.0, 2.0, 3.0, 3.0];执行者依次是 AAABAAB先到先得;lockAtLeastFor 拉大最短间隔;锁表一行;locked_by 默认主机名。
一共执行了 5 次,执行者依次是 BABAB;其中有重叠的相邻两次(前者, 后者, 重叠秒数)[('B', 'A', 1.1), ('A', 'B', 2.9), ('B', 'A', 1.1), ('A', 'B', 2.9)]lockAtMostFor 太短导致并发重叠。
A 先拿到锁开始执行,1 秒后被 kill -9;另一个实例 B 在被杀后 5.9 秒才第一次执行(距离那次加锁 6.9 秒,约等于 lockAtMostFor)
锁不释放,要等 lockAtMostFor 到期。