这是SSM框架整合的第4篇文章了,这两天基本都是每天整理2篇的节奏,真的是闲得蛋疼了我。不过这几篇文章都是自己动手实践过程中记录的,期间也遇到一些问题,参考了一些前辈的实现方式。在这里感谢前辈们的无私奉献,才换来现在我们的学习成本才能这么低,谢谢大家~
回归话题,今天想跟大家分享的是在ssm框架下实现任务调度的实现方式。因为在我们实际的项目中,很多时候会使用到一些定时器,比如邮件汇总、报表汇总这样的业务场景。那在ssm框架下有什么方式实现呢?本人常用的有2种,这里当做记录,和大家一起分享下。
spring task
spring task是spring 3.0版本开始,框架自带的任务调度开发工具。可以通过注解或配置的方式简单快速地将一个普通类转为定时任务,只要在spring-context.xml中启用spring task,简单的配置即可,如:
<!-- 启用spring task -->
<task:annotation-driven />
普通类:
public class DemoTask {
public void doSomething() {
//想要做的事情
}
}
@Component
public class DemoTask {
@Scheduled(cron="0 0/1 * * * ?") //cron表达式
public void doSomething() {
//想要做的事情
}
}
Quartz
Quartz是一个开源的框架,实现的功能也是任务调度。它采用工厂模式进行任务调度,主要有3个概念:JobDetail、Tigger、SchedulerFactory,个人简单的理解就是:什么事情(JobDetail)在什么时候(Tigger)有哪位大爷(SchedulerFactory)调配着做。当然,Qaurtz的功能十分强大,还能够配合mysql数据库实现集群化。这里我们就基于一个需求来实现SSM跟Quartz的整合。
需求
在我们的实际项目中经常会遇到这样的一种情况,我在业务代码里面设定了一个定时任务,单机跑起来没问题吧,都可以执行。但是蛋疼的是,我们很多时候项目是采用集群方式部署的,假设部署了A、B、C三台服务器,那业务代码肯定是一样的,这样定时任务就会各自独立跑一遍吧,假如这个定时任务操作了数据库,写数据进去,是不是有可能因为同样的流程并发着跑了导致有脏数据了。很简单的想法就是我就留一台机子跑定时任务嘛,其他两台去掉相同的业务代码不就可以了?当然可以,可是部署是不是就很麻烦了,还有一个就是哪天机子宕掉了,定时任务不就没有了。所以,基于上述的需要,我们需要的是,集群内服务器的代码肯定要一样的,然后我们的定时任务每次只能有一台机子跑,谁跑我们不关心嘛。这时我们就基于Quartz实现下,把它整合到SSM框架去。
ssm整合Quartz
首先,还是在pom.xml添加相关的依赖。
<!-- quartz -->
<dependency>
<groupId>org.quartz-scheduler</groupId>
<artifactId>quartz</artifactId>
<version>2.2.1</version>
</dependency>
<dependency>
<groupId>org.quartz-scheduler</groupId>
<artifactId>quartz-jobs</artifactId>
<version>2.2.1</version>
</dependency>
上面我们提到过实现集群需要mysql的配合,我们要讲下面的11张表结构导入我们的数据库中。
SET NAMES utf8;
SET FOREIGN_KEY_CHECKS = 0;
-- ----------------------------
-- Table structure for `QRTZ_BLOB_TRIGGERS`
-- ----------------------------
DROP TABLE IF EXISTS `QRTZ_BLOB_TRIGGERS`;
CREATE TABLE `QRTZ_BLOB_TRIGGERS` (
`SCHED_NAME` varchar(120) COLLATE utf8_bin NOT NULL,
`TRIGGER_NAME` varchar(200) COLLATE utf8_bin NOT NULL,
`TRIGGER_GROUP` varchar(200) COLLATE utf8_bin NOT NULL,
`BLOB_DATA` blob,
PRIMARY KEY (`SCHED_NAME`,`TRIGGER_NAME`,`TRIGGER_GROUP`),
CONSTRAINT `QRTZ_BLOB_TRIGGERS_ibfk_1` FOREIGN KEY (`SCHED_NAME`, `TRIGGER_NAME`, `TRIGGER_GROUP`) REFERENCES `QRTZ_TRIGGERS` (`SCHED_NAME`, `TRIGGER_NAME`, `TRIGGER_GROUP`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin ROW_FORMAT=COMPACT;
-- ----------------------------
-- Table structure for `QRTZ_CALENDARS`
-- ----------------------------
DROP TABLE IF EXISTS `QRTZ_CALENDARS`;
CREATE TABLE `QRTZ_CALENDARS` (
`SCHED_NAME` varchar(120) COLLATE utf8_bin NOT NULL,
`CALENDAR_NAME` varchar(200) COLLATE utf8_bin NOT NULL,
`CALENDAR` blob NOT NULL,
PRIMARY KEY (`SCHED_NAME`,`CALENDAR_NAME`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin ROW_FORMAT=COMPACT;
-- ----------------------------
-- Table structure for `QRTZ_CRON_TRIGGERS`
-- ----------------------------
DROP TABLE IF EXISTS `QRTZ_CRON_TRIGGERS`;
CREATE TABLE `QRTZ_CRON_TRIGGERS` (
`SCHED_NAME` varchar(120) COLLATE utf8_bin NOT NULL,
`TRIGGER_NAME` varchar(200) COLLATE utf8_bin NOT NULL,
`TRIGGER_GROUP` varchar(200) COLLATE utf8_bin NOT NULL,
`CRON_EXPRESSION` varchar(200) COLLATE utf8_bin NOT NULL,
`TIME_ZONE_ID` varchar(80) COLLATE utf8_bin DEFAULT NULL,
PRIMARY KEY (`SCHED_NAME`,`TRIGGER_NAME`,`TRIGGER_GROUP`),
CONSTRAINT `QRTZ_CRON_TRIGGERS_ibfk_1` FOREIGN KEY (`SCHED_NAME`, `TRIGGER_NAME`, `TRIGGER_GROUP`) REFERENCES `QRTZ_TRIGGERS` (`SCHED_NAME`, `TRIGGER_NAME`, `TRIGGER_GROUP`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin ROW_FORMAT=COMPACT;
-- ----------------------------