创新实训(18)——springboot定时任务学习及实现用户浏览记录的定时抽取

定时任务的创建

在 Spring 中 可以通过 @EnableScheduling 和 @Scheduled 这两个注解来实现定时任务,接下来看下这两个注解:
(1)@EnableScheduling
可以通过在启动类上添加@EnableScheduling开启定时任务功能
(2)@Scheduled
在定时任务方法上使用@Schedule注解标记定时任务并配置定时任务执行时机。

  • 固定延迟时间:
// 初次调用延迟3秒,任务结束后5秒钟再次调用,两次调用不会同步运行
@Scheduled(initialDelay = 3000, fixedDelay = 5000)
public void timerTask() {
    try {
        System.out.println(System.currentTimeMillis() / 1000);
        Thread.sleep(1000);
    } catch (InterruptedException e) {
        e.printStackTrace();
    }
}
  • 固定间隔时间:
// 初次调用延迟3秒,每隔5秒钟调用一次,多次调用可能同步运行
@Scheduled(initialDelay = 3000, fixedRate = 5000)
public void timerTask() {
    System.out.println(System.currentTimeMillis() / 1000);
}
  • 通过cron表达式配置:
// 从第0秒开始每10秒钟执行一次
@Scheduled(cron = "0/10 * * * * ?")
public void timerTask() {
    System.out.println(System.currentTimeMillis() / 1000);
}
// 从配置文件中读取cron表达式
@Scheduled(cron = "${task.cron}")
public void timerTask() {
    System.out.println(System.currentTimeMillis() / 1000);
}

Cron表达式详解

在这里插入图片描述

动态修改定时任务配置

可以通过实现SchedulingConfigurer接口来配置定时任务,实现不用重启服务修改定时器的cron:

@Component
public class DynamicTask implements SchedulingConfigurer {

    private CronTrigger trigger = new CronTrigger("5/10 * * * * ?");

    @Override
    public void configureTasks(ScheduledTaskRegistrar taskRegistrar) {
        taskRegistrar.addTriggerTask(new Runnable() {
            @Override
            public void run() {
                System.out.println("来自定时器:" + System.currentTimeMillis() / 1000);
            }
        }, new Trigger() {
            @Nullable
            @Override
            public Date nextExecutionTime(TriggerContext context) {
                if (trigger != null) {
                    return trigger.nextExecutionTime(context);
                }
                return null;
            }
        });
    }

    public void setCron(String cron) {
        try {
            this.trigger = new CronTrigger(cron);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

但是上述方法在修改完cron表达式之后,只有再一次到达定时任务的时间,才会调用新的触发时间,导致页面设置的时间不能即时生效,以下改进方法可修正此问题:

@Service
public class ScheduleManager implements SchedulingConfigurer {
    private final Log logger = LogFactory.getLog(getClass());
    /**
     * 受ScheduleManager管理的任务集合
     */
    private final Map<Object, ScheduledTask> taskMap = new HashMap<>();
    /**
     * 定时任务注册器
     */
    private ScheduledTaskRegistrar taskRegistrar;

    /**
     * 系统启动时获取任务注册对象
     *
     * @param taskRegistrar 任务注册对象
     */
    @Override
    public void configureTasks(ScheduledTaskRegistrar taskRegistrar) {
        this.taskRegistrar = taskRegistrar;
        logger.info("scheduleManager has successfully acquired the taskRegistrar");
    }

    /**
     * 添加新任务,如果存在key一致的任务,则取消原任务的执行,但添加新任务失败时原任务不会停止
     *
     * @param key      任务key
     * @param runnable 新任务执行代码
     * @param cron     新任务cron表达式
     */
    public void addTask(Object key, Runnable runnable, String cron) {
        if (runnable != null && !StringUtils.isEmpty(cron)) {
            ScheduledTask oldTask = taskMap.get(key);
            taskMap.put(key, taskRegistrar.scheduleCronTask(new CronTask(runnable, cron)));
            if (oldTask != null) {
                oldTask.cancel();
            }
        }
    }

    /**
     * 重置任务的执行时机,修改失败时任务仍使用原有执行时机
     *
     * @param key  任务key
     * @param cron 任务新cron表达式
     */
    public void modifyTask(Object key, String cron) {
        ScheduledTask oldTask = taskMap.get(key);
        if (oldTask != null && !StringUtils.isEmpty(cron)) {
            taskMap.put(key, taskRegistrar.scheduleCronTask(new CronTask(oldTask.getTask().getRunnable(), cron)));
            oldTask.cancel();
        }
    }

    /**
     * 取消任务执行
     *
     * @param key 任务key
     */
    public void cancelTask(Object key) {
        ScheduledTask task = taskMap.remove(key);
        if (task != null) {
            task.cancel();
        }
    }

    /**
     * 查看是否存在任务
     *
     * @param key 任务key
     * @return 如果任务存在返回true,否则返回false
     */
    public boolean existTask(Object key) {
        return taskMap.get(key) != null;
    }
}

实现用户浏览记录的定时抽取

(1)配置@EnableScheduling
在这里插入图片描述
(2)实现定时抽取方法每20分钟抽取一次


@Component
public class ExtractTask {

    @Resource
    private ExtractData extractData;
    private static final SimpleDateFormat dateFormat = new SimpleDateFormat("HH:mm:ss");

    /**
     * 定时抽取浏览数据 每20分钟一次
     */
    @Scheduled(cron = "0/10 * * * * ?")
    public void extract() {

        System.out.println(System.currentTimeMillis() / 1000);
        extractData.extractUserTagDate();
        extractData.extractUserTagDate();
    }
}

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: 好的,下面是关于使用Spring Boot和Quartz实现定时任务的简介: Quartz是一个流行的Java定时任务框架,可以在应用程序中执行各种定时任务,如定期备份、数据抽取和数据分析等。而Spring Boot是一个快速开发框架,提供了方便的集成Quartz的方式。 要使用Spring Boot和Quartz实现定时任务,首先需要在pom.xml文件中添加Quartz和Spring Boot Quartz的依赖项。然后,定义一个定时任务,可以使用注解@Scheduled来指定任务的执行时间。例如: ```java @Component public class MyScheduler { @Scheduled(cron = "0 0/10 * * * ?") public void myTask() { //执行定时任务的代码 } } ``` 上述代码表示每隔10分钟执行一次myTask()方法。然后,在Spring Boot的主类中,使用@EnableScheduling注解来开启定时任务的支持。例如: ```java @SpringBootApplication @EnableScheduling public class MyApp { public static void main(String[] args) { SpringApplication.run(MyApp.class, args); } } ``` 最后,启动应用程序,定时任务将按照预定时间自动执行。如果需要更高级的定时任务控制,还可以使用Quartz的其他功能,如JobDetail和Trigger等。 ### 回答2: SpringBoot是一个开源的Java开发框架,它提供了很多有用的工具和插件,其中之一便是定时任务quartz。quartz是一款功能强大的开源调度框架,它提供了简单易用的任务调度机制,支持多线程和分布式部署,可以满足大部分的调度需求。 在SpringBoot中,我们可以很方便地使用quartz来实现定时任务。以下是使用SpringBoot和quartz实现定时任务的基本步骤: 1. 在pom.xml文件中添加quartz的依赖项: ``` <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-quartz</artifactId> </dependency> ``` 2. 创建一个任务类,实现Job接口,并实现execute方法来定义任务逻辑: ``` @Component public class MyTask implements Job { @Override public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException { // 定时任务的执行逻辑 } } ``` 3. 在配置文件中定义任务调度器,并为任务分配cron表达式: ``` spring: quartz: job-store-type: jdbc properties: org.quartz.scheduler.instanceName: MyScheduler org.quartz.threadPool.threadCount: 5 job-details: myJob: durability: true requestsRecovery: true trigger-details: myTrigger: cron: 0 0/1 * * * ? job-name: myJob job-data-map: name: world ``` 4. 在任务执行类中,使用@Scheduled注解来指定任务的执行时间: ``` @Component public class MyTask { @Scheduled(cron = "0 0/1 * * * ?") public void doTask(){ // 定时任务的执行逻辑 } } ``` 以上4种方法都是使用SpringBoot和quartz实现定时任务的简单示例,根据实际需求可以进行相应调整和扩展。总的来说,使用springboot和quartz实现定时任务非常方便,能够让我们更加轻松地管理、调度和执行任务,提高开发效率和质量。 ### 回答3: Spring Boot是一款快速构建基于Spring应用的工具,可帮助简化开发和部署。在Spring Boot中,与Quartz相比,Scheduled定时任务通常是首选的。但是,Quartz比Scheduled更灵活、功能更强大、配置更灵活,因此在一些特殊情况下,使用Quartz进行定时任务调度是比较必要的。 Quartz是用Java语言编写的一个开源的调度框架,其主要用于在一个预定义的时间间隔内重复执行某个任务,或者在特定时间点执行某个任务。Quartz提供了众多功能,比如支持分布式定时任务管理、支持动态创建/删除任务、支持时间表达式、状态存储、监控和事件触发等等。 Spring Boot集成了Quartz非常容易,只需要在Spring Boot项目中添加Quartz相关依赖,在Spring Boot配置文件中增加Quartz配置即可。以下是一个完整的Spring Boot集成Quartz的示例代码: 1.在pom.xml中添加Quartz和Spring Boot Starter Web依赖: ``` <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.quartz-scheduler</groupId> <artifactId>quartz</artifactId> <version>${quartz.version}</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-context-support</artifactId> </dependency> ``` 2.在配置文件中增加Quartz相关配置: ``` spring.quartz.job-store-type=memory spring.quartz.properties.org.quartz.threadPool.threadCount=10 spring.quartz.properties.org.quartz.jobStore.class=org.quartz.simpl.RAMJobStore ``` 3.编写定时任务处理类: ``` @Component public class JobScheduler { @Autowired private Scheduler scheduler; @Scheduled(cron = "0 0/1 * * * ?") public void doSomething() { JobDetail jobDetail = buildJobDetail(); Trigger trigger = buildJobTrigger(jobDetail); try { scheduler.scheduleJob(jobDetail, trigger); } catch (SchedulerException e) { e.printStackTrace(); } } private JobDetail buildJobDetail() { JobDataMap jobDataMap = new JobDataMap(); jobDataMap.put("key", "value"); return JobBuilder.newJob(Job.class) .withIdentity(UUID.randomUUID().toString(), "job-group") .withDescription("sample job") .usingJobData(jobDataMap) .storeDurably(true) .build(); } private Trigger buildJobTrigger(JobDetail jobDetail) { return TriggerBuilder.newTrigger() .forJob(jobDetail) .withIdentity(UUID.randomUUID().toString(), "trigger-group") .withDescription("sample trigger") .withSchedule(CronScheduleBuilder.cronSchedule("0 0/1 * * * ?")) .build(); } } ``` 虽然Quartz需要对定时任务进行配置,但是它提供了更为灵活的条件和任务调度,非常适合在实际生产环境中使用。总之,使用Spring Boot集成Quartz可以非常方便地实现定时任务的调度,既简单又强大,可以大大提高应用的效率和可靠性。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值