1.Quartz是一个任务日程管理系统,一个在预先确定(被纳入日程)的时间到达时,负责执行(或者通知)其他软件组件的系统。
这些功能的主要接口是Scheduler接口。它提供了简单的操作,例如:将任务纳入日程或者从日程中取消,开始/停止/暂停日程进度。
2.Easy example
// First we must get a reference to a scheduler
SchedulerFactory sf = new StdSchedulerFactory();
Scheduler sched = sf.getScheduler();
// computer a time that is on the next round minute
Date runTime = TriggerUtils.getEvenMinuteDate(new Date());
// define the job and tie it to our HelloJob class
JobDetail job = new JobDetail("job1", "group1", HelloJob.class);
// Trigger the job to run on the next round minute
Trigger trigger = new SimpleTrigger("trigger1", "group1", runTime);
// Tell quartz to schedule the job using our trigger
sched.scheduleJob(job, trigger);
// Start up the scheduler
sched.start();
3.核心接口
Scheduler
Job
JobDetail
Trigger
JobDataMap
4.Scheduler:
1) A Scheduler maintains a registery of org.quartz.JobDetails and Triggers. Once registered, the Scheduler is responible for executing Jobs when their associated Triggers fire(when their scheduled time arrives).
void addJob(JobDetail jobDetail, boolean replace);
Date scheduleJob(JobDetail jobDetail, Trigger trigger);
Date rescheduleJob(String triggerName, String groupName, Trigger newTrigger) ;
2) 实例化:客户端与调度器交互是通过Scheduler接口的。这个Scheduler的实现,实际上是一个代理,对其中方法调用会传递到QuartzScheduler 实例上。QuartzScheduler处在框架根的位置,它是一个引擎驱动着整个框架。Quartz相当灵活和可配置,许多重要的功能由分离的组件和子框架实现,所以并非所有的功能都直接内建到QuartzScheduler。这就意味着用户可以用自己某个关键特征实现来替换原有默认实现。
3)启动关闭:一旦一个scheduler被实例化,它就可以被启动(start),并且处于驻留模式,直到被关闭(shutdown)。一旦scheduler被关闭(shutdown),则它不能再重新启动,除非重新实例化它。除非scheduler被启动并且不处于暂停状态,否则触发器不会被触发(任务也不能被执行)。
void start() throws SchedulerException;
void startDelayed(int seconds) throws SchedulerException;
void shutdown() throws SchedulerException;
5.Job:
作业是一个执行任务的简单java类。任务可以是任何java代码。只需你实现org.quartz.Job接口。当Quartz确定该是作业运行的时候,它将调用你的作业。Quartz提供了一个机制来建立具有不同粒度的、可重复的调度表,于是,你只需创建一个java类,这个类被调用而执行任务。
public interface Job {
void execute(JobExecutionContext context) throws JobExecutionException;
}
job的实例化由JobFactory控制,默认的JobFactory是SimpleJobFactory,缺省的JobFactory只是简单地对Job类调用newInstance()方法。
设置JobFactory的两种方式:
Scheduler.setJobFactory(factory)
配置quartz.properties的org.quartz.scheduler.jobFactory.class属性设置jobFactory的类型
6.JobDetail
JobDetail对象由Quartz客户端在Job被加入到scheduler时创建。它包含了Job的各种设置属性以及一个JobDataMap对象,这个对象被用来存储给定Job类实例的状态信息。Scheduler并不保存真正的Job Class,而是通过JobDetail来保存。
注意,我们给scheduler传入了一个JobDetail实例,而且这个JobDetail实例只是简单提供了类名来引用被执行的Job。每次scheduler执行这个任务时,它就创建这个类的新实例,然后调用该实例的execute()方法。Job不必担心线程安全性,因为同一时刻仅有一个线程去执行给定Job类的实例,甚至是并发执行同一Job也是如此。
7.JobDataMap
JobDataMap被用来保存一系列的(序列化的)对象,这些对象在Job执行时可以得到。JobDataMap是Java Map接口的一个实现,而且还增加了一些存储和读取主类型数据的便捷方法。
JobDetail.getJobDataMap().put("jobSays", "Hello World!");
JobExecutionContext.getJobDetail().getJobDataMap();
Trigger.getJobDataMap();
JobExecutionContext.getMergedJobDataMap();
任务在执行任务过程中,任何对Job DataMap所作的更改都将丢失而且任务下次执行时也无法看到。
StatefulJob(有状态任务)在任务的每次执行之后重新存储JobDataMap
JobDataMap 在每次执行之后重新持久化到 JobStore 中。
两个或多个有状态的JobDetail实例不能并发执行。
8.Trigger
Trigger对象被用来触发jobs的执行。如希望将任务纳入到进度,要实例化一个Trigger并且“调整”它的属性以满足你想要的进度安排。Triggers也有一个JobDataMap与之关联,从而可向触发器所触发的Job传递参数。Quartz打包了很多不同类型的Trigger,但最常用的Trigger类是SimpleTrigger和CronTrigger。
1)SimpleTrigger
SimpleTrigger用来触发只需执行一次或者在给定时间触发并且重复N次且每次执行延迟一定时间的任务。
例如想让触发器在2010年1月11日,上午11:23:54秒执行,然后每个隔10秒钟重复执行一次,并且这样重复5次。
public SimpleTrigger();
2)CronTrigger
如果需要像日历那样按日程来触发任务,则可使用CronTriggers。配置CronTrigger实例需要使用Cron表达式。
public CronTrigger()
3)TriggerUtils
TriggerUtils提供了许多便捷的方法简化了构造和配置trigger。
TriggerUtils提供了许多便捷的方法简化了构造和配置trigger。
public static Trigger makeSecondlyTrigger(int intervalInSeconds);
public static Trigger makeDailyTrigger(int hour, int minute);
public static Trigger makeWeeklyTrigger(int dayOfWeek, int hour, int minute);
public static Trigger makeMonthlyTrigger(int dayOfMonth, int hour, int minute);
public static Date getNextGivenMinuteDate(Date date, int minuteBase);
public static Date getEvenMinuteDate(Date date);
9.JobStore
Quartz提供两种基本作业存储类型。
第一种类型叫做RAMJobStore,它利用通常的内存来持久化调度程序信息。这种作业存储类型最容易配置、构造和运行。对许多应用来说,这种作业存储已经足够了。然而,因为调度程序信息是存储在被分配给JVM的内存里面,所以,当应用程序停止运行时,所有调度信息将被丢失。如果你需要在重新启动之间持久化调度信息,则将需要第二种类型的作业存储。
第二种类型的作业存储实际上提供两种不同的实现,但两种实现一般都称为JDBC作业存储。两种JDBC作业存储都需要JDBC驱动程序和后台数据库来持久化调度程序信息。这两种类型的不同在于你是否想要控制数据库事务或释放控制给应用服务器。
org.quartz.impl.jdbcjobstore.JobStoreTX
org.quartz.impl.jdbcjobstore.JobStoreCMT
10.TriggerListeners和JobListeners
监听器是在scheduler事件发生时能够执行动作的对象。可以看出,TriggerListeners接收与triggers相关的事件,而JobListeners则接收与Job相关的事件。
创建监听器很简单,创建一个实现TriggerListener或JobListener的接口。监听器然后在执行的时候注册到scheduler中,而且必须给定一个名字(或者,它们必须通过他们的getName()方法来介绍自己)。监听器可以被注册为“全局”的或者“非全局”。“全局”监听器接收所有triggers/jobs产生的事件,而“非全局”监听器只接受那些显式指定监听器名的triggers/jobs所产生的事件。
SchedulerListeners只接收与特定trigger 或job无关的Scheduler自身事件通知
11.SchedulerPlugin
Quartz提供了一个接口(org.quartz.spi.SchedulerPlugin)来插入附加的功能,它们在org.quartz.plugins包中找到。提供了诸如自动安排任务的日程,将任务和触发器事件的历史记入日志以及JVM虚拟机退出时确保干净地关闭scheduler等的功能。
可在quartz.properties的org.quartz.plugin属性中设置SchedulerPlugin
12.Quartz 和 Web 应用
可为QuartzInitializerServlet提供以下初始化参数:config-file,shutdown-on-unload,start-scheduler-on-load,start-delay-seconds,servlet-context-factory-key
示例:
<context-param>
<param-name>config-file</param-name>
<param-value>/some/path/my_quartz.properties</param-value>
</context-param>
<context-param>
<param-name>shutdown-on-unload</param-name>
<param-value>true</param-value>
</context-param>
<context-param>
<param-name>start-scheduler-on-load</param-name>
<param-value>true</param-value>
</context-param>
<listener>
<listener-class>
org.quartz.ee.servlet.QuartzInitializerListener
</listener-class>
</listener>