Spring Scheduler
In today’s world we deal with high volume of transactions. Here many of the transactions need not run immediately. Running such transactions during non business hours/non peak hours help in saving some cost and also reduces the server load. In order to achieve this, spring scheduler will be helpful.
To enable scheduling in spring boot, annotate main class with @EnableScheduling annotation. If there is any need to enable or disable scheduling, then create a configuration class as below.
@Configuration
@EnableScheduling
@ConditionalOnProperty(name = "app.scheduler.enabled", havingValue = "true", matchIfMissing = true)
public class SchedulerConfig {
}
@ConditionalOnProperty allows us to register beans conditionally depending on the presence and value of the specific property mentioned. Here scheduling in the application is enabled/disabled with the value of the property app.scheduler.enabled. Here we have used 2 more attributes of ConditionalOnProperty annotation namely, havingValue and matchIfMissing. havingValue defines the value that the property should have in-order to add specific bean to spring container. matchIfMissing specifies if in case, the property(Eg: app.scheduler.enabled) is not available in the application, the condition should match or not.
Now let us see how to schedule a method in springboot.
@Scheduled(cron = "*/10 * * * * *")
public void scheduledMethod1(){
log.info("Scheduled method with cron value");
}
@Scheduled(fixedRateString = "5000")
public void scheduledMethod2(){
log.info("Scheduled method using fixedRateString");
}
@Scheduled(initialDelayString = "1000", fixedDelayString = "3000")
public void scheduledMethod3() throws InterruptedException {
log.info("Scheduled method using initialDelayString and fixedDelayString");
Thread.sleep(5000);
}
We need to annotate a method which needs to be scheduled with @Scheduled annotation. This annotation has different attributes to configure scheduler time namely cron, fixedRate, initialDelay & fixedDelay.
- cron — It requires a cron pattern which has six space separated fields.
<second> <minute> <hour> <day of month> <month> <day of week>
┌───────────── second (0-59)
│ ┌───────────── minute (0 - 59)
│ │ ┌───────────── hour (0 - 23)
│ │ │ ┌───────────── day of the month (1 - 31)
│ │ │ │ ┌───────────── month (1 - 12) (or JAN-DEC)
│ │ │ │ │ ┌───────────── day of the week (0 - 7)
│ │ │ │ │ │ (0 or 7 is Sunday, or MON-SUN)
│ │ │ │ │ │
* * * * * *
- /10 * * * * * — schedules the method to run every 10 seconds.
- It also supports some macros like @hourly, @midnight, etc.
Refer this spring cron documentation to understand the cron pattern further.
2. fixedRate — This runs the scheduled method periodically as per the value specified. It does not wait for the completion of the previous invoke. By default, value specified is considered in milliseconds. So the value is 5000, then the method is run every 5000ms or 5 seconds. Also, the method runs at the application start as well. To avoid this initial run, we can use initialDelay.
3. fixedDelay — This runs the scheduled method with a fixed delay between 2 executions. In the above example, there is a initial delay of 1000ms. Then the method gets executed. As there is a sleep method invoked with the thread sleeping for 5 seconds, next iteration of the method will run only after the completion of the previous execution + fixed delay which is 3000ms. So, method executes after 8 seconds(5000ms + 3000ms) in our example.
By default, the scheduler will run with a default thread pool containing a single thread. This might be a problem if you have multiple methods annotated with @scheduled in your application. In such cases, we have to specify pool-size attribute in the application.
spring.task.scheduling.pool.size=5
Now we have learnt how to write spring scheduler application in springboot. That's it for this article. If you liked it, please applaud this story which encourages me to write more such stories in future.
:) Keep smiling and keep learning.