求助 quartz框架集群模式下任务重复调度的问题
- 内容介绍
- 文章标签
- 相关推荐
生产上是2台应用服务器的集群,任务调度时会偶发出现2个节点同时执行某个任务(A服务器和B服务器上同一时间点各执行了一遍)。目前毫无思路 有没有懂quartz框架原理的佬看看可能是什么原因导致的,或者说有什么排查思路。
// quartz参数
Properties prop = new Properties();
prop.put("org.quartz.scheduler.instanceName", "MyScheduler");
prop.put("org.quartz.scheduler.instanceId", "AUTO");
// 线程池配置
prop.put("org.quartz.threadPool.class", "org.quartz.simpl.SimpleThreadPool");
prop.put("org.quartz.threadPool.threadCount", "20");
prop.put("org.quartz.threadPool.threadPriority", "5");
prop.put("org.quartz.jobStore.class", "org.springframework.scheduling.quartz.LocalDataSourceJobStore");
// 集群配置
prop.put("org.quartz.jobStore.isClustered", "true");
prop.put("org.quartz.jobStore.clusterCheckinInterval", "15000");
prop.put("org.quartz.jobStore.maxMisfiresToHandleAtATime", "1");
prop.put("org.quartz.jobStore.misfireThreshold", "12000");
prop.put("org.quartz.jobStore.tablePrefix", "QRTZ_");
factory.setQuartzProperties(prop);
factory.setSchedulerName("RedpScheduler");
factory.setStartupDelay(1);
factory.setApplicationContextSchedulerContextKey("applicationContextKey");
// 启动时更新己存在的 Job
factory.setOverwriteExistingJobs(true);
// 设置自动启动,默认为 true
factory.setAutoStartup(true);
网友解答:
--【壹】--:
xxljob多节点轮巡,串行任务一样有可能重复执行。
--【贰】--:
那么多车,蹬起问gpt-5.4啊
--【叁】--:
用xxljob
--【肆】--:
你用xxl-job再加docker部署你就明白了,xxl-job会找不到实例
--【伍】--:
那可能是我太久没碰已修复了这个问题吧,当时这个问题搞我连夜把xxl-job换掉,我就给拉黑了
--【陆】--:
我没遇到过这种现象。
它jobstore用db的时候,好像有个db级别的lock,具体的可以让AI帮忙分析一下。
--【柒】--:
quartx框架只适合单体应用使用,quartz的触发是读取fired表的数据,两个应用会同时触发。
方案一:
如果不想大变的情况下,建议是加redis 全局锁,这样可以做到不重复执行,改动最小,可能十分钟就搞完了。
方案二:
切elasticJob、xxl-job这类分布式调度中心,不过个人不推荐,缺点太多,只有一个定时任务全局不重复的优点,而且还不支持docker 多副本,那还不如就quartz+redis全局锁了。
--【捌】--:
蹬冒烟了已经hhh
--【玖】--:
k8s支持,docker也可以使用network支持的。xxl-job也支持自定义ip的
--【拾】--:
这种任务做幂等比较好吧
--【拾壹】--:
xxl-job执行器支持集群调度啊
--【拾贰】--:
我知道支持集群,但是因为quartz依赖的是数据库,数据库本身就很慢,就会触发一个先查,一个后查,然后就变成两个正在查,最后就变成两个触发任务,这就是根本原因
--【拾叁】--:
产品已经自研了一套定时任务框架。但老系统上还是用的quartz,切过去成本太高,暂时不考虑换框架没办法
--【拾肆】--:
用redis分布式锁能解决问题。可quartz框架本身是支持集群模式的,不应该存在这种设计缺陷才对。目前也只是偶发出现这种情况,1个月会出现一两次这样。
--【拾伍】--:
终于看到一个本专业了,不容易,建议更换成xxljob 这个集群稳定一点,之前我们生产环境xxljob集群也有类似的问题供你参考一下,大概是调度的任务 无法返回成功状态,导致调度器以为没调度成功,又调度到了一个集群上。基本是网络问题,或者定时任务有问题,报错了,无法返回成功
--【拾陆】--:
35c4f49b854373a7028a982affb6f1f8962×406 31.8 KB
看到xxl-job的作者也反馈过这个问题
--【拾柒】--:
今夕是何年
--【拾捌】--:
容我问一下我的,稍后回复
--【拾玖】--:
我是测试环境怎么都复现不了,生产上确实就偶发。
生产上是2台应用服务器的集群,任务调度时会偶发出现2个节点同时执行某个任务(A服务器和B服务器上同一时间点各执行了一遍)。目前毫无思路 有没有懂quartz框架原理的佬看看可能是什么原因导致的,或者说有什么排查思路。
// quartz参数
Properties prop = new Properties();
prop.put("org.quartz.scheduler.instanceName", "MyScheduler");
prop.put("org.quartz.scheduler.instanceId", "AUTO");
// 线程池配置
prop.put("org.quartz.threadPool.class", "org.quartz.simpl.SimpleThreadPool");
prop.put("org.quartz.threadPool.threadCount", "20");
prop.put("org.quartz.threadPool.threadPriority", "5");
prop.put("org.quartz.jobStore.class", "org.springframework.scheduling.quartz.LocalDataSourceJobStore");
// 集群配置
prop.put("org.quartz.jobStore.isClustered", "true");
prop.put("org.quartz.jobStore.clusterCheckinInterval", "15000");
prop.put("org.quartz.jobStore.maxMisfiresToHandleAtATime", "1");
prop.put("org.quartz.jobStore.misfireThreshold", "12000");
prop.put("org.quartz.jobStore.tablePrefix", "QRTZ_");
factory.setQuartzProperties(prop);
factory.setSchedulerName("RedpScheduler");
factory.setStartupDelay(1);
factory.setApplicationContextSchedulerContextKey("applicationContextKey");
// 启动时更新己存在的 Job
factory.setOverwriteExistingJobs(true);
// 设置自动启动,默认为 true
factory.setAutoStartup(true);
网友解答:
--【壹】--:
xxljob多节点轮巡,串行任务一样有可能重复执行。
--【贰】--:
那么多车,蹬起问gpt-5.4啊
--【叁】--:
用xxljob
--【肆】--:
你用xxl-job再加docker部署你就明白了,xxl-job会找不到实例
--【伍】--:
那可能是我太久没碰已修复了这个问题吧,当时这个问题搞我连夜把xxl-job换掉,我就给拉黑了
--【陆】--:
我没遇到过这种现象。
它jobstore用db的时候,好像有个db级别的lock,具体的可以让AI帮忙分析一下。
--【柒】--:
quartx框架只适合单体应用使用,quartz的触发是读取fired表的数据,两个应用会同时触发。
方案一:
如果不想大变的情况下,建议是加redis 全局锁,这样可以做到不重复执行,改动最小,可能十分钟就搞完了。
方案二:
切elasticJob、xxl-job这类分布式调度中心,不过个人不推荐,缺点太多,只有一个定时任务全局不重复的优点,而且还不支持docker 多副本,那还不如就quartz+redis全局锁了。
--【捌】--:
蹬冒烟了已经hhh
--【玖】--:
k8s支持,docker也可以使用network支持的。xxl-job也支持自定义ip的
--【拾】--:
这种任务做幂等比较好吧
--【拾壹】--:
xxl-job执行器支持集群调度啊
--【拾贰】--:
我知道支持集群,但是因为quartz依赖的是数据库,数据库本身就很慢,就会触发一个先查,一个后查,然后就变成两个正在查,最后就变成两个触发任务,这就是根本原因
--【拾叁】--:
产品已经自研了一套定时任务框架。但老系统上还是用的quartz,切过去成本太高,暂时不考虑换框架没办法
--【拾肆】--:
用redis分布式锁能解决问题。可quartz框架本身是支持集群模式的,不应该存在这种设计缺陷才对。目前也只是偶发出现这种情况,1个月会出现一两次这样。
--【拾伍】--:
终于看到一个本专业了,不容易,建议更换成xxljob 这个集群稳定一点,之前我们生产环境xxljob集群也有类似的问题供你参考一下,大概是调度的任务 无法返回成功状态,导致调度器以为没调度成功,又调度到了一个集群上。基本是网络问题,或者定时任务有问题,报错了,无法返回成功
--【拾陆】--:
35c4f49b854373a7028a982affb6f1f8962×406 31.8 KB
看到xxl-job的作者也反馈过这个问题
--【拾柒】--:
今夕是何年
--【拾捌】--:
容我问一下我的,稍后回复
--【拾玖】--:
我是测试环境怎么都复现不了,生产上确实就偶发。

