Java 如何防止 Spring 中的时间表重叠?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/24033208/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-14 09:48:45  来源:igfitidea点击:

How to prevent overlapping schedules in Spring?

javaspringspring-scheduled

提问by membersound

@Scheduled(fixedDelay = 5000)
public void myJob() {
     Thread.sleep(12000);
}

How can I prevent this spring job from running if the previous routine is not yet finished?

如果上一个例程尚未完成,如何防止此春季作业运行?

采纳答案by Jose Luis Martin

With fixedDelay, the period is measured after the completion of job, so no worries.

使用fixedDelay,周期是在工作完成后测量的,所以不用担心。

回答by james turner

by default, spring uses a single-threaded Executor. so no two @Scheduled tasks will ever overlap. even two @Scheduled methods in completely unrelated classes will not overlap simply because there is only a single threadto execute all @Scheduled tasks.

默认情况下,spring 使用单线程 Executor。所以没有两个@Scheduled 任务会重叠。即使是完全不相关的类中的两个@Scheduled 方法也不会仅仅因为只有一个线程来执行所有@Scheduled 任务而重叠。

furthermore, even if you replace the default Executor with a thread pool based executor, those Executors will typically delay the execution of a task instance until the previously scheduled instance completes. this is true for fixedDelay, fixedInterval, and cronbased schedules. for example, this spring configuration will create a ScheduledThreadPoolExecutorthat uses a threadpool, but does not allow concurrent instances of the same schedule just as you desire:

此外,即使您将默认的 Executor 替换为基于线程池的 Executor,这些 Executor 通常也会延迟任务实例的执行,直到先前计划的实例完成。这适用于基于 fixedDelay、fixedInterval 和 cron的计划。例如,这个 spring 配置将创建一个使用线程池的ScheduledThreadPoolExecutor,但不允许如您所愿的相同调度的并发实例:

@Configuration
@EnableScheduling
...
public class MySpringJavaConfig {
    @Bean(destroyMethod = "shutdown")
    public Executor taskScheduler() {
        return Executors.newScheduledThreadPool(5);
    }
    ...
}

here is the javadoc for ScheduledThreadPoolExecutor::scheduleAtFixedRatewhich specifies:

这是ScheduledThreadPoolExecutor::scheduleAtFixedRatejavadoc,它指定:

If any execution of this task takes longer than its period, then subsequent executions may start late, but will not concurrently execute.

如果此任务的任何执行时间超过其周期,则后续执行可能会延迟开始,但不会并发执行。

note: this functionality does not hold true for @Async tasks. spring will create as many concurrent instances of those as needed (if there are sufficient threads in the pool).

注意:此功能不适用于@Async 任务。spring 将根据需要创建尽可能多的并发实例(如果池中有足够的线程)。