一尘不染

确保Spring Quartz作业执行不重叠

spring

我有一个Java程序,每20秒从Spring Qquartz执行一次。有时只需几秒钟即可执行,但是随着数据变大,我确信它会运行20秒或更长时间。

在一个实例仍在执行时,如何防止Quartz触发/触发作业?触发在数据库上执行相同操作的2个作业效果不佳。有没有办法可以进行某种同步?


阅读 592

收藏
2020-04-14

共2个答案

一尘不染

如果您需要做的是每20秒发射一次,那么Quartz就是严重的过度杀伤力。java.util.concurrent.ScheduledExecutorService对于这个工作,应该足够了。

的ScheduledExecutorService还提供了两个语义用于调度。“固定比率”将尝试每20秒运行一次作业,而不管重叠情况如何,而“固定延迟”将尝试在第一个作业结束到下一个作业开始之间间隔20秒。如果要避免重叠,则固定延迟是最安全的。

2020-04-14
一尘不染

Quartz 1

如果你更改类以实现StatefulJob而不是Job,那么Quartz将为你解决这一问题。从StatefulJob javadoc中:

有状态作业不允许同时执行,这意味着在execute(xx)方法完成之前发生的新触发器将被延迟。

StatefulJob扩展了Job且未添加任何新方法,因此,要获得所需的行为,只需要做以下更改:

public class YourJob implements org.quartz.Job {
    void execute(JobExecutionContext context) {/*implementation omitted*/}
}

To this:

public class YourJob implements org.quartz.StatefulJob {
    void execute(JobExecutionContext context) {/*implementation omitted*/}
}

Quartz 2

在Quartz 2.0版中,StatefulJob已弃用。现在建议改为使用注释,例如

@DisallowConcurrentExecution
public class YourJob implements org.quartz.Job {
    void execute(JobExecutionContext context) {/*implementation omitted*/}
}
2020-04-14