首页 > 代码库 > Spring Quartz实现任务调度

Spring Quartz实现任务调度

任务调度

在企业级应用中,经常会制定一些“计划任务”,即在某个时间点做某件事情 核心是以时间为关注点,即在一个特定的时间点,系统执行指定的一个操作 任务调度涉及多线程并发、线程池维护、运行时间规则解析、运行现场的保护以恢复等方面 Quartz框架是一个开源的企业级任务调度服务,已经被作为任务调度的良好解决方案.

技术分享

Quartz框架核心

Quartz对任务调度进行了高度抽象,提出了3个核心概念,并在org.quartz包中通过接口和类进行了描述

任务:就是执行的工作内容。Quartz提供Job接口来支持任务定义

触发器:定义触发Job执行的时间触发规则。Quartz提供Trigger类及其子类支持触发器功能

调度器:Quartz提供了Scheduler接口,将工作任务和触发器绑定,保证任务可以在正确的时间执行

运行环境

技术分享

任务调度

技术分享

技术分享

任务执行
技术分享

任务持久化

技术分享

事务

技术分享

集群

技术分享

监听器和插进

技术分享

Quartz案例

 

1.找到Quartz框架的jar包

技术分享

2.开始创建entity实体层定义任务的模板

package cn.entity;

public class Plan {
      //时间
    private String date;
    //任务
    private String task;
    
    public Plan() {
        super();
    }
    
    public Plan(String date, String task) {
        super();
        this.date = date;
        this.task = task;
    }

    @Override
    public String toString() {
        return "Plan [date=" + date + ", task=" + task + "]";
    }
    public String getDate() {
        return date;
    }
    public void setDate(String date) {
        this.date = date;
    }
    public String getTask() {
        return task;
    }
    public void setTask(String task) {
        this.task = task;
    }
    
}

 

 

3.定制一个泛型集合用户存储多个Plan对象,提供一个方法读取该泛型集合中的data

package cn.service;

import java.util.ArrayList;
import java.util.List;

import cn.entity.Plan;
/**
 * 提醒服务类
 * @author 
 *
 */
public class RemindService {
     //01.创建一个集合,并且方法返回值是一个集合类型
    public List<Plan> getPlansForToday(){
        List<Plan> list=new ArrayList<Plan>();
        Plan plan1=new Plan("2016年12月16日","2016最后一个月");
        Plan plan2=new Plan("2016年12月18日","Quartz");
        
        list.add(plan1);
        list.add(plan2);
        
        return list;
    }
    
    
    //02.用来打印集合中提醒内容的方法
    public void printMessage(){
        List<Plan> list = getPlansForToday();
        for (Plan plan : list) {
            //单个的plan
            System.out.println("计划的时间"+plan.getDate()+"\t计划内容"+plan.getTask());
        }
    }
}

4.提醒业务类

package cn.quartz;

import org.quartz.Job;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;

import cn.service.RemindService;
/**
 * 提醒业务
 * @author 
 *
 */
//让一个普通类变成计划
public class RemindJob implements Job {
    //植入service 对象
    private RemindService service=new RemindService();
    @Override
    public void execute(JobExecutionContext context) throws JobExecutionException {
        service.printMessage();
    }
    public RemindService getService() {
        return service;
    }
    public void setService(RemindService service) {
        this.service = service;
    }

    
}

Job接口中只有一个 execute()方法,在实现类中 实现该方法以执行具体任务。   

技术分享

技术分享

5.真正的任务对象和触发器对象

package cn.test;

import java.util.Date;

import org.quartz.CronScheduleBuilder;
import org.quartz.CronTrigger;
import org.quartz.DateBuilder;
import org.quartz.JobBuilder;
import org.quartz.JobDetail;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.SchedulerFactory;
import org.quartz.SimpleScheduleBuilder;
import org.quartz.Trigger;
import org.quartz.TriggerBuilder;
import org.quartz.TriggerKey;
import org.quartz.impl.StdSchedulerFactory;

import cn.quartz.RemindJob;

public class MyQuartzTest {
    
    public static void tool() throws SchedulerException, InterruptedException{
        //第一步构建Job
         JobDetail job = JobBuilder.newJob(RemindJob.class)//
                 .withIdentity("job1", "group1")//
                 .build();
         
         //第二步创建Trigger
         //第一种方式  控制不太好
        /* Date runTime = DateBuilder.evenMinuteDate(new Date(System.currentTimeMillis()));
         Trigger trigger = TriggerBuilder.newTrigger().withIdentity("trigger1", "group1")//
                 .startAt(runTime).build();*/
         
         //第二种方式  不太好
         /*Trigger trigger = TriggerBuilder.newTrigger() 
                 .withIdentity(TriggerKey.triggerKey("myTrigger", "myTriggerGroup"))
                 .withSchedule(SimpleScheduleBuilder.simpleSchedule()
                     .withIntervalInSeconds(2)
                     .repeatForever())
                 .startAt(new Date(System.currentTimeMillis()+2000))
                 .build();*/
         
                 
         
            //第三步绑定  JOb和Trigger
           // First we must get a reference to a scheduler
           //创建调度者工厂
            SchedulerFactory sf = new StdSchedulerFactory();
          //创建一个调度者
            Scheduler sched = sf.getScheduler();
          //注册并进行调度
            sched.scheduleJob(job, trigger);
          //启动调度
            sched.start();
            /*Thread.sleep(3000);
             * //关闭调度
            sched.shutdown();*/
    }

    
        
    public static void main(String[] args) throws SchedulerException, InterruptedException {
        tool();
        System.out.println("呵呵");
    }
}

 第一种方式:

技术分享

技术分享

第二种方式:

技术分享

 

6.使用CronTrigger

CronTrigger也是Trigger的子类

CronTrigger和SimpleTrigger的对比

技术分享

CronTrigger允许用户更精准地控制任务的运行日期和时间,而不仅仅是定义工作的频度

CronTrigger通过Cron表达式定义准确的运行时间点。创建CronTrigger的语法如下:

技术分享

7.Cron表达式

要使用CronTrigger,必须掌握Cron表达式

 

Cron表达式由6~7个由空格分隔的时间元素组成。第7个元素可选

 

技术分享

Cron表达式的每个字段,都可以显式地规定一个值(如49)、一个范围(如1-6)、一个列表(如1,3,5)或者一个通配符(如*)

 

8.Cron表达式有几个特殊的字符,说明如下

“ - ”:中划线,表示一个范围

“ , ”:使用逗号间隔的数据,表示一个列表

“ * ”:表示每一个值,它可以用于所有字段。例如:在小时字段表示每小时

“ ? ”:该字符仅用于“月份中的哪一天”字段和“星期几”字段,表示不指定值

“ / ”:通常表示为x/y,x为起始值,y表示值的增量。

“ L ”:表示最后一天,仅在日期和星期字段中使用

“ # ”:只能用于“星期几”字段,表示这个月的第几个周几。例如:“6#3”指这个月第三个周五

 

9.Cron表达式案例

技术分享

 

 技术分享

测试:

package cn.test;

import java.util.Date;

import org.quartz.CronScheduleBuilder;
import org.quartz.CronTrigger;
import org.quartz.DateBuilder;
import org.quartz.JobBuilder;
import org.quartz.JobDetail;
import org.quartz.Scheduler;
import org.quartz.SchedulerException;
import org.quartz.SchedulerFactory;
import org.quartz.SimpleScheduleBuilder;
import org.quartz.Trigger;
import org.quartz.TriggerBuilder;
import org.quartz.TriggerKey;
import org.quartz.impl.StdSchedulerFactory;

import cn.quartz.RemindJob;

public class MyQuartzTest {
    
    public static void tool() throws SchedulerException, InterruptedException{
        //第一步构建Job
         JobDetail job = JobBuilder.newJob(RemindJob.class)//
                 .withIdentity("job1", "group1")//
                 .build();
         
         //第二步创建Trigger
        /**
         * 2016年每月的第三个星期六上午10:18触发 0 18 10 ? * 6#3 2016
         */
        CronTrigger trigger=TriggerBuilder.newTrigger()//
                .withIdentity("myTrigger", "myTriggerGroup")//
                .withSchedule(CronScheduleBuilder.//
                        cronSchedule("0 18 10 ? * 6#3 2016")).build();
         
         
            //第三步绑定  JOb和Trigger
           // First we must get a reference to a scheduler
           //创建调度者工厂
            SchedulerFactory sf = new StdSchedulerFactory();
          //创建一个调度者
            Scheduler sched = sf.getScheduler();
          //注册并进行调度
            sched.scheduleJob(job, trigger);
          //启动调度
            sched.start();
              }

    
        
    public static void main(String[] args) throws SchedulerException, InterruptedException {
        tool();
        System.out.println("呵呵");
    }
}

技术分享

Spring Quartz实现任务调度