Our order service generally has an order to be paid, and this order to be paid is time limited. For example, Alibaba’s order is five days, and Taobao’s order is one day. Duoduo orders last one day, Meituan orders last 15 minutes...
In the fund system, how to update fund information in multiple storage partitions at the same time...
In general, in actual development Timers need to solve the problem of multiple timers running concurrently at the same time, as well as the problem of conflicts between timers.
The problem is not big. When it comes to concurrency, multi-threading is inseparable... Take a look I understand
We clearly see that the execution results are all scheduled-1
It can be determined from this that the default Springboot timer is single-threaded
But the problem arises. If after threads compete for resources, a certain thread takes a long time to complete, then other No matter what you do with the timers, you can only enter the waiting state. The longer the time, the more timers you have to wait for, which can easily cause an avalanche... In fact, you only need to add a configuration class and add annotations to solve it. Problem
Add annotation
The specific code is as follows:
import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.scheduling.annotation.Async; import org.springframework.scheduling.annotation.Scheduled; import org.springframework.stereotype.Component; import java.text.SimpleDateFormat; import java.util.Date; @Component public class SchedulerTaskController { private Logger logger= LoggerFactory.getLogger(SchedulerTaskController.class); private static final SimpleDateFormat dateFormat=new SimpleDateFormat("HH:mm:ss"); private int count=0; @Scheduled(cron="*/6 * * * * ?") @Async("threadPoolTaskExecutor") public void process(){ logger.info("英文:this is scheduler task runing "+(count++)); } @Scheduled(fixedRate = 6000) @Async("threadPoolTaskExecutor") public void currentTime(){ logger.info("中文:现在时间"+dateFormat.format(new Date())); } }
Configuration class
The specific code is as follows:
import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.scheduling.annotation.EnableAsync; import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor; import java.util.concurrent.ThreadPoolExecutor; /**使用多线程的时候,往往需要创建Thread类,或者实现Runnable接口,如果要使用到线程池,我们还需要来创建Executors, * 在使用spring中,已经给我们做了很好的支持。只要要@EnableAsync就可以使用多线程 * 通过spring给我们提供的ThreadPoolTaskExecutor就可以使用线程池。*/ //@Configuration 表示该类是一个配置类 @Configuration @EnableAsync //所有的定时任务都放在一个线程池中,定时任务启动时使用不同都线程。 public class TaskScheduleConfig { private static final int corePoolSize = 10; // 默认线程数 private static final int maxPoolSize = 100; // 最大线程数 private static final int keepAliveTime = 10; // 允许线程空闲时间(单位:默认为秒),十秒后就把线程关闭 private static final int queueCapacity = 200; // 缓冲队列数 private static final String threadNamePrefix = "it-is-threaddemo-"; // 线程池名前缀 @Bean("threadPoolTaskExecutor") // bean的名称,默认为首字母小写的方法名 public ThreadPoolTaskExecutor getDemoThread(){ ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor(); executor.setCorePoolSize(corePoolSize); executor.setMaxPoolSize(maxPoolSize); executor.setQueueCapacity(keepAliveTime); executor.setKeepAliveSeconds(queueCapacity); executor.setThreadNamePrefix(threadNamePrefix); //线程池拒绝任务的处理策略 executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy()); //初始化 executor.initialize(); return executor; } }
Then we can see clearly:
The above is the detailed content of How to resolve multiple timer conflicts in Spring Boot. For more information, please follow other related articles on the PHP Chinese website!