[SpringBoot 分布式调度elasticjob 整合 ]

目录

前言:

配置作业

实现任务处理类

启动SpringBoot应用程序

下面是代码是我另一个文章看见 记录的笔记,  我前面也使用了elastic-job做重试机制,有兴趣可以看一下

依赖:

elastic job提供了2种类型的定时任务:SimpleJob、DataflowJob,根据需要实现即可,都需要放到spring容器中

配置文件:

下载 lite ui 的二进制tar包(不是源码包),版本尽量与 maven 引入的 lite 版本保持一致​编辑

解压,根据需要修改 conf/application.properties

常见操作说明

xxl-job

web控制台的部署

下载最新稳定版的压缩包,解压,在IDEA中导入

父项目 xxl-job包含3个子项目

3、修改 xxl-job-admin 的配置文件

4、打包部署,访问 http://localhost:8080/xxl-job-admin 登录系统,默认账号密码 admin/123456

5、初始化系统数据

编写定时任务

2、复制 application.properties 的相关配置项

3、复制配置类

4、仿照 service.jobhandler.SampleXxlJob 写定时任务

策略说明执行器集群部署时,调度中心支持的路由策略如下

调度过于密集,执行器来不及处理任务实例时,调度中心提供的阻塞处理策略如下


前言:

    笔记,elastic-job可以通过可视化界面去操作动态控制参数配置,也可以通过代码配置文件去实现,  我这边用得最多的还是  elastic-job重试机制,大家根据自己情况去判断使用,我主要记录笔记一下

配置注册中心:

elasticjob:
  zookeeper:
    server-lists: 127.0.0.1:2181
    namespace: elasticjob

配置作业

在使用Elastic-Job时,需要先配置作业的相关信息,包括任务处理类、分片总数、分片参数等。在SpringBoot中,可以通过Java Config的方式来配置作业信息。

@Configuration
public class ElasticJobConfig {

    @Autowired
    private ZookeeperRegistryCenter registryCenter;

    @Bean(initMethod = "init")
    public JobScheduler simpleJobScheduler(final OrderMessageConsumer orderMessageConsumer,
                                           @Value("${elasticjob.simpleJob.cron}") final String cron,
                                           @Value("${elasticjob.simpleJob.shardingTotalCount}") final int shardingTotalCount,
                                           @Value("${elasticjob.simpleJob.shardingItemParameters}") final String shardingItemParameters) {
        LiteJobConfiguration liteJobConfiguration = LiteJobConfiguration.newBuilder(
                new SimpleJobConfiguration(
                        JobCoreConfiguration.newBuilder("orderJob", cron, shardingTotalCount)
                                .shardingItemParameters(shardingItemParameters)
                                .build(),
                        orderMessageConsumer.getClass().getCanonicalName()
                )
        ).overwrite(true).build();

        return new SpringJobScheduler(
                orderMessageConsumer,
                registryCenter,
                liteJobConfiguration,
                new ElasticJobListener()
        );
    }
}

 在Java Config中,我们使用@Bean注解来创建SpringJobScheduler对象,并将任务处理类、作业配置信息、注册中心和作业监听器传入该对象中。作业配置信息中包含了任务名、任务处理类、分片总数、分片参数等信息。

实现任务处理类

在使用Elastic-Job时,需要实现任务处理类(Job),用来处理具体的业务逻辑。在SpringBoot中,我们可以将任务处理类配置为一个Bean,并在SpringJobScheduler对象的构造函数中传入该Bean。

@Component
public class OrderMessageConsumer implements SimpleJob {

    @Autowired
    private OrderService orderService;

    @Override
    public void execute(ShardingContext shardingContext) {
        // 处理业务逻辑
        orderService.createOrder(shardingContext.getShardingParameter());
    }
}

在任务处理类中,我们需要实现Elastic-Job的SimpleJob接口,并实现execute方法。在execute方法中,我们可以通过ShardingContext来获取分片参数,用来处理具体的业务逻辑。

启动SpringBoot应用程序

在完成以上步骤后,就可以启动SpringBoot应用程序,Elastic-Job会自动注册作业节点并启动作业。如果需要修改作业配置信息,可以在配置文件中修改对应的参数即可。

总的来说,使用SpringBoot整合Elastic-Job非常方便,只需要引入相关依赖、配置注册中心和作业信息,就可以启动分布式任务调度。同时,Elastic-Job提供了完善的任务调度和重试机制,可以方便地实现任务分片、任务重试等功能


下面是代码是我另一个文章看见 记录的笔记,  我前面也使用了elastic-job做重试机制,有兴趣可以看一下

依赖:


    org.apache.shardingsphere.elasticjob
    elasticjob-lite-spring-boot-starter
    3.0.0



根据情况设置对应版本

    com.dangdang
    elastic-job-lite-spring-boot-starter
    ${elastic-job.version}

elastic job提供了2种类型的定时任务:SimpleJob、DataflowJob,根据需要实现即可,都需要放到spring容器中

@Component
public class MySimpleJob implements SimpleJob {

    @Override
    public void execute(ShardingContext context) {
        //...
    }

}
@Component
public class MyDataflowJob implements DataflowJob {

    @Override
    public List fetchData(ShardingContext context) {
        //...
    }

    @Override
    public void processData(ShardingContext shardingContext, List orders) {
        // ...
    }

}

配置文件:

elasticjob:
  #注册中心配置
  regCenter:
    #zk节点
    serverLists: localhost:2181
    #命名空间,即存储elastic job数据要zk node
    namespace: elasticjob-task
  #定时任务配置
  jobs:
    #自定义的任务名称
    mySimpleJob:
      #对应的类
      elasticJobClass: com.chy.mall.job.MySimpleJob
      cron: 0/10 * * * * ?
      #自定义参数
      jobParameter: xxx
      #分片总数
      shardingTotalCount: 3
      #自定义的分片参数
      shardingItemParameters: 0=Beijing,1=Shanghai,2=Guangzhou
    myDataFlowJob:
      elasticJobClass: com.chy.mall.job.MyDataflowJob
      cron: 0/10 * * * * ?
      shardingTotalCount: 3

定时任务已经注册到zk,后续在yml中修改cron表达式、自定义参数、分片总数这些任务配置项是不会生效的,需要到web控制台修改,来更新zk保存的任务信息


    org.apache.shardingsphere.elasticjob
    elasticjob-error-handler-email
     3.0.0

 

elasticjob:
  regCenter:
    ...
  jobs:
    ...
    jobErrorHandlerType: EMAIL 
  props:
    email:
      host: host
      port: 465
      username: username
      password: password
      useSsl: true
      subject: ElasticJob error message
      from: [email protected]
      to: [email protected],[email protected]
      cc: [email protected]
      bcc: [email protected]
      debug: false

下载 lite ui 的二进制tar包(不是源码包),版本尽量与 maven 引入的 lite 版本保持一致
[SpringBoot 分布式调度elasticjob 整合 ]_第1张图片

 

解压,根据需要修改 conf/application.properties

#使用的端口
server.port=8088

#账号、密码,root账号可修改配置,guest游客账号只能看、不能修改
auth.root_username=root
auth.root_password=root
auth.guest_username=guest
auth.guest_password=guest

#事件追踪数据源配置,这个不是必需的,数据库连接后续可以在web界面配置
#配置了elastic job会自动创建几张表,用于记录任务执行的历史记录、结果、总结摘要,便于分析,建议配上
#默认值引入了h2、postgresql的数据库驱动,如果要配置为mysql等其它数据库,可以把对应的驱动jar包放到 ext-lib目录下
spring.datasource.default.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.default.url=jdbc:mysql://localhost:3306/mall?serverTimezone=UTC
spring.datasource.default.username=root
spring.datasource.default.password=root
spring.jpa.show-sql=false

 

执行bin下的start脚本启动应用,浏览器访问 127.0.0.1:8088,输入账号、密码

添加注册中心,信息与yml配置的注册中心保持一致

常见操作说明


1、状态

分片待调整:新的定时任务注册上去,尚未触发过即为此状态,到cron表达式指定周期时自动触发过1次,状态就正常了。
失效:暂时下线该定时任务,后续还可以上线。
终止:永久下线该定时任务,不能再上线。
 
2、分片总数、参数
这些配置参数都可以从上下文中获取到,用于向定时任务传递额外的配置,均可以在web控制台进行配置
 

#自定义参数
jobParameter: xxx
#分片总数,此定时任务每次触发时使用几个分片来执行
shardingTotalCount: 3
#自定义的分片参数,index=value,数量与分片总数保持一致
shardingItemParameters: 0=Beijing,1=Shanghai,2=Guangzhou
 
https://blog.csdn.net/chy_18883701161/article/details/106314007

@Component
public class MySimpleJob implements SimpleJob {

    @Override
    public void execute(ShardingContext context) {
        //自定义参数
        String jobParameter = context.getJobParameter();
        //分片总数
        int shardingTotalCount = context.getShardingTotalCount();
        //当前分片的index
        int shardingItem = context.getShardingItem();
        //当前分片项对应的值
        String shardingParameter = context.getShardingParameter();

        //...
    }

}

[SpringBoot 分布式调度elasticjob 整合 ]_第2张图片

 

分片总数:指定该定时任务触发1次时,需要分配给几个副本执行。假设分片总数设置为3,定时任务所在服务

  • 部署了5个实例,分片分散情况往往是 1+1+1 ,触发1次时这3个实例会分别执行1次;
  • 部署了2个实例,分片分散情况往往时 1+2,触发1次时1个实例执行1次,另一个实例执行2个;
  • 部署了1个实例,这个定时任务的所有分片都集中在这个实例上,触发1次时这个实例会执行3次;
  • 分片总数通常设置为1,避免触发时重复执行。

 如果定时任务要处理的数据量级很大,可以将数据分配给多个分片共同处理,shardingItemParameters 指定分段(id分段、状态划分等),定时任务中判断当前分片对应的 shardingItemParameters,做相应处理

shardingTotalCount: 3 shardingItemParameters: 0=待付款,1=待发货,2=待退款

@Component
public class MySimpleJob implements SimpleJob {

    @Override
    public void execute(ShardingContext context) {
        switch (context.getShardingParameter()) {
            case "待付款":
                //...
                break;
            case "待发货":
                //...
                break;
            case "待退款":
                //...
                break;
            default:
        }
    }

}

xxl-job

官网:分布式任务调度平台XXL-JOB
github:GitHub - xuxueli/xxl-job: A distributed task scheduling framework.(分布式任务调度平台XXL-JOB)

web控制台的部署

下载最新稳定版的压缩包,解压,在IDEA中导入

父项目 xxl-job包含3个子项目
  • xxl-job-core:核心模块,提供公共依赖
  • xxl-job-admin:调度中心,提供web界面的控制台
  • xxl-job-executor-samples:执行器(定时任务)示例,不需要的可以删除这个模块。包含2个子项目,一个是springboot版本的示例,一个是frameless无框架版本的示例。

 
2、执行doc/db下的初始化sql脚本
 

3、修改 xxl-job-admin 的配置文件

application.properties:根据需要调整应用使用的端口、访问路径、数据库配置、报警邮箱配置。邮箱配置可以不管,但不能注释掉。
logback.xml 日志配置
xxl-job-admin 集群部署时,各 xxl-job-admin 节点务必连接同一个mysql数据库、节点机器的时钟务必保持一致;如果 mysql 做主从,xxl-job-admin 各节点务必强制走主库。
 

4、打包部署,访问 http://localhost:8080/xxl-job-admin 登录系统,默认账号密码 admin/123456

5、初始化系统数据

在用户管理中修改密码、增删用户
在任务管理中删除示例任务
在执行器管理中增删、修改执行器
 

编写定时任务

从springboot版本的示例中copy所需内容

1、添加依赖,最好与控制台的版本保持一致


    com.xuxueli
    xxl-job-core
    2.3.1

2、复制 application.properties 的相关配置项

### 调度中心部署根地址 [选填]:如调度中心集群部署存在多个地址则用逗号分隔。执行器将会使用该地址进行"执行器心跳注册"和"任务结果回调";为空则关闭自动注册;
xxl.job.admin.addresses=http://127.0.0.1:8080/xxl-job-admin

### 执行器通讯TOKEN [选填]:非空时启用;
xxl.job.accessToken=

### 执行器AppName [选填]:执行器心跳注册分组依据;为空则关闭自动注册
xxl.job.executor.appname=xxl-job-executor-sample

### 执行器注册 [选填]:优先使用该配置作为注册地址,为空时使用内嵌服务 ”IP:PORT“ 作为注册地址。从而更灵活的支持容器类型执行器动态IP和动态映射端口问题。
xxl.job.executor.address=

### 执行器IP [选填]:默认为空表示自动获取IP,多网卡时可手动设置指定IP,该IP不会绑定Host仅作为通讯实用;地址信息用于 "执行器注册" 和 "调度中心请求并触发任务";
xxl.job.executor.ip=

### 执行器端口号 [选填]:小于等于0则自动获取;默认端口为9999,单机部署多个执行器时,注意要配置不同执行器端口;
xxl.job.executor.port=9999

### 执行器运行日志文件存储磁盘路径 [选填] :需要对该路径拥有读写权限;为空则使用默认路径;
xxl.job.executor.logpath=/data/applogs/xxl-job/jobhandler

### 执行器日志文件保存天数 [选填] : 过期日志自动清理, 限制值大于等于3时生效; 否则, 如-1, 关闭自动清理功能;
xxl.job.executor.logretentiondays=30

3、复制配置类

import com.xxl.job.core.executor.impl.XxlJobSpringExecutor;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * xxl-job config
 *
 * @author xuxueli 2017-04-28
 */
@Configuration
public class XxlJobConfig {
    private Logger logger = LoggerFactory.getLogger(XxlJobConfig.class);

    @Value("${xxl.job.admin.addresses}")
    private String adminAddresses;

    @Value("${xxl.job.accessToken}")
    private String accessToken;

    @Value("${xxl.job.executor.appname}")
    private String appname;

    @Value("${xxl.job.executor.address}")
    private String address;

    @Value("${xxl.job.executor.ip}")
    private String ip;

    @Value("${xxl.job.executor.port}")
    private int port;

    @Value("${xxl.job.executor.logpath}")
    private String logPath;

    @Value("${xxl.job.executor.logretentiondays}")
    private int logRetentionDays;


    @Bean
    public XxlJobSpringExecutor xxlJobExecutor() {
        logger.info(">>>>>>>>>>> xxl-job config init.");
        XxlJobSpringExecutor xxlJobSpringExecutor = new XxlJobSpringExecutor();
        xxlJobSpringExecutor.setAdminAddresses(adminAddresses);
        xxlJobSpringExecutor.setAppname(appname);
        xxlJobSpringExecutor.setAddress(address);
        xxlJobSpringExecutor.setIp(ip);
        xxlJobSpringExecutor.setPort(port);
        xxlJobSpringExecutor.setAccessToken(accessToken);
        xxlJobSpringExecutor.setLogPath(logPath);
        xxlJobSpringExecutor.setLogRetentionDays(logRetentionDays);

        return xxlJobSpringExecutor;
    }

    /**
     * 针对多网卡、容器内部署等情况,可借助 "spring-cloud-commons" 提供的 "InetUtils" 组件灵活定制注册IP;
     *
     *      1、引入依赖:
     *          
     *             org.springframework.cloud
     *             spring-cloud-commons
     *             ${version}
     *         
     *
     *      2、配置文件,或者容器启动变量
     *          spring.cloud.inetutils.preferred-networks: 'xxx.xxx.xxx.'
     *
     *      3、获取IP
     *          String ip_ = inetUtils.findFirstNonLoopbackHostInfo().getIpAddress();
     */


}

4、仿照 service.jobhandler.SampleXxlJob 写定时任务

import com.xxl.job.core.context.XxlJobHelper;
import com.xxl.job.core.handler.annotation.XxlJob;
import org.springframework.stereotype.Component;

@Component  //放到容器中
public class XxxJob {

    /**
     * 简单任务示例
     */
    @XxlJob("sampleJobHandler")
    public void sampleJobHandler() throws Exception {
        //执行日志:需要通过 "XxlJobHelper.log" 打印执行日志;
        XxlJobHelper.log("sampleJobHandler start");

        //可通过 XxlJobHelper.handleFail()/handleSuccess() 指定任务执行结果,未设置时默认默认为 handleSuccess() 成功
        try {
            int i = 1 / 0;
        } catch (Exception e) {
            XxlJobHelper.handleFail();
        }
    }

    /**
     * 分片广播任务示例
     */
    @XxlJob("shardingJobHandler")
    public void shardingJobHandler() throws Exception {
        // 分片参数
        int shardIndex = XxlJobHelper.getShardIndex();
        int shardTotal = XxlJobHelper.getShardTotal();
        XxlJobHelper.log("分片参数:当前分片序号 = {}, 总分片数 = {}", shardIndex, shardTotal);
        //...
    }

}

启动应用,调度中心 -> 任务管理 -> 增删、修改任务实例[SpringBoot 分布式调度elasticjob 整合 ]_第3张图片

 

运行模式使用 BEAN,JobHandler 与 @XxlJob 指定的 jobName 保持一致。

策略说明
执行器集群部署时,调度中心支持的路由策略如下

ROUND(轮询)
FIRST(第一个):固定选择第一个节点
LAST(最后一个):固定选择最后一个节点
RANDOM(随机):随机选择在线的节点
CONSISTENT_HASH(一致性HASH):每个任务按照Hash算法固定选择某个节点,且所有任务均匀散列在不同节点上。
LEAST_FREQUENTLY_USED(最不经常使用):优先选择使用频率最低的节点。
LEAST_RECENTLY_USED(最近最久未使用):优先选择最久未使用的节点。
FAILOVER(故障转移):按照顺序依次进行心跳检测,第一个心跳检测成功的节点选定为目标执行器并发起调度。
BUSYOVER(忙碌转移):按照顺序依次进行空闲检测,第一个空闲检测成功的节点选定为目标执行器并发起调度。
SHARDING_BROADCAST(分片广播):广播触发对应集群中所有节点执行一次任务,同时系统自动传递分片参数;可根据分片参数开发分片任务。
 

调度过于密集,执行器来不及处理任务实例时,调度中心提供的阻塞处理策略如下

  • 单机串行(默认):调度请求进入单机执行器后,调度请求进入FIFO队列并以串行方式运行。
  • 丢弃后续调度:调度请求进入单机执行器后,发现执行器存在运行的调度任务,本次请求将会被丢弃并标记为失败。
  • 覆盖之前调度:调度请求进入单机执行器后,发现执行器存在运行的调度任务,将会终止运行中的调度任务并清空队列,然后运行本地调度任务。

 
 相关URL:https://blog.csdn.net/chy_18883701161/article/details/106314007

你可能感兴趣的:(大数据,spring,boot,java,后端)