Spring定时任务框架(静态、动态SchedulingConfigurer)

静态定时任务

cron表达式

cron=“0/25 * * * * ?”
定时任务时间段内执行不完直接跳过下次任务,下例: 25秒,50秒,0秒执行, 注意0秒也执行。

固定间隔

fixedDelay = 1000 * 10
固定间隔执行, 定时任务时间段内执行不完, 下次定时任务在上次执行结束fixedDelay时间后开始执行, 下例: 假如11秒执行,23秒结束,下次33秒开始执行。

固定频率

fixedRate = 1000 * 10
固定频率, 如果任务执行时间超过频率大小, 下次任务直接在上次执行完就开始执行, 下例: 11秒开始,23秒结束, 下次23秒直接开始。

//@Scheduled(cron="0/25 * * * * ?")
//@Scheduled(fixedDelay = 1000 * 10)
@Scheduled(fixedRate = 1000 * 10)
public void test(){
    logger.info("开始执行定时任务================");
    try {
        Thread.sleep(12000);
    } catch (InterruptedException e) {
        e.printStackTrace();
    }
    logger.info("定时任务执行完成================");
}

动态定时任务

用途

可以动态改变调度方式等, 相对于静态定时任务, 更加灵活可配置。

实现

实现SchedulingConfigurer接口 org.springframework.scheduling.annotation.SchedulingConfigurer。
同样支持静态任务三种调度方式:
configureTasks()方法中进行配置, 改方法每次任务都会执行;
如果在上述方法中启动了多个定时任务scheduledTaskRegistrar.add多个, 会相互影响, 因为后台其实只起了一个线程, 解决如下: 添加线程池(验证TODO)
scheduledTaskRegistrar.setScheduler(Executors.newScheduledThreadPool(10))

/**
 * @desc : 动态定时任务绑定(根据convert.file.method两种配置)
 **/
public abstract class ScheduleConfig implements SchedulingConfigurer {

    Logger logger = LoggerFactory.getLogger(ScheduleConfig.class);

    @Autowired
    ConfigBean myConfig;

    @Override
    public void configureTasks(ScheduledTaskRegistrar scheduledTaskRegistrar) {
        //TODO 设定一个长度为10的定时任务线程池
        scheduledTaskRegistrar.setScheduler(Executors.newScheduledThreadPool(10));

        if ("1".equals(myConfig.getConvertFileMethod())) {
            scheduledTaskRegistrar.addTriggerTask(
                    () -> {
                        //定时任务具体逻辑
                        processTask();
                    },
                    //定时任务表达式
                    triggerContext -> {
                        CronTrigger cronTrigger = new CronTrigger(getCron());
                        return cronTrigger.nextExecutionTime(triggerContext);
                    }
            );
        }else{
            scheduledTaskRegistrar.addFixedRateTask(
                    () -> {
                        //定时任务具体逻辑
                        processTask();
                    },myConfig.getFixRate()
            );
        }
    }

    /**
     * 任务的处理函数, 本函数需要由派生类根据业务逻辑来实现
     */
    abstract void processTask();


    /**
     * 获取定时任务周期表达式
     * 可以将cron表达式存储在数据库中读取使用
     */
    private String getCron() {
        int mtime = Integer.parseInt(myConfig.getMtime());
        String cron =  "0/20 * * * * ?";
        if("1".equals(myConfig.getCronType())){
            if(mtime > 60){
                int i = mtime % 60;
                cron = "0 */"+ i + " * * * ?";
            }else{
                cron = "0/" + mtime + " * * * * ?";
            }
        }
        logger.debug("cron表达式为: {}", cron);
        return cron;
    }
}

注意

静态、动态都需要添加注解 @EnableScheduling 开启定时任务。

总结

Spring Schedule模块相较于 java.util.Timer、Quartz 实现都比较简单, 而且能够满足大多数需求; 简单、快速、高效、稳定的定时任务调度框架。

参考

https://blog.csdn.net/u013998466/article/details/90373811

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值