关于分布式任务调度平台 XXL-JOB, 其实作者 许雪里在其发布的中文教程 http://www.xuxueli.com/xxl-job/#/ 中已经介绍的很清楚了, 这里我就不做过多的介绍了, 关于其搭建教程, 本人依照其文档搭建起来基本上也没遇到啥问题, 这里通过博客的形式记录下来.
1, 源码下载地址
1,GitHub: https://github.com/xuxueli/xxl-job
2, 码云: https://gitee.com/xuxueli0323/xxl-job
2, 文档地址
1, 中文文档: http://www.xuxueli.com/xxl-job/#/
2, 英文文档: http://www.xuxueli.com/xxl-job/en/#/
3, 源码结构
通过上面给出的源码下载地址, 我们将源码 clone 到 IDEA 中, 如下:
4, 初始化数据库
初始化脚本在上面源码目录的 /doc/db/tables_xxl_job.sql , 将此脚本在 MySQL 数据库中执行一遍.
执行完毕, 会在 MySQL 数据库中生成如下 16 张表:
5, 配置调度中心
调度中心就是源码中的 xxl-job-admin 工程, 我们需要将其配置成自己需要的调度中心, 通过该工程我们能够以图形化的方式统一管理任务调度平台上调度任务, 负责触发调度执行.
1, 修改调度中心配置文件
文件地址:/xxl-job/xxl-job-admin/src/main/resources/xxl-job-admin.properties
配置文件说明:
- ### 1, 调度中心项目的端口号以及访问路径
- server.port=8080
- server.context-path=/xxl-job-admin
- ### 2, 配置静态文件的前缀
- spring.mvc.static-path-pattern=/static/**
- spring.resources.static-locations=classpath:/static/
- ### 3, 配置模板文件
- spring.freemarker.templateLoaderPath=classpath:/templates/
- spring.freemarker.suffix=.ftl
- spring.freemarker.charset=UTF-8
- spring.freemarker.request-context-attribute=request
- spring.freemarker.settings.number_format=0.##########
- ### 4, 配置 mybatis 的 mapper 文件地址
- mybatis.mapper-locations=classpath:/mybatis-mapper/*Mapper.xml
- ### 5, 配置数据库的地址
- spring.datasource.url=jdbc:MySQL://127.0.0.1:3306/xxl-job?Unicode=true&characterEncoding=UTF-8
- spring.datasource.username=root
- spring.datasource.password=root_pwd
- spring.datasource.driver-class-name=com.MySQL.jdbc.Driver
- spring.datasource.type=org.apache.tomcat.jdbc.pool.DataSource
- spring.datasource.tomcat.max-wait=10000
- spring.datasource.tomcat.max-active=30
- spring.datasource.tomcat.test-on-borrow=true
- spring.datasource.tomcat.validation-query=SELECT 1
- spring.datasource.tomcat.validation-interval=30000
- ### 6, 配置报警邮箱
- spring.mail.host=smtp.qq.com
- spring.mail.port=25
- spring.mail.username=xxx@qq.com
- spring.mail.password=xxx
- spring.mail.properties.mail.smtp.auth=true
- spring.mail.properties.mail.smtp.starttls.enable=true
- spring.mail.properties.mail.smtp.starttls.required=true
- ### 7, 管理界面的登录用户名密码
- xxl.job.login.username=admin
- xxl.job.login.password=123456
- ### 8, 调度中心通讯 TOKEN, 非空时启用
- xxl.job.accessToken=
- ### 9, 调度中心国际化设置, 默认为中文版本, 值设置为 "en" 时切换为英文版本
- xxl.job.I18N=
- 注意: 基本上上面的配置文件我们需要修改的只有第 5 点, 修改数据库的地址, 这要与我们前面初始化的数据库名称径, 用户名密码保持一致;
- 第二个就是修改第 6 点, 报警邮箱, 因为该工程任务失败后有失败告警功能, 可以通过邮件来提醒, 如果我们需要此功能, 可以配置一下.
- 2, 部署调度中心
- 该工程是一个 springboot 项目, 我们只需要在 IDEA 中执行 XxlJobAdminApplication 类即可运行该工程:
- 3, 访问调度中心管理界面
- 在浏览器输入 http://localhost:8080/xxl-job-admin 然后输入用户名和密码 (前面配置文件中配置的), 即可看到如下管理界面.
- 6, 创建执行器项目
- 其实在源码中, 作者提供了各个版本的 执行器项目, 下面我以创建一个 springboot 版本的执行器为例来介绍.
- 这个执行器的地址为: https://github.com/YSOcean/xxljobexecutordemo.git
- 1, 添加 maven 依赖
- 在创建好的 springboot 项目的 pom.xml 文件中添加如下依赖:
- <!-- xxl-rpc-core -->
- <dependency>
- <groupId>com.xuxueli</groupId>
- <artifactId>xxl-job-core</artifactId>
- <version>2.0.1</version>
- </dependency>
- 2, 配置执行器
- 在创建好的 springboot 项目的配置文件 application.YAML 添加如下配置:
- server:
- #项目端口号
- port: 8081
- logging:
- #日志文件
- config: classpath:logback.xml
- xxl:
- job:
- admin:
- #调度中心部署跟地址: 如调度中心集群部署存在多个地址则用逗号分隔.
- #执行器将会使用该地址进行 "执行器心跳注册" 和 "任务结果回调".
- addresses: http://127.0.0.1:8080/xxl-job-admin
- #分别配置执行器的名称, ip 地址, 端口号
- #注意: 如果配置多个执行器时, 防止端口冲突
- executor:
- appname: executorDemo
- ip: 127.0.0.1
- port: 9999
- #执行器运行日志文件存储的磁盘位置, 需要对该路径拥有读写权限
- logpath: /data/applogs/xxl-job/jobhandler
- #执行器 Log 文件定期清理功能, 指定日志保存天数, 日志文件过期自动删除. 限制至少保持 3 天, 否则功能不生效;
- #-1 表示永不删除
- logretentiondays: -1
- 这里需要注意的是: 配置执行器的名称, IP 地址, 端口号, 后面如果配置多个执行器时, 要防止端口冲突. 再就是执行器的名称, 我们后面会到上一步的调度中心管理界面进行对应配置.
- 3, 载入配置文件
- 在项目中创建 XxlJobConfig.class 文件:
- package com.ys.xxljobexecutordemo.config;
- 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;
- /**
- * Create by YSOcean
- */
- @Configuration
- public class XxlJobConfig {
- private Logger logger = LoggerFactory.getLogger(XxlJobConfig.class);
- @Value("${xxl.job.admin.addresses}")
- private String adminAddresses;
- @Value("${xxl.job.executor.appname}")
- private String appName;
- @Value("${xxl.job.executor.ip}")
- private String ip;
- @Value("${xxl.job.executor.port}")
- private int port;
- @Value("${xxl.job.accessToken}")
- private String accessToken;
- @Value("${xxl.job.executor.logpath}")
- private String logPath;
- @Value("${xxl.job.executor.logretentiondays}")
- private int logRetentionDays;
- @Bean(initMethod = "start", destroyMethod = "destroy")
- public XxlJobSpringExecutor xxlJobExecutor() {
- logger.info(">>>>>>>>>>> xxl-job config init.");
- XxlJobSpringExecutor xxlJobSpringExecutor = new XxlJobSpringExecutor();
- xxlJobSpringExecutor.setAdminAddresses(adminAddresses);
- xxlJobSpringExecutor.setAppName(appName);
- xxlJobSpringExecutor.setIp(ip);
- xxlJobSpringExecutor.setPort(port);
- xxlJobSpringExecutor.setAccessToken(accessToken);
- xxlJobSpringExecutor.setLogPath(logPath);
- xxlJobSpringExecutor.setLogRetentionDays(logRetentionDays);
- return xxlJobSpringExecutor;
- }
- }
- View Code
4, 创建任务 JobHandler
在项目中创建一个 Handler, 用于执行我们想要执行的东西, 这里我只是简单的打印一行日志:
XXL-JOB, Hello World!!!
- package com.ys.xxljobexecutordemo.jobhandler;
- import com.xxl.job.core.biz.model.ReturnT;
- import com.xxl.job.core.handler.IJobHandler;
- import com.xxl.job.core.handler.annotation.JobHandler;
- import com.xxl.job.core.log.XxlJobLogger;
- import org.springframework.stereotype.Component;
- /**
- * 任务 Handler 示例 (Bean 模式)
- *
- * 开发步骤:
- * 1, 继承 "IJobHandler":"com.xxl.job.core.handler.IJobHandler";
- * 2, 注册到 Spring 容器: 添加 "@Component" 注解, 被 Spring 容器扫描为 Bean 实例;
- * 3, 注册到执行器工厂: 添加 "@JobHandler(value=" 自定义 jobhandler 名称 ")" 注解, 注解 value 值对应的是调度中心新建任务的 JobHandler 属性的值.
- * 4, 执行日志: 需要通过 "XxlJobLogger.log" 打印执行日志;
- */
- @JobHandler(value="demoJobHandler")
- @Component
- public class JobHandlerDemo extends IJobHandler{
- @Override
- public ReturnT<String> execute(String s) throws Exception {
- XxlJobLogger.log("XXL-JOB, Hello World.");
- return SUCCESS;
- }
- }
- View Code
注意: 这里有个注解 @JobHandler(value="demoJobHandler"), 对于 value 的值, 我们会在下面进行相应配置.
7, 在调度中心中配置执行器
调度中心前面我们已经配置好了, 启动该配置中心, 进入 http://localhost:8080/xxl-job-admin 界面.
1, 配置执行器
点击 执行器管理 ----》新增执行器 ---》, 如下如下界面, 然后填充此表格, 点击保存即可.
下面是对这几个参数的介绍:
AppName: 是每个执行器集群的唯一标示 AppName, 执行器会周期性以 AppName 为对象进行自动注册. 可通过该配置自动发现注册成功的执行器, 供任务调度时使用;
名称: 执行器的名称, 因为 AppName 限制字母数字等组成, 可读性不强, 名称为了提高执行器的可读性;
排序: 执行器的排序, 系统中需要执行器的地方, 如任务新增, 将会按照该排序读取可用的执行器列表;
注册方式: 调度中心获取执行器地址的方式,
自动注册: 执行器自动进行执行器注册, 调度中心通过底层注册表可以动态发现执行器机器地址;
手动录入: 人工手动录入执行器的地址信息, 多地址逗号分隔, 供调度中心使用;
机器地址:"注册方式" 为 "手动录入" 时有效, 支持人工维护执行器的地址信息;
2, 创建任务
点击 任务管理 ---》新增任务 ---》
执行器: 任务的绑定的执行器, 任务触发调度时将会自动发现注册成功的执行器, 实现任务自动发现功能; 另一方面也可以方便的进行任务分组. 每个任务必须绑定一个执行器, 可在 "执行器管理" 进行设置.
任务描述: 任务的描述信息, 便于任务管理;
路由策略: 当执行器集群部署时, 提供丰富的路由策略, 包括;
FIRST(第一个): 固定选择第一个机器;
LAST(最后一个): 固定选择最后一个机器;
ROUND(轮询):;
RANDOM(随机): 随机选择在线的机器;
CONSISTENT_HASH(一致性 HASH): 每个任务按照 Hash 算法固定选择某一台机器, 且所有任务均匀散列在不同机器上.
LEAST_FREQUENTLY_USED(最不经常使用): 使用频率最低的机器优先被选举;
LEAST_RECENTLY_USED(最近最久未使用): 最久为使用的机器优先被选举;
FAILOVER(故障转移): 按照顺序依次进行心跳检测, 第一个心跳检测成功的机器选定为目标执行器并发起调度;
BUSYOVER(忙碌转移): 按照顺序依次进行空闲检测, 第一个空闲检测成功的机器选定为目标执行器并发起调度;
SHARDING_BROADCAST(分片广播): 广播触发对应集群中所有机器执行一次任务, 同时系统自动传递分片参数; 可根据分片参数开发分片任务;
Cron: 触发任务执行的 Cron 表达式;
运行模式:
BEAN 模式: 任务以 JobHandler 方式维护在执行器端; 需要结合 "JobHandler" 属性匹配执行器中任务;
GLUE 模式 (Java): 任务以源码方式维护在调度中心; 该模式的任务实际上是一段继承自 IJobHandler 的 Java 类代码并 "groovy" 源码方式维护, 它在执行器项目中运行, 可使用 @Resource/@Autowire 注入执行器里中的其他服务;
GLUE 模式 (Shell): 任务以源码方式维护在调度中心; 该模式的任务实际上是一段 "shell" 脚本;
GLUE 模式 (Python): 任务以源码方式维护在调度中心; 该模式的任务实际上是一段 "python" 脚本;
GLUE 模式 (PHP): 任务以源码方式维护在调度中心; 该模式的任务实际上是一段 "php" 脚本;
GLUE 模式 (Node.JS): 任务以源码方式维护在调度中心; 该模式的任务实际上是一段 "nodejs" 脚本;
GLUE 模式 (PowerShell): 任务以源码方式维护在调度中心; 该模式的任务实际上是一段 "PowerShell" 脚本;
JobHandler: 运行模式为 "BEAN 模式" 时生效, 对应执行器中新开发的 JobHandler 类 "@JobHandler" 注解自定义的 value 值;
阻塞处理策略: 调度过于密集执行器来不及处理时的处理策略;
单机串行 (默认): 调度请求进入单机执行器后, 调度请求进入 FIFO 队列并以串行方式运行;
丢弃后续调度: 调度请求进入单机执行器后, 发现执行器存在运行的调度任务, 本次请求将会被丢弃并标记为失败;
覆盖之前调度: 调度请求进入单机执行器后, 发现执行器存在运行的调度任务, 将会终止运行中的调度任务并清空队列, 然后运行本地调度任务;
子任务: 每个任务都拥有一个唯一的任务 ID(任务 ID 可以从任务列表获取), 当本任务执行结束并且执行成功时, 将会触发子任务 ID 所对应的任务的一次主动调度.
任务超时时间: 支持自定义任务超时时间, 任务运行超时将会主动中断任务;
失败重试次数; 支持自定义任务失败重试次数, 当任务失败时将会按照预设的失败重试次数主动进行重试;
报警邮件: 任务调度失败时邮件通知的邮箱地址, 支持配置多邮箱地址, 配置多个邮箱地址时用逗号分隔;
负责人: 任务的负责人;
执行参数: 任务执行所需的参数, 多个参数时用逗号分隔, 任务执行时将会把多个参数转换成数组传入;
8, 启动任务
配置完执行器以及任务, 我们只需要启动该任务, 便可以运行了.
启动之后, 我们查看日志:
我们上面配置任务时的 cron 表达式是每秒钟执行一次 (0/1 * * * * ? *):
打印日志如下:
注意: 在项目中, 只有通过 XxlJobLogger.log() 代码才能将日志打印到上面.
参考文档: https://www.cnblogs.com/xuxueli/p/5021979.html 这是 xxl-job 作者的博客地址.
http://www.xuxueli.com/xxl-job/# http://www.xuxueli.com/xxl-job/# 这是中文教程.
来源: https://www.cnblogs.com/ysocean/p/10541151.html