下面详细讲解如何使用Spring Boot集成Quartz并注入Spring管理的类。
准备工作
首先,我们需要引入相关依赖。在 pom.xml
中加入以下依赖:
<!-- Quartz -->
<dependency>
<groupId>org.quartz-scheduler</groupId>
<artifactId>quartz</artifactId>
</dependency>
<!-- Quartz-Scheduler integration with Spring -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
</dependency>
配置Quartz
在 Spring Boot 中,我们可以使用 @Configuration
注解来配置 Quartz,并使用 QuartzJobBean
接口实现我们的任务。
@Configuration
public class QuartzConfig {
/**
* 配置定时任务
*/
@Bean
public JobDetail sampleJobDetail() {
return JobBuilder.newJob(SampleJob.class).withIdentity("sampleJob")
.usingJobData("name", "world").storeDurably().build();
}
/**
* 配置触发器
*/
@Bean
public Trigger sampleJobTrigger() {
SimpleScheduleBuilder scheduleBuilder = SimpleScheduleBuilder.simpleSchedule()
.withIntervalInSeconds(10).repeatForever();
return TriggerBuilder.newTrigger().forJob(sampleJobDetail())
.withIdentity("sampleTrigger").withSchedule(scheduleBuilder).build();
}
/**
* 配置定时任务管理器
*/
@Bean
public SchedulerFactoryBean schedulerFactory(ApplicationContext applicationContext,
JobFactory jobFactory) throws IOException {
SchedulerFactoryBean factory = new SchedulerFactoryBean();
// 全局 Job 监听器
factory.setGlobalJobListeners(new SampleJobListener());
// 全局 Trigger 监听器
factory.setGlobalTriggerListeners(new SampleTriggerListener());
factory.setJobFactory(jobFactory);
// 配置 QuartzProperties
factory.setQuartzProperties(quartzProperties());
return factory;
}
/**
* 配置 QuartzProperties
* @throws IOException
*/
private Properties quartzProperties() throws IOException {
PropertiesFactoryBean propertiesFactoryBean = new PropertiesFactoryBean();
propertiesFactoryBean.setLocation(new ClassPathResource("/quartz.properties"));
propertiesFactoryBean.afterPropertiesSet();
return propertiesFactoryBean.getObject();
}
/**
* 配置任务工厂
*/
@Bean
public JobFactory jobFactory(ApplicationContext applicationContext) {
AutowiringSpringBeanJobFactory jobFactory = new AutowiringSpringBeanJobFactory();
jobFactory.setApplicationContext(applicationContext);
return jobFactory;
}
}
在上面的配置中,我们通过 JobDetail
定义了一个名为 sampleJob
的 Quartz 任务,并通过 name
声明了一个任务参数。接着,我们通过 Trigger
配置了任务触发器,每隔 10 秒钟触发一次。
最后,我们通过 SchedulerFactoryBean
配置了定时任务管理器,注入了一个自定义的 JobFactory
,它用于将任务对象注入到 Spring 容器中,并配置了一个全局的 Job 监听器和 Trigger 监听器。
在上述配置中,我们引用了一个 AutowiringSpringBeanJobFactory
类,这是一个用于将 Quartz 中的 Job 类注入到 Spring 容器中的类。我们需要自己实现这个类:
public class AutowiringSpringBeanJobFactory extends SpringBeanJobFactory implements
ApplicationContextAware {
private transient AutowireCapableBeanFactory beanFactory;
@Override
public void setApplicationContext(final ApplicationContext context) {
beanFactory = context.getAutowireCapableBeanFactory();
}
@Override
protected Object createJobInstance(final TriggerFiredBundle bundle) throws Exception {
final Object job = super.createJobInstance(bundle);
beanFactory.autowireBean(job);
return job;
}
}
编写任务类
在我们的任务类中,我们首先需要实现 Quartz 中的 Job
接口,并注入我们的 Spring Bean,实现任务逻辑。
public class SampleJob implements Job {
private static final Logger logger = LoggerFactory.getLogger(SampleJob.class);
@Autowired
private SampleService sampleService;
@Override
public void execute(JobExecutionContext context) throws JobExecutionException {
logger.info("Running SampleJob...");
logger.info("Hello " + context.getJobDetail().getJobDataMap().getString("name"));
sampleService.run();
}
}
在上面的任务类中,我们通过 @Autowired
注解将 SampleService
注入到了正在运行的任务中。
@Service
public class SampleService {
private static final Logger logger = LoggerFactory.getLogger(SampleService.class);
public void run() {
logger.info("Running SampleService...");
}
}
上面的代码演示了如何在 Quartz 任务中注入 Spring Bean,并通过 Spring 框架执行任务逻辑。
示例
接下来,我们演示如何使用上述配置和任务类,实现定时任务。
Servlet 容器部署
如果你是使用 Servlet 容器部署的 Spring Boot 应用,在 application.properties
中配置以下属性:
# 配置定时任务触发频率(此处配置的是 5 分钟触发一次)
spring.quartz.properties.org.quartz.jobStore.isClustered = false
spring.quartz.properties.org.quartz.jobStore.class = org.quartz.simpl.RAMJobStore
spring.quartz.properties.org.quartz.threadPool.threadCount=3
spring.quartz.properties.org.quartz.threadPool.threadPriority=5
spring.quartz.properties.org.quartz.jobStore.misfireThreshold=600000
spring.quartz.properties.org.quartz.jobStore.acquireTriggersWithinLock=true
spring.quartz.properties.org.quartz.jobStore.tablePrefix = QRTZ_
spring.quartz.properties.org.quartz.jobStore.driverDelegateClass = org.quartz.impl.jdbcjobstore.StdJDBCDelegate
spring.quartz.job-store-type=memory
spring.quartz.job-store-type='quartz'
spring.quartz.properties.org.quartz.scheduler.instanceName = MyScheduler
spring.quartz.properties.org.quartz.scheduler.instanceId = AUTO
spring.task.scheduling.pool.size=3
单独运行
如果你是使用单独运行的 Spring Boot 应用,程序启动后会执行定时任务,例如:
@SpringBootApplication
public class Application {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
@Bean
CommandLineRunner demoRunner(SchedulerFactoryBean schedulerFactory) {
return new CommandLineRunner() {
@Override
public void run(String... args) throws Exception {
Scheduler scheduler = schedulerFactory.getScheduler();
scheduler.scheduleJob(sampleJobDetail(), sampleJobTrigger());
scheduler.start();
}
};
}
}
在上面的代码中,我们通过 CommandLineRunner
将我们的任务注入到 Spring 容器中,并构建定时任务。
小结
通过本文,我们了解了如何使用 Spring Boot 集成 Quartz 并注入 Spring 管理的类,实现定时任务的自动配置。同时,我们也提供了在 Servlet 容器部署和单独运行中,如何使用该配置的两个示例。
本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:Spring Boot集成Quartz注入Spring管理的类的方法 - Python技术站