美文网首页
springboot+quartz实现多任务动态修改时间,亲测有

springboot+quartz实现多任务动态修改时间,亲测有

作者: hey_sometimes | 来源:发表于2018-10-09 10:16 被阅读0次

    网上已经有太多quartz定时任务的例子了,但是大多都不全,我这里整理了一下,希望对大家有所帮助。

    下面不多说,直接上代码。

    任务类,就是需要执行的定时任务。网上基本上都是一个任务一个类,但是我这边试了下,不同的任务可以放在同一个类下面,只要对应不同的方法就可以了。当然只是我这边试了可以,如果大家觉得有误的希望指正哈。

    
    import com.ophylink.ems.api.dao.ScheduleConfigRepository;
    import org.quartz.Job;
    import org.quartz.JobExecutionContext;
    import org.slf4j.Logger;
    import org.slf4j.LoggerFactory;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.scheduling.annotation.EnableScheduling;
    import org.springframework.stereotype.Component;
    
    import java.util.Date;
    
    @Component // 此注解必加
    @EnableScheduling // 此注解必加
    public class ScheduleTask implements Job {
        private static final Logger LOGGER = LoggerFactory.getLogger(ScheduleTask.class);
        @Autowired
        ScheduleConfigRepository repository;
    
        public void sayHello1() {
            LOGGER.info("这个是1" + repository.findOne("定时任务1").getName());
        }
    
        public void sayHello2() {
            LOGGER.info("这个是2");
        }
    
        @Override
        public void execute(JobExecutionContext jobExecutionContext) {
            Object jobName = jobExecutionContext.getJobDetail().getKey();
            System.err.println("这是" + jobName + "任务" + new Date());
        }
    }
    

    quartz配置类,这里不同的任务需要配置不同的jobDetail和不同的trigger,方便后面指定动态修改定时时间。

    
    import org.quartz.JobDetail;
    import org.quartz.Trigger;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.scheduling.quartz.MethodInvokingJobDetailFactoryBean;
    import org.springframework.scheduling.quartz.SchedulerFactoryBean;
    import org.springframework.scheduling.quartz.SimpleTriggerFactoryBean;
    
    @Configuration
    public class QuartzConfiguration {
        // 配置定时任务1
        @Bean(name = "firstJobDetail")
        public MethodInvokingJobDetailFactoryBean firstJobDetail(ScheduleTask firstJob) {
            MethodInvokingJobDetailFactoryBean jobDetail = new MethodInvokingJobDetailFactoryBean();
            // 是否并发执行
            jobDetail.setConcurrent(false);
            // 为需要执行的实体类对应的对象
            jobDetail.setTargetObject(firstJob);
            // 需要执行的方法
            jobDetail.setTargetMethod("sayHello1");
    
            return jobDetail;
        }
    
        // 配置触发器1
        @Bean(name = "firstTrigger")
        public SimpleTriggerFactoryBean firstTrigger(JobDetail firstJobDetail) {
            SimpleTriggerFactoryBean trigger = new SimpleTriggerFactoryBean();
            trigger.setJobDetail(firstJobDetail);
            // 设置任务启动延迟
            trigger.setStartDelay(0);
            // 每5秒执行一次
            trigger.setRepeatInterval(5000);
            return trigger;
        }
    
        // 配置定时任务2
        @Bean(name = "secondJobDetail")
        public MethodInvokingJobDetailFactoryBean secondJobDetail(ScheduleTask secondJob) {
            MethodInvokingJobDetailFactoryBean jobDetail = new MethodInvokingJobDetailFactoryBean();
            // 是否并发执行
            jobDetail.setConcurrent(false);
            // 为需要执行的实体类对应的对象
            jobDetail.setTargetObject(secondJob);
            // 需要执行的方法
            jobDetail.setTargetMethod("sayHello2");
            return jobDetail;
        }
    
        // 配置触发器2
        @Bean(name = "secondTrigger")
        public SimpleTriggerFactoryBean secondTrigger(JobDetail secondJobDetail) {
            SimpleTriggerFactoryBean trigger = new SimpleTriggerFactoryBean();
            trigger.setJobDetail(secondJobDetail);
            // 定时任务时间(这里也可以用CronTrigger,同理)
            trigger.setStartDelay(0);
            trigger.setRepeatInterval(10000);
            return trigger;
        }
    
        // 配置Scheduler
        @Bean(name = "scheduler")
        public SchedulerFactoryBean schedulerFactory(Trigger firstTrigger, Trigger secondTrigger) {
            SchedulerFactoryBean bean = new SchedulerFactoryBean();
            // 延时启动,应用启动1秒后
            bean.setStartupDelay(1);
            // 注册触发器
            bean.setTriggers(firstTrigger,secondTrigger);
            return bean;
        }
    }
    

    查询数据库,修改定时间类,这里每隔五秒查询一次数据库,判断是否需要修改定时时间

    
    import com.ophylink.ems.api.dao.ScheduleConfigRepository;
    import com.ophylink.ems.api.entity.ScheduleConfig;
    import org.quartz.Scheduler;
    import org.quartz.SchedulerException;
    import org.quartz.SimpleScheduleBuilder;
    import org.quartz.SimpleTrigger;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.scheduling.annotation.EnableScheduling;
    import org.springframework.scheduling.annotation.Scheduled;
    import org.springframework.stereotype.Component;
    
    import javax.annotation.Resource;
    import java.util.List;
    
    @Configuration
    @EnableScheduling
    @Component
    public class ScheduleRefreshDatabase {
    
        @Autowired
        private ScheduleConfigRepository repository;
        private List<ScheduleConfig> configList;
    
        @Resource(name = "firstTrigger")
        private SimpleTrigger firstTrigger;
    
        @Resource(name = "secondTrigger")
        private SimpleTrigger secondTrigger;
    
        @Resource(name = "scheduler")
        private Scheduler scheduler;
    
        @Scheduled(fixedRate = 5000) // 每隔5s查库,并根据查询结果决定是否重新设置定时任务
        public void scheduleUpdateCronTrigger() throws SchedulerException {
            configList = repository.findAll();
            if(configList!=null&&configList.size()>0) {
                for(ScheduleConfig config:configList) {
                    SimpleTrigger trigger = null;
                    switch (config.getName()){
                        case "定时任务1":trigger = (SimpleTrigger) scheduler.getTrigger(firstTrigger.getKey());break;
                        case "定时任务2":trigger = (SimpleTrigger) scheduler.getTrigger(secondTrigger.getKey());break;
                    }
                    Long currentTime = trigger.getRepeatInterval();// 当前Trigger使用的
                    Long searchTime = repository.findOne(config.getName()).getScheduleTime();// 从数据库查询出来的
    
                    if (currentTime.equals(searchTime)) {
                        // 如果当前使用的定时时间和数据库查出来的定时时间一致,则不刷新任务
                    } else {
                        // 表达式调度构建器
                        SimpleScheduleBuilder scheduleBuilder = SimpleScheduleBuilder.repeatSecondlyForever(Integer.valueOf(String.valueOf(searchTime)));
                        // 按新的cronExpression表达式重新构建trigger
                        trigger = (SimpleTrigger) scheduler.getTrigger(trigger.getKey());
                        trigger = trigger.getTriggerBuilder().withIdentity(trigger.getKey())
                                .withSchedule(scheduleBuilder).build();
                        // 按新的trigger重新设置job执行
                        scheduler.rescheduleJob(trigger.getKey(), trigger);
                    }
                }
            }
        }
    }
    

    以上就是全部的,下面贴出实体类,仓库类和maven

    
    import javax.persistence.*;
    import java.util.Objects;
    
    @Entity
    @Table(name = "schedule_config", schema = "ems", catalog = "")
    public class ScheduleConfig {
        private String name;
        private Long scheduleTime;
        @Id
        @Column(name = "name")
        public String getName() {
            return name;
        }
    
        public void setName(String name) {
            this.name = name;
        }
    
        @Basic
        @Column(name = "schedule_time")
        public Long getScheduleTime() {
            return scheduleTime;
        }
    
        public void setScheduleTime(Long scheduleTime) {
            this.scheduleTime = scheduleTime;
        }
    
    
        @Override
        public boolean equals(Object o) {
            if (this == o) return true;
            if (o == null || getClass() != o.getClass()) return false;
            ScheduleConfig config = (ScheduleConfig) o;
            return Objects.equals(name, config.name) &&
                    Objects.equals(scheduleTime, config.scheduleTime);
        }
    
        @Override
        public int hashCode() {
            return Objects.hash(name, scheduleTime);
        }
    }
    
    
    import com.ophylink.ems.api.entity.ScheduleConfig;
    import org.springframework.data.jpa.repository.JpaRepository;
    
    public interface ScheduleConfigRepository extends JpaRepository<ScheduleConfig,String> {
    }
    
    <?xml version="1.0" encoding="UTF-8"?>
    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
             xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
        <modelVersion>4.0.0</modelVersion>
    
        <groupId>com.ophylink</groupId>
        <artifactId>ems</artifactId>
        <version>0.0.1-SNAPSHOT</version>
        <packaging>jar</packaging>
    
        <name>ems</name>
        <description>Demo project for Spring Boot</description>
    
        <parent>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-parent</artifactId>
            <version>1.5.9.RELEASE</version>
            <relativePath/> <!-- lookup parent from repository -->
        </parent>
    
        <properties>
            <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
            <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
            <java.version>1.8</java.version>
        </properties>
    
        <dependencies>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter</artifactId>
            </dependency>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-web</artifactId>
            </dependency>
    
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-test</artifactId>
                <scope>test</scope>
            </dependency>
    
    
    
            <dependency>
                <groupId>org.quartz-scheduler</groupId>
                <artifactId>quartz</artifactId>
                <version>2.2.1</version>
                <exclusions>
                    <exclusion>
                        <artifactId>slf4j-api</artifactId>
                        <groupId>org.slf4j</groupId>
                    </exclusion>
                </exclusions>
            </dependency>
            <dependency><!-- 该依赖必加,里面有sping对schedule的支持 -->
                <groupId>org.springframework</groupId>
                <artifactId>spring-context-support</artifactId>
            </dependency>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-data-jpa</artifactId>
            </dependency>
            <dependency>
                <groupId>mysql</groupId>
                <artifactId>mysql-connector-java</artifactId>
                <scope>runtime</scope>
            </dependency>
    </project>
    

    下面是数据库结构和数据
    ![1G%85P6C41XN9~I99MJ$)P.png

    R01VYV${F4@4R9A8LPEGR3S.png

    相关文章

      网友评论

          本文标题:springboot+quartz实现多任务动态修改时间,亲测有

          本文链接:https://www.haomeiwen.com/subject/ydqeaftx.html