springboot下报错“MethodInvokingJobDetailFactoryBean is not serializable”

quartz是在java语言中用得最为广泛的任务调度框架,spring对quartz进行了集成,方便了开发和使用。

在springboot下,我们对一个采用quartz的app进行多个集群部署的时候,对于quartz的集群采用数据库集群方式,报了“MethodInvokingJobDetailFactoryBean is not serializable”的错误。

原因是spring为了让开发更方便,耦合性更低,对quartz中 JobDetailFactoryBean 用 MethodInvokingJobDetailFactoryBean 进行了封装,假如quartz是单机运行那是没有关系的,但是当采用数据库方式进行集群的时候,quartz会把 JobDetailFactoryBean 序列化存储到数据库中,假如用 MethodInvokingJobDetailFactoryBean 的话,就会报错,说不能序列化。

解决的办法参考这篇文章:使用Spring + quartz集群持久化时注意事项,但是这篇文章中只讲了在spring下如何修改。

下面讲一下在 springboot 中如何修改:
一、需要将原先定义的pojo 的 Job 改成实现 Job 接口:

@Component("myJobHandler")
public class MyJobHandler implements Job {

    @Override
    public void execute(JobExecutionContext context) throws JobExecutionException {
        System.out.println("do it ......");
    }

}

二、在配置中如下设置:

@Bean(name = "myJobDetailFactoryBean")
    public JobDetailFactoryBean getMyJobDetailFactoryBean() {
        JobDetailFactoryBean jobDetail = new JobDetailFactoryBean();
        jobDetail.setJobClass(com.champbay.quartztest.MyJobHandler.class);
        jobDetail.setDurability(true);
        return jobDetail;
    }

    @Bean(name = "myCronTriggerFactoryBean")
    public CronTriggerFactoryBean getMyCronTriggerFactoryBean(
            @Qualifier("myJobDetailFactoryBean") JobDetailFactoryBean jobDetail) {
        CronTriggerFactoryBean tigger = new CronTriggerFactoryBean();
        tigger.setJobDetail(jobDetail.getObject());
        // 每1分钟     
        tigger.setCronExpression("0 0/1 * * * ?");
        return tigger;
    }

本文结束。

发表评论

邮箱地址不会被公开。 必填项已用*标注