正如 JobListener, org.quartz.TriggerListener 接口也包含一系列给 Scheduler 调用的方法。然而,与 JobListener 有所不同的是, TriggerListener 接口还有关于 Trigger 实例生命周期的方法。代码 5 列出了 TriggerListener 接口的方法。
代码 5. org.quartz.TriggerListener 接口的方法
public interface TriggerListener {
public String getName();
public void triggerFired(Trigger trigger,
JobExecutionContext context);
public boolean vetoJobExecution(Trigger trigger,
JobExecutidonContext context);
public void triggerMisfired(Trigger trigger);
public void triggerComplete(Trigger trigger,
JobExecutionContext context,
int triggerInstructionCode);
}
public interface TriggerListener {
public String getName();
public void triggerFired(Trigger trigger,
JobExecutionContext context);
public boolean vetoJobExecution(Trigger trigger,
JobExecutidonContext context);
public void triggerMisfired(Trigger trigger);
public void triggerComplete(Trigger trigger,
JobExecutionContext context,
int triggerInstructionCode);
}
- ·getName() 方法
和前面的 JobListener 一样,TriggerListner 接口的 getName() 返回一个字符串用以说明监听器的名称。对于非全局的 TriggerListener,在 addTriggerListener() 方法中给定的名称必须与监听器的 getName() 方法返回值相匹配。
·triggerFired() 方法
当与监听器相关联的 Trigger 被触发,Job 上的 execute() 方法将要被执行时,Scheduler 就调用这个方法。在全局 TriggerListener 情况下,这个方法为所有 Trigger 被调用。
·vetoJobExecution() 方法
在 Trigger 触发后,Job 将要被执行时由 Scheduler 调用这个方法。TriggerListener 给了一个选择去否决 Job 的执行。假如这个方法返回 true,这个 Job 将不会为此次 Trigger 触发而得到执行。
·triggerMisfired() 方法
Scheduler 调用这个方法是在 Trigger 错过触发时。如这个方法的 JavaDoc 所指出的,你应该关注此方法中持续时间长的逻辑:在出现许多错过触发的 Trigger 时,长逻辑会导致骨牌效应。你应当保持这上方法尽量的小。
·triggerComplete() 方法
Trigger 被触发并且完成了 Job 的执行时,Scheduler 调用这个方法。这不是说这个 Trigger 将不再触发了,而仅仅是当前 Trigger 的触发(并且紧接着的 Job 执行) 结束时。这个 Trigger 也许还要在将来触发多次的。
代码 6 展示了一个很简单的 TriggerListener 实现
代码 6. 一个简单的 TriggerListener 实现
package org.cavaness.quartzbook.chapter7;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.quartz.JobExecutionContext;
import org.quartz.Trigger;
import org.quartz.TriggerListener;
public class SimpleTriggerListener implements TriggerListener {
Log logger = LogFactory.getLog(SimpleTriggerListener.class);
private String name;
public SimpleTriggerListener(String name) {
this.name = name;
}
public String getName() {
return name;
}
public void triggerFired(Trigger trigger,
JobExecutionContext context) {
String triggerName = trigger.getName();
logger.info(triggerName + " was fired");
}
public boolean vetoJobExecution(Trigger trigger,
JobExecutionContext context) {
String triggerName = trigger.getName();
logger.info(triggerName + " was not vetoed");
return false;
}
public void triggerMisfired(Trigger trigger) {
String triggerName = trigger.getName();
logger.info(triggerName + " misfired");
}
public void triggerComplete(Trigger trigger,
JobExecutionContext context,
int triggerInstructionCode) {
String triggerName = trigger.getName();
logger.info(triggerName + " is complete");
}
}
package org.cavaness.quartzbook.chapter7;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.quartz.JobExecutionContext;
import org.quartz.Trigger;
import org.quartz.TriggerListener;
public class SimpleTriggerListener implements TriggerListener {
Log logger = LogFactory.getLog(SimpleTriggerListener.class);
private String name;
public SimpleTriggerListener(String name) {
this.name = name;
}
public String getName() {
return name;
}
public void triggerFired(Trigger trigger,
JobExecutionContext context) {
String triggerName = trigger.getName();
logger.info(triggerName + " was fired");
}
public boolean vetoJobExecution(Trigger trigger,
JobExecutionContext context) {
String triggerName = trigger.getName();
logger.info(triggerName + " was not vetoed");
return false;
}
public void triggerMisfired(Trigger trigger) {
String triggerName = trigger.getName();
logger.info(triggerName + " misfired");
}
public void triggerComplete(Trigger trigger,
JobExecutionContext context,
int triggerInstructionCode) {
String triggerName = trigger.getName();
logger.info(triggerName + " is complete");
}
}
正如代码 2 中的 JobListener 一样,代码 6 中的 TriggerListener 也是初步的。 它不过是在 Scheduler 调用它的方法时打印了一条日志信息。代码 7 中代码测试了这个简单的 TriggerListener。
代码 使用 SimpleTriggerListener 作为一个全局的 TriggerListener
package org.cavaness.quartzbook.chapter7;
import java.util.Date;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.cavaness.quartzbook.common.PrintInfoJob;
import org.quartz.JobDetail;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.Trigger;
import org.quartz.TriggerListener;
import org.quartz.TriggerUtils;
import org.quartz.impl.StdSchedulerFactory;
public class Listing_7_7 {
static Log logger = LogFactory.getLog(Listing_7_ class);
public static void main(String[] args) {
Listing_7_7 example = new Listing_7_7();
try {
example.startScheduler();
} catch (SchedulerException ex) {
logger.error(ex);
}
}
public void startScheduler() throws SchedulerException {
// Create an instance of the factory
Scheduler scheduler = null;
// Create the scheduler and JobDetail
scheduler = StdSchedulerFactory.getDefaultScheduler();
JobDetail jobDetail = new JobDetail("PrintInfoJob",
Scheduler.DEFAULT_GROUP, PrintInfoJob.class);
// Create and register the global job listener
TriggerListener triggerListener =
new SimpleTriggerListener("SimpleTriggerListener");
scheduler.addGlobalTriggerListener(triggerListener);
/*
* Set up a trigger to start firing now, with no end
* date/time, repeat forever and have 10 secs
* (10000 ms) between each firing.
*/
Trigger trigger = TriggerUtils.makeSecondlyTrigger(10);
trigger.setName("SimpleTrigger");
trigger.setStartTime(new Date());
// Register the JobDetail and Trigger
scheduler.scheduleJob(jobDetail, trigger);
// Start the scheduler
scheduler.start();
logger.info("Scheduler was started at " + new Date());
}
}
package org.cavaness.quartzbook.chapter7;
import java.util.Date;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.cavaness.quartzbook.common.PrintInfoJob;
import org.quartz.JobDetail;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.Trigger;
import org.quartz.TriggerListener;
import org.quartz.TriggerUtils;
import org.quartz.impl.StdSchedulerFactory;
public class Listing_7_7 {
static Log logger = LogFactory.getLog(Listing_7_ class);
public static void main(String[] args) {
Listing_7_7 example = new Listing_7_7();
try {
example.startScheduler();
} catch (SchedulerException ex) {
logger.error(ex);
}
}
public void startScheduler() throws SchedulerException {
// Create an instance of the factory
Scheduler scheduler = null;
// Create the scheduler and JobDetail
scheduler = StdSchedulerFactory.getDefaultScheduler();
JobDetail jobDetail = new JobDetail("PrintInfoJob",
Scheduler.DEFAULT_GROUP, PrintInfoJob.class);
// Create and register the global job listener
TriggerListener triggerListener =
new SimpleTriggerListener("SimpleTriggerListener");
scheduler.addGlobalTriggerListener(triggerListener);
/*
* Set up a trigger to start firing now, with no end
* date/time, repeat forever and have 10 secs
* (10000 ms) between each firing.
*/
Trigger trigger = TriggerUtils.makeSecondlyTrigger(10);
trigger.setName("SimpleTrigger");
trigger.setStartTime(new Date());
// Register the JobDetail and Trigger
scheduler.scheduleJob(jobDetail, trigger);
// Start the scheduler
scheduler.start();
logger.info("Scheduler was started at " + new Date());
}
}
代码 7 显示了如何注册 SimpleTriggerListener 为一个全局的 TriggerListener。它看起来与代码 3 中用来注册一个全局 JobListener 的代码完全相似。你只需要调用 addGloabelTriggerListener() 方法并传入这个 TriggerListener 实例。
·注册为非全局的 TriggerListener
要注册为一个非全局的 TriggerListener,你必须调用 addTriggerListener() 方法并传入这个 TriggerListener 实例。接着调用 Trigger 实例的 addTriggerListener() 方法并传入这个 TriggerListener 的名称。
在代码 8 中展示了这一过程。
代码 8. 使用一个非全局的 TriggerListener
package org.cavaness.quartzbook.chapter7;
import java.util.Date;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.cavaness.quartzbook.common.PrintInfoJob;
import org.quartz.JobDetail;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.Trigger;
import org.quartz.TriggerListener;
import org.quartz.TriggerUtils;
import org.quartz.impl.StdSchedulerFactory;
public class Listing_7_8 {
static Log logger = LogFactory.getLog(Listing_7_8.class);
public static void main(String[] args) {
Listing_7_8 example = new Listing_7_8();
try {
example.startScheduler();
} catch (SchedulerException ex) {
logger.error(ex);
}
}
public void startScheduler() throws SchedulerException {
// Create an instance of the factory
Scheduler scheduler = null;
// Create the scheduler and JobDetail
scheduler = StdSchedulerFactory.getDefaultScheduler();
JobDetail jobDetail = new JobDetail("PrintInfoJob",
Scheduler.DEFAULT_GROUP, PrintInfoJob.class);
// Create and register the nonglobal job listener
TriggerListener triggerListener =
new SimpleTriggerListener("SimpleTriggerListener");
scheduler.addTriggerListener( triggerListener );
/*
* Set up a trigger to start firing now, with no end
* date/time, repeat forever and have 10 secs
* (10000 ms) between each firing.
*/
Trigger trigger = TriggerUtils.makeSecondlyTrigger(10);
trigger.setName("SimpleTrigger");
trigger.setStartTime(new Date());
// Set the listener name for the trigger
trigger.addTriggerListener( triggerListener.getName() );
// Register the JobDetail and Trigger
scheduler.scheduleJob(jobDetail, trigger);
// Start the scheduler
scheduler.start();
logger.info("Scheduler was started at " + new Date());
}
}
package org.cavaness.quartzbook.chapter7;
import java.util.Date;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.cavaness.quartzbook.common.PrintInfoJob;
import org.quartz.JobDetail;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.Trigger;
import org.quartz.TriggerListener;
import org.quartz.TriggerUtils;
import org.quartz.impl.StdSchedulerFactory;
public class Listing_7_8 {
static Log logger = LogFactory.getLog(Listing_7_8.class);
public static void main(String[] args) {
Listing_7_8 example = new Listing_7_8();
try {
example.startScheduler();
} catch (SchedulerException ex) {
logger.error(ex);
}
}
public void startScheduler() throws SchedulerException {
// Create an instance of the factory
Scheduler scheduler = null;
// Create the scheduler and JobDetail
scheduler = StdSchedulerFactory.getDefaultScheduler();
JobDetail jobDetail = new JobDetail("PrintInfoJob",
Scheduler.DEFAULT_GROUP, PrintInfoJob.class);
// Create and register the nonglobal job listener
TriggerListener triggerListener =
new SimpleTriggerListener("SimpleTriggerListener");
scheduler.addTriggerListener( triggerListener );
/*
* Set up a trigger to start firing now, with no end
* date/time, repeat forever and have 10 secs
* (10000 ms) between each firing.
*/
Trigger trigger = TriggerUtils.makeSecondlyTrigger(10);
trigger.setName("SimpleTrigger");
trigger.setStartTime(new Date());
// Set the listener name for the trigger
trigger.addTriggerListener( triggerListener.getName() );
// Register the JobDetail and Trigger
scheduler.scheduleJob(jobDetail, trigger);
// Start the scheduler
scheduler.start();
logger.info("Scheduler was started at " + new Date());
}
}
针对于前面的非全局 JobListener 提到的相同的警告可以应用到这里来;你必须在把它设置给 Trigger 实例并存储了 Trigger 之前把 TriggerListener 加入到 Scheduler 中。