quartZ的使用

quartZ

注:本文章只是自己在学习中记的笔记(可能有点乱),只提供参考。如有错误请指出。

一.简介

Quartz是OpenSymphony开源组织在Job scheduling领域又一个开源项目,完全由Java开发,可以用来执行定时任务,类似于java.util.Timer。但是相较于Timer, Quartz增加了很多功能

  • 持久性作业 - 就是保持调度定时的状态;
  • 作业管理 - 对调度作业进行有效的管理;

官网:http://www.quartz-scheduler.org/

二.QuartZ设计模式

  • Builder模式
  • Factory模式
  • 组件模式
  • 链式编程

三.核心概念

  • 任务Job

    Job就是你想实现的任务类,每一个Job必须实现org.quartz.Job接口,且只需实现接口定义的方法execute()即可

    graph BT
      B(自定义的实现类)-.<font color=#ccc>实现</font>.->A(&ltInterface&gtorg.quartz.Job)
    
  • 触发器Trigger

    Trigger为你执行任务的触发器,触发器Trigger最基本的功能是指定Job的执行时间,执行间隔,运行次数等。

    Quartz 提供了四种类型的 Trigger,但其中两种是最为常用的,分别是:SimpleTrigger 和 CronTrigger

graph BT
    a1(SimpleTrigger) -.-> B(&ltInterface&gtTrigge)
    a2(CronTrigger) -.<font color=#ccc>实现</font>.-> B(&ltInterface&gtTrigge)
    a3(自定义的Trigger) -.-> B(&ltInterface&gtTrigge)
  • 调度器Scheduler

    Scheduler为任务调度器,它会将任务job和触发器Trigger整合起来,负责基于Trigger设定的时间来执行job

    graph TB
      a1(&ltInterface&gtScheduler) ==<font color=#ccc>调度</font>==> a2(Trigger)
      a1(&ltInterface&gtScheduler)  ==<font color=#ccc>调度</font>==> a3(JOB)
    
    

四.QuartZ几个常用的API

  • Schedule用于调度程序交互的主程序接口

    Schedule调度程序-任务执行计划表,只有安排进执行计划的任务job(通过scheduler.scheduleJob方法安排进执行计划),当它预先定义的执行时间到了的时候(任务触发Tigger),该任务才会执行

  • Job 我们预先定义的希望在未来时间能被调度程序执行的任务类,我们可以自己定义

  • JobDetail 使用JobDetail来定义任务的实例。JobDetail通过jobbuilder来创建的

  • JobDataMap 可以包含不限量(序列化)的对象,在job实例执行的时候,可以使用其中的数据。jobMap是Java map中的一个实现类,额外增加了一些便于存取基本类型的数据的方法

  • Tigger 触发器,Tigger对象是用来触发执行job的,当调度一个job时,我们实例一个触发器,然后调整他的属性来满足job的执行的条件,比如每3秒执行一次

  • jobBuilder 用于声明一个任务实例,也可以定义该任务的详情,比如任务名,组名,这个申明的实例将会作为一个实际执行的任务

  • TiggerBuilder 触发器创建器,用于创建tagger实例

  • jobListener,tiggerlistener,schedulelistener监听器。用于对组件的监听

五.QuartZ的使用

  1. 准备工作(创建项目,导入jar包)

            <!--定时调度任务-->
            <dependency>
                <groupId>org.quartz-scheduler</groupId>
                <artifactId>quartz</artifactId>
                <version>2.3.2</version>
            </dependency>
            <dependency>
                <groupId>org.quartz-scheduler</groupId>
                <artifactId>quartz-jobs</artifactId>
                <version>2.3.2</version>
            </dependency>
    
  2. 创建j我们要做定时任务的类(实现org.quartz.Job)

    import org.quartz.Job;
    import org.quartz.JobExecutionContext;
    import org.quartz.JobExecutionException;
    
    public class MyJob implements Job {
     
        
        public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException  {
            SimpleDateFormat format = new SimpleDateFormat("yy-MM-dd HH-mm-ss");
            String date = format.format(new Date());
            System.out.println(date);
        }
    }
    
  3. 创建Schedule,执行任务

    import org.quartz.*;
    import org.quartz.impl.StdSchedulerFactory;
    
    /**
     * @author shkstart
     * @create 2020-03-11 15:22
     */
    public class QuartzTest {
        public static void main(String[] args) throws Exception {
            //创建调度器Scheduler方式一
             //Scheduler scheduler1 = StdSchedulerFactory.getDefaultScheduler();
            //创建调度器Scheduler方式二
            StdSchedulerFactory schedulerFactory = new StdSchedulerFactory();
            Scheduler scheduler = schedulerFactory.getScheduler();
    
           
    
            //创建JobDetail实例,并与quartZ类绑定(Job执行内容)
            JobDetail jobDetail = JobBuilder.newJob(MyJob.class).withIdentity("h1", "group1").usingJobData("count","11111").build();
    
            //触发器
            SimpleTrigger trigger = TriggerBuilder.newTrigger().withIdentity("t1", "group1")
                    .startNow()//立即执行
                    .withSchedule(SimpleScheduleBuilder.simpleSchedule()//simpleSchedule触发器
                            .withIntervalInSeconds(5)//几秒执行一次
                            .repeatForever()//一直执行
                    ).build();
    
            //执行,让调度器关联任务和触发器
            scheduler.scheduleJob(jobDetail, trigger);
            scheduler.start();
        }
    }
    
  4. 运行main方法,可以看到控制台每5秒打印一次时间

六.Quartz核心详解

  • job和JobDetail介绍

    • job:工作任务调用的接口,任务类需要实现该类,重写该类的execute()方法。

      public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException     {
          //业务代码
          //jobExecutionContext可以获取JobDataMap里传入的数据
      }
      
    • JobDetail:绑定指定的Job,每次Scheduler调度执行一个Job的时候,首先会拿到对应的Job,然后创建该Job实例,再去执行Job中的execute()的内容,任务执行结束后,关联的Job对象实例会被释放,且会被JVM GC清除。重要属性有name,group,jobClass,jobDataMap

      JobDetail jobDetail = JobBuilder.newJob(MyJob.class)//传入自定义实现Job的任务类
          .withIdentity("h1","group1")//定义name,group
          .usingJobData("count","11111")//JobDataMap实现了JDK的Map接口,可以以Key-Value的形式存储数据。
          .build();
      
  • JobExecutionContext:中包含了Quartz运行时的环境以及Job本身的详细数据信息。
    当Schedule调度执行一个Job的时候,就会将JobExecutionContext传递给该Job的execute()中,Job就可以通过JobExecutionContext对象获取信息。

    public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException {
            JobKey jobKey = jobExecutionContext.getJobDetail().getKey();
            System.out.println(jobKey.getName()+"-----"+jobKey.getGroup());//获取到jobDetail里定义的name和group
        JobDataMap jobDataMap = jobExecutionContext.getJobDetail().getJobDataMap();//拿到jobDataMap里传入的jobDataMap数据。就是这一句 .usingJobData("count","11111")。
            String count = jobDataMap.getString("count");//根据key获取value值
            System.out.println(count);
        //可以拿到很多数据,可以拿到jobDetail,相反也可以拿到tigger里的数据。还可以拿到其他比如任务名称等数据...
        }
    
    打印数据为:
    h1-----group1
    11111
    
  • Trigger、SimpleTrigger、CronTrigger

    • Trigger:rigger是Quartz的触发器,会去通知Scheduler何时去执行对应Job。

    • SimpleTrigger:SimpleTrigger可以实现在一个指定时间段内执行一次作业任务或一个时间段内多次执行作业任务。
      下面的程序就实现了程序运行5s后开始执行Job,执行Job 5s后结束执行:

    • CronTrigger:CronTrigger功能非常强大,是基于日历的作业调度,而SimpleTrigger是精准指定间隔,所以相比SimpleTrigger,CroTrigger更加常用。CroTrigger是基于Cron表达式的,先了解下Cron表达式:
      由7个子表达式组成字符串的,格式如下:

      [秒] [分] [小时] [日] [月] [周] [年]

      如果不知道什么写,可通过在线生成Cron表达式的工具:http://cron.qqe2.com/ 来生成自己想要的表达式。

      //写法跟SimpleTrigger一样,就是withSchedule传入的触发器不一样和返回值不一样。
      CronTrigger cronTrigger = TriggerBuilder.newTrigger().withIdentity("trigger1", "triggerGroup1")
                      .usingJobData("trigger1", "这是jobDetail1的trigger")
                      .startNow()//立即生效
                      //.startAt(startDate)
                      .endAt(endDate)
                      .withSchedule(CronScheduleBuilder.cronSchedule("* 30 10 ? * 1/5 2018"))//使用CronTrigger来进行定时。每周一到周五上午10:30执行定时任务
                      .build();
      
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 214,588评论 6 496
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,456评论 3 389
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 160,146评论 0 350
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,387评论 1 288
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,481评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,510评论 1 293
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,522评论 3 414
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,296评论 0 270
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,745评论 1 307
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,039评论 2 330
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,202评论 1 343
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,901评论 5 338
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,538评论 3 322
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,165评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,415评论 1 268
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,081评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,085评论 2 352

推荐阅读更多精彩内容