1. Job 和 JobDetail
Job
接口,只有一个execute()
方法。
源码:
package org.quartz;
public interface Job {
void execute(JobExecutionContext var1) throws JobExecutionException;
}
我们开发者只要实现此接口,实现execute方法即可。把我们想做的事情,在execute中执行即可。
/ 1 / Job
实例在quartz
中的生命周期
每次调度器调度job
时,在执行execute
方法前都会创建新的job
实例。
当调用完成后,关联的job实例会被释放,会GC回收。
/ 2 / JobDetail
属性
JobDeail
为job
实例提供了许多设置属性,存储job实例的状态信息。调度器需要借助jobdetail对象来添加job实例。
属性:
- name
- group
- jobClass
- jobDataMap
解析:
JobDetail jobDetail = JobBuilder
.newJob(PrintJob.class)
.withIdentity("myjob","group1")
.build();
System.out.println(jobDetail.getKey().getName());
System.out.println(jobDetail.getKey().getGroup());
System.out.println(jobDetail.getJobClass().getName());
说明:
每个JobDetail
和Trigger
都name
和group
组成的key
。
显示信息:
myjob
group1(group不写则默认DEFALT)
cn.whbing.pro.quartz.PrintJob
2. JobExecuteContext
1.当scheduler
调用一个job
,就会将jobExecuteContext
传递给job的execute
方法。
2.job
能够通过对象访问到quartz
运行时候的环境以及job
本身的明细数据。
3. jobDataMap
1.在进行任务调度时,jobDataMap
存储在jobExecuteContext
,非常方便获取。
2.jobDataMap
可以用来存储任何可以序列化
的数据对象,当job实例对象被执行时,这些参数对象会传递给它。
3.jobDataMap
实现了Map
接口。
4. 实验
目标:在scheduler
中传入jobDataMap
,在job
中通过jobExecuteContext
获取。
方法:在jobScheduler
或Trigger
上使用链式
方法usingDataMap()
绑定数据。
具体获取有两种方法:
方法一:在Map中获取
方法二:Job实现类中添加setter方法对应JobDataMap的键值(在初始化job实例时会自动调用setter方法)
/ 1 / 在JobDetail
和Trigger
实例上绑定JobDataMap
//1.创建JobDetail实例,并与printJob Class绑定
JobDetail jobDetail = JobBuilder
.newJob(PrintJob.class)
.withIdentity("myjob","group1")
.usingJobData("message","hello myjob1")
.usingJobData("FloatJobValue",3.14F)
.build();
//2.定义Trigger实例,定义该job立即执行,并且每隔两秒重复执行一次,直到永远
Trigger trigger = TriggerBuilder
.newTrigger()
.withIdentity("mytrigger","group1")
.usingJobData("message","hello mytrigger1")
.usingJobData("DoubleTriggerValue",5.21D)
.startNow()...
方法1:通过Map获取
/ 2(A) / 在Job
中通过context
获取JobDetail
和Trigger
本身信息,及JobDataMap
信息
public class PrintJob implements Job {
@Override
public void execute(JobExecutionContext context) throws JobExecutionException {
//编写具体的业务逻辑即可
//打印当前时间及hello
LocalDateTime timeNow = LocalDateTime.now();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy MM dd hh:mm:ss");
System.out.println("execute time:"+formatter.format(timeNow));
System.out.println("hello!");
//获取jobDetail和trigger信息
System.out.println("My job name and group:"
+context.getJobDetail().getKey().getName()
+","+context.getJobDetail().getKey().getGroup());
System.out.println("My trigger name and group:"
+context.getTrigger().getKey().getName()
+","+context.getTrigger().getKey().getGroup());
JobDataMap dataMap = context.getJobDetail().getJobDataMap();
JobDataMap tdataMap = context.getTrigger().getJobDataMap();
String message = dataMap.getString("message");
System.out.println(message);
//trigger和其他字段同理
}
}
结果:
execute time:2018 07 30 08:04:25
hello!
My job name and group:myjob,group1
My trigger name and group:mytrigger,group1
hello myjob1
/ 2(B) / 在Job
中通过context
获取getMergedJobDataMap
(需保证jobDetail和Trigger中无重复key)
//通过getMergedJobDataMap获取jobdetail和trigger合并后的信息
JobDataMap data = context.getMergedJobDataMap();
//当有相同的key时,先获取jobdetail中的,trigger中的key会覆盖jobdetail
System.out.println(data.getString("message"));
结果:
hello mytrigger1
方法二:Job实现类中添加setter方法对应JobDataMap的键值
(需保证jobDetail和Trigger中无重复key)
说明:类自动注入
(连注解都不需要),将通过反射直接将scheduler
中的jobdetail
或trigger
中的jobDataMap的key
,通过setter
赋予对应字段(名称要相同)
public class PrintJob implements Job {
private String message;
private Float FloatJobValue;
private Double DoubleTriggerValue;
getter and setter...
...
@Override
public void execute(JobExecutionContext context) throws JobExecutionException {
//直接通过setter后的字段访问
System.out.println("直接通过字段访问1:"+message);
System.out.println("直接通过字段访问2:"+FloatJobValue);
System.out.println("直接通过字段访问3:"+DoubleTriggerValue);
}
结果:(表明有相同字段时,这时以jobdetail为准)
直接通过字段访问1:hello myjob1
直接通过字段访问2:3.14
直接通过字段访问3:5.21