Reputation: 450
I have some functions in a Bean that I want to run every 5 seconds which the variable should be "generalized" not hard coded:
the working code looks as follows: (I have written in the relevant XML)
@Component
@EnableScheduling
public class CacheManager{
@Scheduled(initialDelay=0,fixedDelay=5000)
public void updateConfigurations() {
Some Code Here
}
@Scheduled(initialDelay=0,fixedDelay=5000)
public void updateMapping() {
Some Code Here
}
}
Both functions execute every 5 seconds.
Now when I want to move it into XML:
<task:scheduler id="ttScheduler" pool-size="1" />
<task:scheduled-tasks scheduler="ttScheduler">
<task:scheduled ref="cacheManager" method="updateConfigurations" fixed-delay="5000" initial-delay="0" />
<task:scheduled ref="cacheManager" method="updateMapping" fixed-delay="5000" initial-delay="0" />
</task:scheduled-tasks>
@Component
public class CacheManager{
public void updateConfigurations() {
log.info("update configurations");
Some Code
log.info("end update configurations");
}
public void updateMapping() {
Some Code Here
}
}
both functions executes with no delay. output:
20190127-17:24:48.254 INFO [ttScheduler-1] CacheManager[109] - end update configurations
20190127-17:24:48.255 INFO [ttScheduler-1] CacheManager[105] - update configurations
20190127-17:24:48.282 INFO [ttScheduler-1] CacheManager[109] - end update configurations
20190127-17:24:48.283 INFO [ttScheduler-1] CacheManager[105] - update configurations
20190127-17:24:48.311 INFO [ttScheduler-1] CacheManager[109] - end update configurations
20190127-17:24:48.312 INFO [ttScheduler-1] CacheManager[105] - update configurations
20190127-17:24:48.337 INFO [ttScheduler-1] CacheManager[109] - end update configurations
20190127-17:24:48.337 INFO [ttScheduler-1] CacheManager[105] - update configurations
20190127-17:24:48.362 INFO [ttScheduler-1] CacheManager[109] - end update configuration
...
...
Update: I have fixed the typo: to fixed-delay (generates the same output) the application is a web app that runs under tomcat 8.
I made small app (not web this time) as suggested by Dmitry Khamitov. It does work as a single executable app, BUT still as I wrote the same code just not works under web app environment.
The sample of the working test code:
public class SpringTestApplication {
private final AtomicInteger counter = new AtomicInteger();
public void updateConfigurations() throws InterruptedException {
if (counter.getAndIncrement() == 0) {
Date instant = new Date(System.currentTimeMillis());
SimpleDateFormat sdf = new SimpleDateFormat( "HH:mm:ss" );
String time = sdf.format( instant );
System.out.println( "Time: " + time );
Thread.sleep(5000);
}
Date instant = new Date(System.currentTimeMillis());
SimpleDateFormat sdf = new SimpleDateFormat( "HH:mm:ss" );
String time = sdf.format( instant );
System.out.println( "Time: " + time );
}
public static void main(String[] args) {
new ClassPathXmlApplicationContext("spring.xml");
}
}
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:task="http://www.springframework.org/schema/task"
xsi:schemaLocation="http://www.springframework.org/schema/task
http://www.springframework.org/schema/task/spring-task-4.2.xsd
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.1.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.1.xsd">
<bean id="SpringTestApplication" class="com.example.demo.SpringTestApplication" scope="singleton">
</bean>
<task:scheduler id="ttScheduler" pool-size="1"/>
<task:scheduled-tasks scheduler="ttScheduler">
<task:scheduled ref="SpringTestApplication" method="updateConfigurations" fixed-delay="5000" initial-delay="0"/>
</task:scheduled-tasks>
</beans>
Upvotes: 0
Views: 2729
Reputation: 3276
Probably this is because in XML you use fixed-rate, whereas in Java config you use fixed-delay. As the Official Spring Doc states:
...fixed delay indicating the number of milliseconds to wait after each task execution has completed. Another option is fixed-rate, indicating how often the method should be executed regardless of how long any previous execution takes...
So if Some Code in your example took much more time than your fixed-rate in some interval, then the consecutive tasks might have just queued up during that interval. Once that heavy execution is finished and if the next executions happen to be lightweight then you will see what you see in your logs until the ScheduledExecutorService's queue is drained. After that your lightweight tasks will start to run every fixed-rate ms.
Try searching the logs for the first executions to see the time taken by them. You can also comment out Some Code and restart your application in attempt of locating the root cause. Below is my simulated example which is expected to run every 1 sec but its first run takes 5 sec:
public class CacheManager {
private static final Logger LOG = LoggerFactory.getLogger(CacheManager.class);
private final AtomicInteger counter = new AtomicInteger();
public void updateConfigurations() throws InterruptedException {
LOG.info("update configurations");
if (counter.getAndIncrement() == 0) {
Thread.sleep(5000);
}
LOG.info("end update configurations");
}
public static void main(String[] args) {
new ClassPathXmlApplicationContext("spring.xml");
}
}
<beans ...>
<bean id="cacheManager" class="CacheManager"/>
<task:scheduler id="ttScheduler" pool-size="1"/>
<task:scheduled-tasks scheduler="ttScheduler">
<task:scheduled ref="cacheManager" method="updateConfigurations" fixed-rate="1000" initial-delay="0"/>
</task:scheduled-tasks>
</beans>
Output:
21:00:58.703 [ttScheduler-1] INFO CacheManager - update configurations
21:01:03.706 [ttScheduler-1] INFO CacheManager - end update configurations
21:01:03.706 [ttScheduler-1] INFO CacheManager - update configurations
21:01:03.707 [ttScheduler-1] INFO CacheManager - end update configurations
21:01:03.707 [ttScheduler-1] INFO CacheManager - update configurations
21:01:03.707 [ttScheduler-1] INFO CacheManager - end update configurations
21:01:03.707 [ttScheduler-1] INFO CacheManager - update configurations
21:01:03.707 [ttScheduler-1] INFO CacheManager - end update configurations
21:01:03.707 [ttScheduler-1] INFO CacheManager - update configurations
21:01:03.708 [ttScheduler-1] INFO CacheManager - end update configurations
21:01:03.708 [ttScheduler-1] INFO CacheManager - update configurations
21:01:03.708 [ttScheduler-1] INFO CacheManager - end update configurations
21:01:04.707 [ttScheduler-1] INFO CacheManager - update configurations
21:01:04.708 [ttScheduler-1] INFO CacheManager - end update configurations
21:01:05.706 [ttScheduler-1] INFO CacheManager - update configurations
21:01:05.706 [ttScheduler-1] INFO CacheManager - end update configurations
21:01:06.704 [ttScheduler-1] INFO CacheManager - update configurations
21:01:06.704 [ttScheduler-1] INFO CacheManager - end update configurations
Upvotes: 1