Quartz是OpenSymphony开源组织在Job scheduling领域又一个开源项目,它可以与J2EE与J2SE应用程序相结合也可以单独使用。Quartz可以用来创建简单或为运行十个,百个,甚至是好几万个Jobs这样复杂的日程序表。Jobs可以做成标准的Java组件或 EJBs。Quartz的最新版本为Quartz 1.5.0。
使用quartz的过程中,大部分的代码都大同小异,变化的是调度任务的corn表达式。下面是关于corn表达式的介绍:
Corn表达式介绍:
Cron 表达式包括以下 7 个字段:
• 秒
• 分
• 小时
• 月内日期
• 月
• 周内日期
• 年(可选字段)
特殊字符
Cron 触发器利用一系列特殊字符,如下所示:
• 反斜线(/)字符表示增量值。例如,在秒字段中“5/15”代表从第 5 秒开始,每 15 秒一次。
• 问号(?)字符和字母 L 字符只有在月内日期和周内日期字段中可用。问号表示这个字段不包含具体值。所以,如果指定月内日期,可以在周内日期字段中插入“?”,表示周内日期值无关紧要。字母 L 字符是 last 的缩写。放在月内日期字段中,表示安排在当月最后一天执行。在周内日期字段中,如果“L”单独存在,就等于“7”,否则代表当月内周内日期的最后一个实例。所以“0L”表示安排在当月的最后一个星期日执行。
• 在月内日期字段中的字母(W)字符把执行安排在最靠近指定值的工作日。把“1W”放在月内日期字段中,表示把执行安排在当月的第一个工作日内。
• 井号(#)字符为给定月份指定具体的工作日实例。把“MON#2”放在周内日期字段中,表示把任务安排在当月的第二个星期一。
• 星号(*)字符是通配字符,表示该字段可以接受任何可能的值。
字段 允许值 允许的特殊字符
秒 0-59 , - * /
分 0-59 , - * /
小时 0-23 , - * /
日期 1-31 , - * ? / L W C
月份 1-12 或者 JAN-DEC , - * /
星期 1-7 或者 SUN-SAT , - * ? / L C #
年(可选) 留空, 1970-2099 , - * /
表达式意义
- "0 0 12 * * ?" 每天中午12点触发
- "0 15 10 ? * *" 每天上午10:15触发
- "0 15 10 * * ?" 每天上午10:15触发
- "0 15 10 * * ? *" 每天上午10:15触发
- "0 15 10 * * ? 2005" 2005年的每天上午10:15触发
- "0 * 14 * * ?" 在每天下午2点到下午2:59期间的每1分钟触发
- "0 0/5 14 * * ?" 在每天下午2点到下午2:55期间的每5分钟触发
- "0 0/5 14,18 * * ?" 在每天下午2点到2:55期间和下午6点到6:55期间的每5分钟触发
- "0 0-5 14 * * ?" 在每天下午2点到下午2:05期间的每1分钟触发
- "0 10,44 14 ? 3 WED" 每年三月的星期三的下午2:10和2:44触发
- "0 15 10 ? * MON-FRI" 周一至周五的上午10:15触发
- "0 15 10 15 * ?" 每月15日上午10:15触发
- "0 15 10 L * ?" 每月最后一日的上午10:15触发
- "0 15 10 ? * 6L" 每月的最后一个星期五上午10:15触发
- "0 15 10 ? * 6L 2002-2005" 2002年至2005年的每月的最后一个星期五上午10:15触发
- "0 15 10 ? * 6#3" 每月的第三个星期五上午10:15触发
1、作业
实现 org.quartz.job 接口,实现接口方法 public void execute(JobExecutionContext context) throws JobExecutionException,在这个方法实现具体的作业任务。
execute 方法接受一个 JobExecutionContext 对象作为参数。这个对象提供了作业实例的运行时上下文。它提供了对调度器和触发器的访问,这两者协作来启动作业以及作业的 JobDetail 对象的执行。Quartz 通过把作业的状态放在 JobDetail 对象中并让 JobDetail 构造函数启动一个作业的实例,分离了作业的执行和作业周围的状态。JobDetail 对象储存作业的侦听器、群组、数据映射、描述以及作业的其他属性。
public class SummaryJob implements Job
{
private static Logger logger = Logger.getLogger(SummaryJob.class);
/**
* @see org.quartz.Job#execute(org.quartz.JobExecutionContext)
*/
public void execute(JobExecutionContext context) throws JobExecutionException
{
SummaryModel model = new SummaryModel();
try {
//这里是发送邮件功能
model.sendPostsSummary(model.listRecipients());
}
catch (Exception e) {
logger.warn(e);
}
}
}
2.生成调度器scheduler,定义触发器trigger以及jobDetail(这个不知道用什么专用名词)
/*
* Schedule the summaries to be sent to the users.
*/
public class SummaryScheduler
{
private static Scheduler scheduler;
private static Logger logger = Logger.getLogger(SummaryScheduler.class);
private static boolean isStarted;
/**
* Starts the summary Job. Conditions to start: Is not started yet and is enabled on the file
* SystemGlobasl.properties. The to enable it is "summary.enabled"
* (ConfigKeys.SUMMARY_IS_ENABLED).
*
* @throws SchedulerException
* @throws IOException
*/
public static void startJob() throws SchedulerException
{
//是否执行的标志位
boolean isEnabled = SystemGlobals.getBoolValue(ConfigKeys.SUMMARY_IS_ENABLED);
if (!isStarted && isEnabled) {
//所有quartz的配置信息文件
String filename = SystemGlobals.getValue(ConfigKeys.QUARTZ_CONFIG);
//从配置文件中读取调度参数
String cronExpression = SystemGlobals.getValue("org.quartz.context.summary.cron.expression");
scheduler = new StdSchedulerFactory(filename).getScheduler();
Trigger trigger = null;
try {
trigger = new CronTrigger(SummaryJob.class.getName(), "summaryJob", cronExpression);
logger.info("Starting quartz summary expression " + cronExpression);
scheduler.scheduleJob(new JobDetail(SummaryJob.class.getName(), "summaryJob", SummaryJob.class),
trigger);());//任务名,任务组,任务执行类
scheduler.start();
}
catch (ParseException e) {
e.printStackTrace();
}
}
isStarted = true;
}
}
参考文档:http://www.javaeye.com/topic/115666