最新 spring 4.2.2 整合 Quartz Scheduler 2.2.2 任務調度樣本
本文將示範如何通過 Spring 使用 Quartz Scheduler 進行任務調度。Spring 為簡化 Quartz 的操作提供了相關支援類。
本文樣本使用的相關工具如下:
Spring 4.2.2 (發佈於 2015 年 10 月)
Quartz Scheduler 2.2.2 (發佈於 2015 年 10 月)
Maven 3
JDK 1.7
Eclipse Luna Service Release 1 (4.4.1)
步驟 1:建立 Maven 項目
這一步如果不知道怎麼做可以參考部落格《使用 Eclipse 的 Maven 2 外掛程式開發一個 JEE 項目》。
步驟 2:第三方依賴包的引入Maven pom.xml 編輯如下:
4.0.0 settle spring-quartz 1.0.0 jar spring-quartz http://maven.apache.orgUTF-84.2.2.RELEASE2.2.2 org.springframework spring-core ${springframework.version} org.springframework spring-context-support ${springframework.version} org.springframework spring-tx ${springframework.version} org.quartz-scheduler quartz ${quartz.version}
步驟 3:Quartz Scheduler 配置作業有兩種方式在 Spring 中使用 Quartz 來配置一個作業。
A:使用 MethodInvokingJobDetailFactoryBean
這種方式在你想要調用特定 bean 的一個方法的時候很是方便,比另一種方法要簡單的多。
以上作業配置簡單調用了 myBean 的 printMessage 方法,myBean 是一個簡單的 POJO。
B:使用 JobDetailFactoryBean
如果你需要更進階的設定,需要給作業傳遞資料,想更加靈活的話就使用這種方式。
jobClass 關聯到一個繼承自 QuartzJobBean 的類,它實現了 Quartz 作業介面。調用到這個作業的時候,它的 executeInternal 將被執行。
jobDataMap 允許我們給相關作業 bean 傳遞一些資料。在這個例子裡,我們將 ScheduledJob 將要使用到的 'anotherBean' 傳遞給它。
以下是引用 jobclass(FirstScheduledJob)的具體實現。
com.defonds.scheduler.jobs.FirstScheduledJob
/** * File Name:ScheduledJob.java * * Copyright Defonds Corporation 2015 * All Rights Reserved * */package com.defonds.scheduler.jobs;import org.quartz.JobExecutionContext;import org.quartz.JobExecutionException;import org.springframework.scheduling.quartz.QuartzJobBean;import com.defonds.scheduler.util.AnotherBean;/** * * Project Name:spring-quartz * Type Name:ScheduledJob * Type Description: * Author:Defonds * Create Date:2015-10-29 * @version * */public class FirstScheduledJob extends QuartzJobBean {private AnotherBean anotherBean;@Overrideprotected void executeInternal(JobExecutionContext arg0)throws JobExecutionException {System.out.println(I am FirstScheduledJob);this.anotherBean.printAnotherMessage();}public void setAnotherBean(AnotherBean anotherBean) {this.anotherBean = anotherBean;}}
步驟 4:配置 Quartz 調度時要使用到的觸發器觸發器用來定義調度器何時將會執行你的調度任務的那個時間。有兩種可能的觸發器類型:
A:簡單觸發器,使用 SimpleTriggerFactoryBean
你可以定義作業的啟動時間、觸發器之間的延遲時間以及 repeatInterval(頻率)。
B:計劃觸發器,使用 CronTriggerFactoryBean
這種類型更加靈活,允許你針對特定執行個體選擇計劃方案以及將來要執行的頻率。
步驟 5:配置建立定配置 Quartz 調度器的 SchedulerFactoryBeanSchedulerFactoryBean 將 jobDetails 和 triggers 整合在一起以配置 Quartz 調度器。
下面貼出我們樣本的完整的上下文檔案。
src/main/resources/quartz-context.xml:
步驟 6:建立本文用到的幾個簡單 POJO 任務 Bean
com.defonds.scheduler.jobs.MyBean:
/** * File Name:MyBean.java * * Copyright Defonds Corporation 2015 * All Rights Reserved * */package com.defonds.scheduler.jobs;import org.springframework.stereotype.Component;/** * * Project Name:spring-quartz * Type Name:MyBean * Type Description: * Author:Defonds * Create Date:2015-10-29 * @version * */@Component(myBean)public class MyBean { public void printMessage() { System.out.println(I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean); } }
com.defonds.scheduler.util.AnotherBean:
/** * File Name:AnotherBean.java * * Copyright Defonds Corporation 2015 * All Rights Reserved * */package com.defonds.scheduler.util;import org.springframework.stereotype.Component;/** * * Project Name:spring-quartz * Type Name:AnotherBean * Type Description: * Author:Defonds * Create Date:2015-10-29 * @version * */@Component(anotherBean)public class AnotherBean { public void printAnotherMessage(){ System.out.println(I am AnotherBean. I am called by Quartz jobBean using CronTriggerFactoryBean); } }
com.defonds.scheduler.jobs.SecondScheduledJob:
/** * File Name:SecondScheduledJob.java * * Copyright Defonds Corporation 2015 * All Rights Reserved * */package com.defonds.scheduler.jobs;import org.quartz.JobExecutionContext;import org.quartz.JobExecutionException;import org.springframework.scheduling.quartz.QuartzJobBean;/** * * Project Name:spring-quartz * Type Name:SecondScheduledJob * Type Description: * Author:Defonds * Create Date:2015-10-29 * @version * */public class SecondScheduledJob extends QuartzJobBean {@Overrideprotected void executeInternal(JobExecutionContext arg0)throws JobExecutionException {System.out.println(I am SecondScheduledJob);}}
為了示範多個執行計畫的一起調度,我們寫了兩個 JobDetailFactoryBean,於是就有了 SecondScheduledJob。
步驟 7:建立執行程式的 Main 類:
/** * File Name:AppMain.java * * Copyright Defonds Corporation 2015 * All Rights Reserved * */package com.defonds.scheduler;import org.springframework.context.support.AbstractApplicationContext;import org.springframework.context.support.ClassPathXmlApplicationContext;/** * * Project Name:spring-quartz * Type Name:AppMain * Type Description: * Author:Defonds * Create Date:2015-10-29 * @version * */public class AppMain {public static void main(String args[]){ AbstractApplicationContext context = new ClassPathXmlApplicationContext(quartz-context.xml); }}
這時整個項目目錄結構如所示:
執行這個 Main 類,輸出結果如下:
I am FirstScheduledJob
I am AnotherBean. I am called by Quartz jobBean using CronTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am FirstScheduledJob
I am AnotherBean. I am called by Quartz jobBean using CronTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am FirstScheduledJob
I am AnotherBean. I am called by Quartz jobBean using CronTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am FirstScheduledJob
I am AnotherBean. I am called by Quartz jobBean using CronTriggerFactoryBean
I am SecondScheduledJob
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am FirstScheduledJob
I am AnotherBean. I am called by Quartz jobBean using CronTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am FirstScheduledJob
I am AnotherBean. I am called by Quartz jobBean using CronTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
I am MyBean. I am called by MethodInvokingJobDetailFactoryBean using SimpleTriggerFactoryBean
可以看到,簡單觸發器調用的作業每隔兩秒執行一次,而計劃觸發器一的則是每隔五秒鐘執行一次,計劃觸發器二則是固定只執行了一次(晚上八點整,紅色字型部分)。
後記
大多數情況下都會使用 JobDetailFactoryBean 進行任務調度配置;每個 JobDetailFactoryBean 都有一個觸發器與之匹配。配置多個調度計劃,需要配置多個這種匹配對;由觸發器指向 JobDetailFactoryBean;