您现在的位置是:首页 >学无止境 >关于Spring中自带的@Schedule实现自动任务网站首页学无止境

关于Spring中自带的@Schedule实现自动任务

秋天code 2024-08-26 12:01:03
简介关于Spring中自带的@Schedule实现自动任务

SpringBoot中自带了一个能够实现定时任务的注解@Schedule
如果定时任务比较简单,则可以使用SpringBoot中自带的@Schedule,但是如果任务调度很复杂的话,就建议使用Quartz组件了。
说一下这个@Schedule注解怎么用?

基本使用

  1. 第一步:在一个方法上使用@Schedule,标注这个方法是一个自定义任务
    通过该注解的cron属性,指定任务的运行规则
@Slf4j  
@Component  
public class MyTimeJob {  
  
	@Scheduled(cron = "0/1 * * * * *")  
	public void distanceOffDuty() {  
		log.info("现在是{},{}",new Date(),"~~~马上就要下班了");  
	}
	
}

关于Cron表达式,可以自己学习,
写cron表达式是一件麻烦的事情,就像写正则表达式似的
建议使用工具来生成cron表达式
在线Cron表达式生成器

  1. 在配置类上通过@EnableScheduling开启定时任务配置,开启了此配置后,SpringBoot会自动扫描容器中带有@Schedule注解
    注意:将包含@Schedule标注的方法所在的类,设置为Component或Configuration,要让SpringBoot知道这个类
@SpringBootApplication  
@EnableScheduling  
public class TestQuartzApplication {  
  
	public static void main(String[] args) {  
		SpringApplication.run(TestQuartzApplication.class, args);  
	}  
}

接下来启动程序,就可以看到自定义任务执行了

多线程执行

默认情况下,我们所有自定义的任务是单线程的,多个任务之间排队执行。
例如,我们定义了两个任务:

@Slf4j  
@Component  
public class MyTimeJob {  
  
	@Scheduled(cron = "0/1 * * * * *")  
	public void distanceOffDuty() {  
		log.info("现在是{},{}",new Date(),"~~~马上就要下班了");  
	}  
  
	@Scheduled(cron = "0/10 * * * * *")  
	public void work(){  
		log.info("又工作(摸鱼)了10秒钟了");  
	}  
}

看控制台这两个任务的执行情况:

如果想要为每一个任务单独开一个线程,异步化操作,效率能提高,不会被阻塞。
此时需要自定义线程池,看操作!

自定义配置类

@Configuration  
@EnableScheduling  
public class ScheduledConfig implements SchedulingConfigurer {  
  
	/**  
	* 任务执行线程池大小  
	*/  
	private static final int TASK_POOL_SIZE = 50;  
	/**  
	* 自定义线程前缀  
	*/  
	private static final String TASK_THREAD_PREFIX = "scheduling-task-";  
	  
	@Override  
	public void configureTasks(ScheduledTaskRegistrar scheduledTaskRegistrar) {  
		// 创建任务线程池  
		ThreadPoolTaskScheduler taskPool = new ThreadPoolTaskScheduler();  
		// 设置线程池大小  
		taskPool.setPoolSize(TASK_POOL_SIZE);  
		// 线程前缀名  
		taskPool.setThreadNamePrefix(TASK_THREAD_PREFIX);  
		// 初始化  
		taskPool.initialize();  
		scheduledTaskRegistrar.setTaskScheduler(taskPool);  
	}  
}

看自定义任务的执行情况:

每次执行任务,都会在线程池中取一个线程来使用

风语者!平时喜欢研究各种技术,目前在从事后端开发工作,热爱生活、热爱工作。