SpringBoot 之定时任务

文章目录

  • 序言
  • 一、静态:基于注解
  • 二、动态:基于接口
  • 三、多线程定时任务

序言

使用SpringBoot创建定时任务有三种方式

  1. 基于注解(@Scheduled)
  2. 基于接口(SchedulingConfigurer)可以从配置文件或数据库里面维护定时任务的cron , 优点:可以在不重启应用的条件下,使下一次定时任务动态生效,方便配置。
  3. 基于注解设定多线程定时任务

一、静态:基于注解

基于注解@Scheduled默认为单线程,开启多个任务时,任务的执行时机会受上一个任务执行时间的影响。

1、创建定时器
使用SpringBoot基于注解来创建定时任务非常简单,只需几行代码便可完成。 代码如下:

@Configuration      //1.主要用于标记配置类,兼备Component的效果。
@EnableScheduling   // 2.开启定时任务
public class SaticScheduleTask {
    //3.添加定时任务
    @Scheduled(cron = "0/5 * * * * ?")
    //或直接指定时间间隔,例如:5秒
    //@Scheduled(fixedRate=5000)
    private void configureTasks() {
        System.err.println("执行静态定时任务时间: " + LocalDateTime.now());
    }
}

Cron表达式参数分别表示:

秒(0~59) 例如0/5表示每5秒
分(0~59)
时(0~23)
日(0~31)的某天,需计算
月(0~11)
周几( 可填1-7 或 SUN/MON/TUE/WED/THU/FRI/SAT)
@Scheduled:除了支持灵活的参数表达式cron之外,还支持简单的延时操作,例如 fixedDelay ,fixedRate 填写相应的毫秒数即可。

// Cron表达式范例:

每隔5秒执行一次:*/5 * * * * ?

每隔1分钟执行一次:0 */1 * * * ?

每天23点执行一次:0 0 23 * * ?

每天凌晨1点执行一次:0 0 1 * * ?

每月1号凌晨1点执行一次:0 0 1 1 * ?

每月最后一天23点执行一次:0 0 23 L * ?

每周星期天凌晨1点实行一次:0 0 1 ? * L26分、29分、33分执行一次:0 26,29,33 * * * ?

每天的0点、13点、18点、21点都执行一次:0 0 0,13,18,21 * * ?

二、动态:基于接口

package com.dechnic.framework.config;/**
 * @className: DynamicScheduleTask
 * @author: houqd
 * @date: 2022/10/26
 **/

import com.dechnic.common.config.WChatConfig;
import com.dechnic.common.exception.ServiceException;
import com.dechnic.common.utils.StringUtils;
import com.dechnic.system.service.IScheduleService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.SchedulingConfigurer;
import org.springframework.scheduling.config.ScheduledTaskRegistrar;
import org.springframework.scheduling.support.CronTrigger;

/**
 * @description:
 * @author:houqd
 * @time: 2022/10/26 15:13
 */
@Configuration
@EnableScheduling
@ConditionalOnProperty(prefix = "wchat", name = "file_clean_enabled")
public class DynamicScheduleTask implements SchedulingConfigurer {

    @Autowired
    private WChatConfig wChatConfig;
    @Autowired
    private IScheduleService scheduleService;

    @Override
    public void configureTasks(ScheduledTaskRegistrar taskRegistrar) {
        taskRegistrar.addTriggerTask(
                () -> {
                    //System.out.println("=====动态执行定时任务:" + LocalDateTime.now().toLocalTime());
                    scheduleService.cleanUnusedFiles();

                }
                , triggerContext -> {
                    String cron = wChatConfig.getFileCleanCron();
                    // 合法性校验
                    if (StringUtils.isEmpty(cron)) {
                        throw new ServiceException("定时任务 cron 为空");
                    }
                    return new CronTrigger(cron).nextExecutionTime(triggerContext);
                });

    }
}

三、多线程定时任务

//@Component注解用于对那些比较中立的类进行注释;
//相对与在持久层、业务层和控制层分别采用 @Repository、@Service 和 @Controller 对分层中的类进行注释
@Component
@EnableScheduling   // 1.开启定时任务
@EnableAsync        // 2.开启多线程
public class MultithreadScheduleTask {

        @Async
        @Scheduled(fixedDelay = 1000)  //间隔1秒
        public void first() throws InterruptedException {
            System.out.println("第一个定时任务开始 : " + LocalDateTime.now().toLocalTime() + "\r\n线程 : " + Thread.currentThread().getName());
            System.out.println();
            Thread.sleep(1000 * 10);
        }

        @Async
        @Scheduled(fixedDelay = 2000)
        public void second() {
            System.out.println("第二个定时任务开始 : " + LocalDateTime.now().toLocalTime() + "\r\n线程 : " + Thread.currentThread().getName());
            System.out.println();
        }
    }

你可能感兴趣的:(SpringBoot,+VUE,系列,spring,boot,java,spring)