Spring Scheduled fixedRate 无法正常工作 [英] Spring Scheduled fixedRate not working properly

查看:106
本文介绍了Spring Scheduled fixedRate 无法正常工作的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

正如标题所说,我正在尝试使用 Scheduled 注释的 fixedRate 参数,以便每秒调用一个函数.这是我正在使用的代码:

As the title says, I am trying to use the fixedRate paramater of the Scheduled annotation in order to invoke a function every second. Here is the code that I am using:

  //execute once every second
  @Scheduled(fixedRate = 1000)
  private void pullLiveDataFromExternalServer() throws InterruptedException {

    System.err.println("START THREAD " + Thread.currentThread().getId());
    Thread.sleep(5500L);
    System.err.println("END THREAD " + Thread.currentThread().getId());

  }

按照我的理解,函数应该在打印第一个END THREAD"之前打印START THREAD"五次.

The way I understand it, the function should print "START THREAD" five times before the first "END THREAD" is printed.

问题是函数先打印START THREAD",然后等了5.5秒,打印END THREAD",然后再去START THREAD"等等……貌似调度器在等待前面的执行在它开始新的执行之前完成,但对于 fixedRate 属性来说不应该是这种情况.

The problem is that the function first prints "START THREAD" and then waits 5.5 seconds, prints "END THREAD", and then goes "START THREAD" and so on... It looks like the scheduler waits for the previous execution to finish before it starts the new execution but that should not be the case for the fixedRate attribute.

我多读了一点,发现@Scheduled 注释的默认调度程序只有一个线程,所以我创建了一个配置,将池大小更改为 8.

I read into it a bit more and found out that the default scheduler for @Scheduled annotation has only one thread, so I created a configuration to change the pool size to 8.

@Component
public class SchedulingConfigurerConfiguration implements SchedulingConfigurer {
  @Override
  public void configureTasks(ScheduledTaskRegistrar taskRegistrar) {
    ThreadPoolTaskScheduler taskScheduler = new ThreadPoolTaskScheduler();
    taskScheduler.setPoolSize(8);
    taskScheduler.initialize();
    taskRegistrar.setTaskScheduler(taskScheduler);
  }
}

但是 fixedRate 属性的行为没有改变,调度程序在开始新的执行之前仍在等待上一次执行的结束.为什么会发生这种情况?

But the behaviour of the fixedRate attribute was no changed and the scheduler was still waiting for the end of the previous execution before starting a new one. Why is this happening ?

我使用的spring boot版本是v1.5.8.RELEASE.

The spring boot version that I am using is v1.5.8.RELEASE.

推荐答案

看起来调度器在开始新的执行之前等待上一个执行完成

It looks like the scheduler waits for the previous execution to finish before it starts the new execution

这是正确的,这是预期的行为.每个计划任务,无论 fixedRatefixedDelay 是什么,都不会并行运行.即使调用时间比配置的 fixedRate 长,也是如此.

This is correct and it is the intended behaviour. Each scheduled task, irrespective of fixedRate or fixedDelay, will never run in parallel. This is true even if the invocation takes longer than the configured fixedRate.

最终,固定速率调度会导致调用 ScheduledExecutorService.scheduleAtFixedRate.它的 javadoc 声明如下:

Ultimately, fixed rate scheduling results in a call to ScheduledExecutorService.scheduleAtFixedRate. Its javadoc states the following:

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

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

如果可以并行运行同一计划任务的多个调用,那么您问题中的示例将耗尽所有可用线程.每 1000 毫秒使用一个新线程,并且每 5500 毫秒重新可用一个线程.

If it was possible for multiple invocations of the same scheduled task to run in parallel, the example in your question would exhaust all of the available threads. A new thread would be used every 1000ms and a thread would only become available again every 5500ms.

这篇关于Spring Scheduled fixedRate 无法正常工作的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆