定时任务一般会存在中大型企业级项目中,为了减少服务器、数据库的压力往往会采用时间段性的去完成某些业务逻辑。比较常见的就是金融服务系统推送回调,一般支付系统订单在没有收到成功的回调返回内容时会持续性的回调,这种回调一般都是定时任务来完成的。还有就是报表的生成,我们一般会在客户访问量过小的时候来完成这个操作,那往往都是在凌晨。这时我们也可以采用定时任务来完成逻辑。SpringBoot为我们内置了定时任务,我们只需要一个注解就可以开启定时为我们所用了。
本章目标
基于SpringBoot架构完成注解@Scheduled的定时任务配置。
构建项目
使用idea开发工具来构建SpringBoot项目,我们预先导入Web依赖,pom.xml如下图1所示:
![](http://upload-images.jianshu.io/upload_images/4461954-2a4c1df506333596.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
文章开头我说到了SpringBoot为我们内置了@Scheduled定时任务,下面我们就来配置下这个注解,找到入口程序Chapter26Application添加注解@EnableScheduling,如下图2所示:
![](http://upload-images.jianshu.io/upload_images/4461954-d663fdfc0470015e.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
可以看到上图2内我们添加注解后SpringBoot就已经认定了我们要使用定时任务来完成一些业务逻辑了,内部会对应原始配置定时任务添加对应的配置文件。
@Scheduled
@scheduled注解用来配置到方法上来完成对应的定时任务的配置,如执行时间,间隔时间,延迟时间等等,下面我们就来详细的看下对应的属性配置。
我们先来创建一个测试的定时任务实体,如下图3所示:
![](http://upload-images.jianshu.io/upload_images/4461954-80d19ffd5c5416bc.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
上图3内的注解@Compoment用来标明这是一个被Spring管理的Bean,这个就不用多做讲解了。下面我们来配置@Scheduled,来完成每小时的整10分钟输出内容,如下图4所示:
![](http://upload-images.jianshu.io/upload_images/4461954-7518234c7d838a27.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
cron属性
这是一个时间表达式,可以通过简单的配置就能完成各种时间的配置,我们通过CRON表达式几乎可以完成任意的时间搭配,它包含了六或七个域:
Seconds : 可出现", - * /"四个字符,有效范围为0-59的整数
Minutes : 可出现", - * /"四个字符,有效范围为0-59的整数
Hours : 可出现", - * /"四个字符,有效范围为0-23的整数
DayofMonth : 可出现", - * / ? L W C"八个字符,有效范围为0-31的整数
Month : 可出现", - * /"四个字符,有效范围为1-12的整数或JAN-DEc
DayofWeek : 可出现", - * / ? L C #"四个字符,有效范围为1-7的整数或SUN-SAT两个范围。1表示星期天,2表示星期一, 依次类推
Year : 可出现", - * /"四个字符,有效范围为1970-2099年
下面简单举几个例子:
"0 0 12 * * ?" 每天中午十二点触发
"0 15 10 ? * *" 每天早上10:15触发
"0 15 10 * * ?" 每天早上10:15触发
"0 15 10 * * ? *" 每天早上10:15触发
"0 15 10 * * ? 2005" 2005年的每天早上10:15触发
"0 * 14 * * ?" 每天从下午2点开始到2点59分每分钟一次触发
"0 0/5 14 * * ?" 每天从下午2点开始到2:55分结束每5分钟一次触发
"0 0/5 14,18 * * ?" 每天的下午2点至2:55和6点至6点55分两个时间段内每5分钟一次触发
"0 0-5 14 * * ?" 每天14:00至14:05每分钟一次触发
"0 10,44 14 ? 3 WED" 三月的每周三的14:10和14:44触发
"0 15 10 ? * MON-FRI" 每个周一、周二、周三、周四、周五的10:15触发
fixedRate属性
该属性的含义是上一个调用开始后再次调用的延时(不用等待上一次调用完成),这样就会存在重复执行的问题,所以不是建议使用,但数据量如果不大时在配置的间隔时间内可以执行完也是可以使用的。配置示例如下图5所示:
![](http://upload-images.jianshu.io/upload_images/4461954-9256bb8a1cfd664d.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
可以看到上图5内我配置的间隔时间是1秒,我在方法内使用了线程休眠,我们来测试下间隔输出的时间是多少,下面我们来启动项目,并且查看控制台输出内容。
项目成功启动后查看控制台内容如下图6所示:
![](http://upload-images.jianshu.io/upload_images/4461954-01a9b68b61822da4.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
我们可以看到每一次打印的间隔都是2秒钟,也就是我们配置线程休眠的时间,很好的证实了该方法并没有等到执行完再开始下一次执行。
fixedDelay属性
该属性的功效与上面的fixedRate则是相反的,配置了该属性后会等到方法执行完成后延迟配置的时间再次执行该方法。配置示例如下图7所示:
![](http://upload-images.jianshu.io/upload_images/4461954-0da18dadb0ec17d5.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
我们重启下项目后查看控制台输出(因为方便查看把之前配置的注解都已经注释掉),输出内容如下图8所示:
![](http://upload-images.jianshu.io/upload_images/4461954-81e1981571821bd9.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
可以看到上图8内的输出内容,时间间隔是4秒钟,我们在方法内仅仅使线程休眠了3秒钟,配置方法的延迟执行时间则是1秒钟,证明了确实是在方法执行完成后延迟配置时间后再次执行该方法。
initialDelay属性
该属性跟上面的fixedDelay、fixedRate有着密切的关系,为什么这么说呢?该属性的作用是第一次执行延迟时间,只是做延迟的设定,并不会控制其他逻辑,所以要配合fixedDelay或者fixedRate来使用,配置示例图下图9所示:
![](http://upload-images.jianshu.io/upload_images/4461954-e8280411ddd056d9.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
我们再次重启项目,查看控制台输出,这次我们等待了10秒钟后才看到了第一次输出内容,如下图10所示:
![](http://upload-images.jianshu.io/upload_images/4461954-79fc24bdc73dbee3.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/700)
可以看到上图10内红色部分,项目成功启动的时间为23:02:06而第一次输出的时间则是23:02:16,证明了我们配置的延迟时间生效了。第一次加载完成后之后就是每间隔2秒钟执行一边该方法。
注意上面所有属性的配置时间单位都是毫秒,可根据项目中实际情况进行时间单位换算
总结
上述内容就是本章的所有讲解内容,本章主要讲解了SpringBoot项目内的定时任务如果配置使用,上述的属性是我们实际项目中最常用到的,可根据项目实际情况进行选择配置。
本章源码已经上传到码云:
SpringBoot配套源码地址:https://gitee.com/hengboy/spring-boot-chapter
SpringCloud配套源码地址:https://gitee.com/hengboy/spring-cloud-chapter
SpringBoot相关系列文章请访问:目录:SpringBoot学习目录
QueryDSL相关系列文章请访问:QueryDSL通用查询框架学习目录
SpringDataJPA相关系列文章请访问:目录:SpringDataJPA学习目录
SpringBoot相关文章请访问:目录:SpringBoot学习目录,感谢阅读!
作者:恒宇少年
链接:https://www.jianshu.com/p/c7492aeb35a1
來源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。