diff --git a/ruoyi-quartz/src/main/java/com/ruoyi/quartz/service/impl/SysJobServiceImpl.java b/ruoyi-quartz/src/main/java/com/ruoyi/quartz/service/impl/SysJobServiceImpl.java index 77fdbb5..4e1a7a5 100644 --- a/ruoyi-quartz/src/main/java/com/ruoyi/quartz/service/impl/SysJobServiceImpl.java +++ b/ruoyi-quartz/src/main/java/com/ruoyi/quartz/service/impl/SysJobServiceImpl.java @@ -1,7 +1,10 @@ package com.ruoyi.quartz.service.impl; import java.util.List; +import java.util.concurrent.TimeUnit; import javax.annotation.PostConstruct; + +import com.ruoyi.common.core.redis.DistributedLockUtil; import org.quartz.JobDataMap; import org.quartz.JobKey; import org.quartz.Scheduler; @@ -30,6 +33,13 @@ public class SysJobServiceImpl implements ISysJobService @Autowired private SysJobMapper jobMapper; + @Autowired + private DistributedLockUtil distributedLockUtil; + + // 分布式锁key(唯一标识任务初始化操作) + private static final String JOB_INIT_LOCK_KEY = "sys_job:quartz:init:lock"; + // 获取锁的超时时间(集群争抢锁的超时) + private static final long LOCK_ACQUIRE_TIMEOUT_SECONDS = 10; /** * 项目启动时,初始化定时器 主要是防止手动修改数据库导致未同步到定时任务处理(注:不能手动修改数据库ID和任务组名,否则会导致脏数据) @@ -37,11 +47,27 @@ public class SysJobServiceImpl implements ISysJobService @PostConstruct public void init() throws SchedulerException, TaskException { - scheduler.clear(); - List jobList = jobMapper.selectJobAll(); - for (SysJob job : jobList) - { - ScheduleUtils.createScheduleJob(scheduler, job); + try (DistributedLockUtil.AutoReleaseLock autoLock = + distributedLockUtil.tryLock(JOB_INIT_LOCK_KEY, LOCK_ACQUIRE_TIMEOUT_SECONDS, TimeUnit.SECONDS)) { + if (autoLock == null || !autoLock.isLocked()) { + System.out.println("【定时任务初始化】其他实例已持有锁,当前实例跳过初始化"); + return; + } + + scheduler.clear(); + List jobList = jobMapper.selectJobAll(); + for (SysJob job : jobList) + { + //单个任务失败不影响其他任务 + try { + ScheduleUtils.createScheduleJob(scheduler, job); + } catch (Exception e) { + System.err.println("【定时任务初始化】单个任务失败:" + job.getJobId() + ",原因:" + e.getMessage()); + } + } + }catch (Exception e){ + System.err.println("【定时任务初始化】执行失败:" + e.getMessage()); + throw new RuntimeException("定时任务初始化失败", e); } }