1. 介紹
Quartz是OpenSymphony開源組織在Job scheduling領域又一個開源的任務調度框架,是完全由java開發的一個開源的任務日程管理系統,“任務進度管理器”就是一個在預先確定(被納入日程)的時間到達時,負責執行(或者通知)其他軟件組件的系統。
Quartz用一個小Java庫發佈文件(.jar文件),這個庫文件包含了所有Quartz核心功能。這些功能的主要接口(API)是Scheduler接口。它提供了簡單的操作,例如:將任務納入日程或者從日程中取消,開始/停止/暫停日程進度。
官網:http://www.quartz-scheduler.org/
2.特點
強大的調度功能,spring默認的任務調度框架。
靈活的應用方式
分佈式和集羣能力
3.用到的主要設計模式
Builder模式 組件模式
Factory模式 鏈式寫法
4.體系結構:
1.三個核心概念:
調度器 任務 觸發器
2.體系結構:
JobDetail
trigger
SimpleTrigger
CronTrigger
scheduler
start
stop
pause
resume
示例圖:
3.定時器種類
Quartz 中五種類型的 Trigger:SimpleTrigger,CronTirgger,DateIntervalTrigger,NthIncludedDayTrigger和Calendar 類( org.quartz.Calendar)。
最常用的:
SimpleTrigger:用來觸發只需執行一次或者在給定時間觸發並且重複N次且每次執行延遲一定時間的任務。
CronTrigger:按照日曆觸發,例如“每個週五”,每個月10日中午或者10:15分。
核心類
QuartzSchedulerThread :負責執行向QuartzScheduler註冊的觸發Trigger的工作的線程。
ThreadPool:Scheduler使用一個線程池作爲任務運行的基礎設施,任務通過共享線程池中的線程提供運行效率。
QuartzSchedulerResources:包含創建QuartzScheduler實例所需的所有資源(JobStore,ThreadPool等)。
SchedulerFactory :提供用於獲取調度程序實例的客戶端可用句柄的機制。
JobStore: 通過類實現的接口,這些類要爲org.quartz.core.QuartzScheduler的使用提供一個org.quartz.Job和org.quartz.Trigger存儲機制。作業和觸發器的存儲應該以其名稱和組的組合爲唯一性。
QuartzScheduler :這是Quartz的核心,它是org.quartz.Scheduler接口的間接實現,包含調度org.quartz.Jobs,註冊org.quartz.JobListener實例等的方法。
Scheduler :這是Quartz Scheduler的主要接口,代表一個獨立運行容器。調度程序維護JobDetails和觸發器的註冊表。 一旦註冊,調度程序負責執行作業,當他們的相關聯的觸發器觸發(當他們的預定時間到達時)。
Trigger :具有所有觸發器通用屬性的基本接口,描述了job執行的時間出發規則。 - 使用TriggerBuilder實例化實際觸發器。
JobDetail :傳遞給定作業實例的詳細信息屬性。 JobDetails將使用JobBuilder創建/定義。
Job:要由表示要執行的“作業”的類實現的接口。只有一個方法 void execute(jobExecutionContext context)
(jobExecutionContext 提供調度上下文各種信息,運行時數據保存在jobDataMap中)
Job有個子接口StatefulJob ,代表有狀態任務。
有狀態任務不可併發,前次任務沒有執行完,後面任務處於阻塞等到。
quartz入門
1.maven配置:
<!--quartz --> <dependency> <groupId>org.quartz-scheduler</groupId> <artifactId>quartz</artifactId> <version>2.1.7</version> </dependency>
2.編寫程序(實現每兩秒打印當前日期並且不停的打印)
- 實現job類(HelloJob.java)
package cn.qlq.quartz; import java.text.SimpleDateFormat; import java.util.Date; import org.quartz.Job; import org.quartz.JobDataMap; import org.quartz.JobExecutionContext; import org.quartz.JobExecutionException; import org.quartz.JobKey; import org.quartz.TriggerKey; public class HelloJob implements Job { public void execute(JobExecutionContext context) throws JobExecutionException { //打印當前的時間 Date date = new Date(); SimpleDateFormat sf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss"); System.out.println("current time is:"+sf.format(date)); System.out.println("hello world"); // 編寫具體的業務邏輯 } }
- HelloScheduler .java開啓任務調度
package cn.qlq.quartz; import static org.quartz.DateBuilder.newDate; import static org.quartz.JobBuilder.newJob; import static org.quartz.SimpleScheduleBuilder.simpleSchedule; import static org.quartz.TriggerBuilder.newTrigger; import java.util.GregorianCalendar; import org.quartz.JobDetail; import org.quartz.Scheduler; import org.quartz.SimpleScheduleBuilder; import org.quartz.Trigger; import org.quartz.TriggerBuilder; import org.quartz.impl.StdSchedulerFactory; import org.quartz.impl.calendar.AnnualCalendar; public class HelloScheduler { public static void main(String[] args) { try { //1. 創建一個JodDetail實例 將該實例與Hello job class綁定 (鏈式寫法XX.XX.XX) JobDetail jobDetail = newJob(HelloJob.class) // 定義Job類爲HelloQuartz類,這是真正的執行邏輯所在 .withIdentity("myJob","group1") // 定義name/group .build();//2. 定義一個Trigger,定義該job立即執行,並且每兩秒鐘執行一次,直到永遠 Trigger trigger = TriggerBuilder.newTrigger().withIdentity("myTrigger", "group1")// 定義名字和組 .startNow()//現在開始 .withSchedule(SimpleScheduleBuilder.simpleSchedule().withIntervalInSeconds(2).repeatForever()) .build(); //3. 創建scheduler Scheduler scheduler = StdSchedulerFactory.getDefaultScheduler(); //4. 將trigger和jobdetail加入這個調度 scheduler.scheduleJob(jobDetail, trigger); //5. 啓動scheduler scheduler.start(); } catch (Exception e) { e.printStackTrace(); } } }
注意:創建Scheduler的方式也可以改爲:
// 3. 創建scheduler SchedulerFactory sfact = new StdSchedulerFactory(); Scheduler scheduler = sfact.getScheduler();
淺談job&jobDetail
1.job簡介
Job:接口非常容易實現,只有一個execute方法,類似於Timer的run方法,在裏面編寫業務邏輯。
job實例在quartz中的聲明週期:
每次調度器在執行job時,它在執行execute方法前創建一個job實例
當調用完成之後,關聯的job對象實例會被釋放,釋放的實例被垃圾回收期你回收。
2. jobDetail簡介
JobDetail爲Job實例提供了許多設置屬性,以及JobDataMap成員變量屬性,它用來存儲特定job實例的狀態信息系,調度器需要藉助Jobdetail對象來添加Job實例。
重要屬性:
name:任務的名稱,必須屬性
group:任務所在的組,也是必須,默認值是DEFAULT,必須的
jobclass:任務的實現類,必須的
jobdatamap:用於傳遞傳參數
例如:將入門代碼改造獲取jobDetail的屬性
package cn.qlq.quartz; import static org.quartz.DateBuilder.newDate; import static org.quartz.JobBuilder.newJob; import static org.quartz.SimpleScheduleBuilder.simpleSchedule; import static org.quartz.TriggerBuilder.newTrigger; import java.util.GregorianCalendar; import org.quartz.JobDetail; import org.quartz.Scheduler; import org.quartz.SimpleScheduleBuilder; import org.quartz.Trigger; import org.quartz.TriggerBuilder; import org.quartz.impl.StdSchedulerFactory; import org.quartz.impl.calendar.AnnualCalendar; public class HelloScheduler { public static void main(String[] args) { try { //1. 創建一個JodDetail實例 將該實例與Hello job class綁定 (鏈式寫法) JobDetail jobDetail = newJob(HelloJob.class) // 定義Job類爲HelloQuartz類,這是真正的執行邏輯所在 .withIdentity("myJob") // 定義name,默認組是DEFAULT .build(); System.out.println("jobDetail's name:"+jobDetail.getKey().getName()); System.out.println("jobDetail's group:"+jobDetail.getKey().getGroup()); System.out.println("jobDetail's jobClass:"+jobDetail.getJobClass().getName()); //2. 定義一個Trigger,定義該job立即執行,並且每兩秒鐘執行一次,直到永遠 Trigger trigger = TriggerBuilder.newTrigger().withIdentity("myTrigger", "group1")// 定義名字和組 .startNow()//現在開始 .withSchedule(SimpleScheduleBuilder.simpleSchedule().withIntervalInSeconds(2).repeatForever()) .build(); //3. 創建scheduler Scheduler scheduler = StdSchedulerFactory.getDefaultScheduler(); //4. 將trigger和jobdetail加入這個調度 scheduler.scheduleJob(jobDetail, trigger); //5. 啓動scheduler scheduler.start(); } catch (Exception e) { e.printStackTrace(); } } }