Quartz 是一个完全由 Java 编写的开源作业调度框架,不要让作业调度这个术语吓着你,其实不难。尽管 Quartz 框架整合了许多额外功能,但就我们使用来说,你会发现它易用得简直让人受不了!

简单来说,任务调度就是在指定时间做指定的事,之前说过在执行定时定频率作业时可以使用原生 JDK,Timer 和 TimerTask 。

但是假如我们有一些非常苛刻的要求该怎么办呢?比如,在每年 5 月的第二个星期日和每年 6 月的第三个星期日给我发一个邮件。

这种看似随机但还有有一点规律的定时任务该怎么实现呢?别急,Quartz 都能给你搞定!

我们执行任务必须的几个条件,一个是调度器,二是执行的任务,三是触发器(可以理解为设置闹钟)。连在一起就是我们使用调度器将任务和触发器绑定在一起执行,以达到在指定的时间点执行或循环执行任务。

虽说 Quartz 框架有十多个包,300 多个类,但是我们使用它还是比较容易的。

首先,创建一个任务,一样的套路我们只需要实现 Job 类,实现特定的方法即可,任务创建成功。

public class HelloJob implements Job{
@Override
public void execute(JobExecutionContext context) throws JobExecutionException {
TimeUtil.printCurrentTime();
System.out.println("Hello world!");
}
}

但是我们调度器绑定的不是 Job 的实现类 HelloJob,而是一个 JobDetail,为什么需要它呢,都写在脸上了,Job 详情嘛!

我们执行任务需要知道任务的名称啊,分组之类的,这样打出来的 log 也好分辨。这个 JobDetail 是和哪个 Job 绑定的呢?我们还要知道 Class 信息。在任务执行的时候可能还需要传参,这些都会封装在 JobDetail 中。

JobDetail 的创建就更是巧妙了,Quartz 为任务和触发器的创建提供了一种构建器风格的 API。具体的创建就是这样(一路点下去)

JobDetail jobDetail = JobBuilder.newJob(HelloJob.class).withIdentity("job1", "group1").build();

呃呃,构建器风格…… 我也不是很懂,感觉用起来很方便就对了,这样我们就创建了一个 JobDetail ,并设置了绑定的 Job (HelloJob),还为任务命名并分组,其实还可以继续绑定参数。这里没有演示而已。

同样的创建风格也用在触发器身上,想想看我们要设置一个闹钟,我们要设置开始执行的时间,执行的频率,执行的次数,这些一次性搞定,若是你英文还可以,看这些方法应该都明白了。

Trigger trigger = TriggerBuilder.newTrigger().withIdentity("trigger1", "group").startNow()
.withSchedule(SimpleScheduleBuilder.simpleSchedule().withIntervalInSeconds(2).repeatForever()).build();

哎,不是说好了不按套路出牌的嘛,我要的是每年 5 月的第二个星期日执行呀,可不是定时定频率啊,别急,后面说。

最后,再创建一个调度器,使用工厂模式创建,这里选择 StdSchedulerFactory ,因为这个工厂是可以加载配置文件的。在框架中会默认给我们提供一套配置,我们也可以在项目根目录下自行创建。

调度器的创建、绑定任务和触发器到执行,几行代码搞定。

// 定义一个 Schedule,用于绑定任务和触发器
SchedulerFactory sf = new StdSchedulerFactory();
Scheduler scheduler = sf.getScheduler();
scheduler.scheduleJob(jobDetail, trigger);
scheduler.start();

好了,这里为此,我们就已经搞定了最牛逼的定时任务的 demo 了。但是,你有没有发现,若是想实现定时定频率的执行任务,使用 Timer 就可以啊,为什么要劳烦大哥出场呢?

这里提一下 Timer 和 Quartz 的区别吧。

1、Timer 只能执行定时定频率的任务,而 Quartz 不是。

2、Timer 只有一个线程在执行,而 Quartz 有线程池,默认开启 10 个线程。

3、Timer 中出现异常,一切 GG,不能记录事故现场,而 Quartz 可以。

Quartz 想灵活的设置执行时间,依赖谁呢?调度器?NO,那肯定是触发器啊,其实 Trigger 有两个实现类,一个是 SimpleTrigger 就是功能比较简单的那个,默认实现的就是这个,所以上面我们返回就是 SimpleTrigger 的对象。

而另一个重磅级的实现类就是 CronTrigger ,它的触发机制是基于日历的,所以,你能想到的每一天,都能给你表示出来,触发器,重点就在这个时间的表示上面,我们使用 Cron 表达式来表示执行的时间。

举个例子吧 "* * * * * ? *" 表示每秒钟都执行,"0 15 10 ? 6L 2018-2020" 表示 2018-2020 年的每个月的最后一个星期五上午 10:15 执行。你会想,WTF ? 这是什么鬼,我不打算细说这个 Cron 表达式怎么写,因为不需要自己写!简单说,这就类似与正则表达式,而我们可以用在线生成工具来生成他们。

你只需要搜索 Cron 表达式在线生成器即可。

有了随心所欲的时间之后,我们就可以使用 CronTrigger 来定义触发器了,核心就在 Cron 表达式上面。

CronTrigger cronTrigger = (CronTrigger)TriggerBuilder.newTrigger().withIdentity("trigger1", "group").startNow()
.withSchedule(CronScheduleBuilder.cronSchedule("* * * * * ? *")).build();

至于多线程和持久化相关的类都在调度器中,不得不说 Quartz 封装的就是好呀,使用者根本感觉不到这些,在 StdSchedulerFactory 的内部,封装了核心调度器 QuartzScheduler ,用于持久化任务的 JobStore ,多线程相关的线程池、线程执行器。

但是我这种没有具体业务需求的人是不会深入研究的,对了,不要忘了 Quartz 的可配置的特性,简直就是逆天,没有业务场景应用的我也就想想得了。

以上也就是带你了解一下 Quartz,自己玩玩完全没问题。但是,你要是还不知道 Timer ,那就是你的问题了,可以回头看看这篇。

Java 中的定时任务 | 初级

最牛逼的任务调度工具 | Quartz的更多相关文章

  1. 任务调度工具Quartz入门笔记

    一,导包 1)官网下载:http://www.quartz-scheduler.org/downloads/ 2)Maven <dependency> <groupId>org ...

  2. vim牛逼的code工具: ctags+ cscope

    自己总结 在我的工作目录里的.vimrc中做了这样的配置:   set tags=tags;   set autochdir 在项目根目录里利用"sudo ctags -R *", ...

  3. C# 最牛逼的Utility工具类

    完整代码: using System; using System.Collections.Specialized; using System.IO; using System.Net; using S ...

  4. SNF开发平台WinForm-EasyQuery统计分析-效果-非常牛逼的报表查询工具

    无论是单轴曲线 .双轴曲线 .柱形图 .饼图 .雷达图 .仪表图.图表引擎全能为您轻松实现.您只需要 3 步操作(数据源准备,设计图表,挂接到您想要展示的位置)便可完成 BI 的设计. 无论是普通报表 ...

  5. 推荐 2 款超牛逼、炫酷、实用的Docker管理工具!

    Docker技术的火热程度,想必每个互联网IT技术人员都能时时感受的到,的确,近些年,国内对于Docker容器技术的应用需求越来越强烈!! 人均年薪80万以上,docker到底是什么?为什么这么火? ...

  6. 不推荐别的了,IDEA 自带的数据库工具就很牛逼!

    MySQL 等数据库客户端软件市面上非常多了,别的栈长就不介绍了, 其实 IntelliJ IDEA 自带的数据库工具就很牛逼,不信你继续往下看. 本文以 IntelliJ IDEA/ Mac 版本作 ...

  7. 为什么我会认为SAP是世界上最好用最牛逼的ERP系统,没有之一?

    为什么我认为SAP是世界上最好用最牛逼的ERP系统,没有之一?玩过QAD.Tiptop.用友等产品,深深觉得SAP是贵的有道理! 一套好的ERP系统,不仅能够最大程度承接适配企业的管理和业务流程,在技 ...

  8. 我喜欢ASP.NET的MVC因为它牛逼的9大理由(转载)

    我很早就关注ASP.NET的mvc的,因为最开始是学了Java的MVC,由于工作的原因一直在做.Net开发,最近的几个新项目我采用了MVC做了,我个一直都非常喜欢.Net的MVC.我们为什么使用MVC ...

  9. java定时任务调度工具

    一.什么是定时任务调度 基于给定的时间点,给定的时间间隔或者给定的时间执行次数自动执行的任务. 二.java中常用的定时任务调度工具: Timer Quartz 2.1两者区别: Timer源自jdk ...

随机推荐

  1. LeetCode 8 有效的括号

    给定一个只包括 '(',')','{','}','[',']' 的字符串,判断字符串是否有效. 有效字符串需满足: 左括号必须用相同类型的右括号闭合. 左括号必须以正确的顺序闭合. 注意空字符串可被认 ...

  2. nginx 重写URL尾部斜杠

    1. 在URL结尾添加斜杠 在虚拟主机中这么添加一条改写规则: rewrite ^(.*[^/])$ $1/ permanent;或者rewrite ^([/\w-_]*[^/])$ $1/ perm ...

  3. vue中assets文件夹与static文件夹的区别

    1.如果这些产品图片文件“万年不变”,放在 /static 目录里,(不需要使用require将这些图片作为模块来引用) var products = [{ img: '/static/img/pro ...

  4. [原]Android Fragment 入门介绍

    Fragment Fragment 产生,优点,用途,使用方法简介 1 Fragmeng简介 自从Android 3.0中引入fragments 的概念,根据词海的翻译可以译为:碎片.片段.其上的是为 ...

  5. AngularJS入门基础——过滤器

    在HTML中的模板绑定符号{{ }}内通过 | 符号来调用过滤器 {{ name | uppercase }}   以HTML的形式使用过滤器时,如果需要传递参数给过滤器,只要在过滤器名字后面加冒号即 ...

  6. Windows bat 学习(初级)

    http://steve-jansen.github.io/guides/windows-batch-scripting/part-1-getting-started.html 注释:REM 或 :: ...

  7. 20155225 2016-2017-2 《Java程序设计》第八周学习总结

    20155225 2016-2017-2 <Java程序设计>第八周学习总结 教材学习内容总结 通用API 日志API 国际化基础 规则表达式 JDK8增强功能 教材学习中的问题和解决过程 ...

  8. 2016-2017-2 20155309 南皓芯java第六周学习总结

    教材内容详解 这一次主要学习的是第十章与第十一章的内容.主要讲述了串流,字符处理和线程以及并行API. 输入输出 串流:Java中的数据有来源(source)和目的地(destination),衔接两 ...

  9. [BZOJ 1879][SDOI 2009]Bill的挑战 题解(状压DP)

    [BZOJ 1879][SDOI 2009]Bill的挑战 Description Solution 1.考虑状压的方式. 方案1:如果我们把每一个字符串压起来,用一个布尔数组表示与每一个字母的匹配关 ...

  10. vsftp服务器部署

    环境:CentOS 6.6 目标:个人虚机部署vsftp服务器,供测试使用. 说明:步骤已改写为脚本,直接添加用户与对应的密码列表,调用函数名即可 ########################## ...