XXL-Job【一、简介】

XXL-JOB 完整版详解:调度原理 + 核心架构 + 内置工具类 + 部署集成 + 控制台配置 + 生产实践

一、XXL-JOB 整体概述

XXL-JOB 是轻量级分布式任务调度框架,核心架构:调度中心(Admin) + 执行器(Executor),具备去中心化注册、动态调度、故障转移、分片广播、日志溯源、失败告警等能力,开箱即用、无侵入、适配 SpringBoot 微服务。

核心优势:

  1. 支持 CRON 定时、固定速率、一次性任务;
  2. 执行器自动注册发现,集群负载均衡;
  3. 调度中心集群高可用,数据库锁防重复调度;
  4. 内置日志、分片、任务终止、参数获取等工具类;
  5. 支持任务阻塞策略、失败重试、超时控制、钉钉/邮件告警。

二、XXL-JOB 核心调度原理

2.1 核心角色分工

角色 职责 部署特点
调度中心 xxl-job-admin 任务管理、CRON 解析、任务触发、日志存储、告警、执行器注册监控 集群部署,共享MySQL,无业务逻辑
执行器 Executor 嵌入业务项目,接收调度指令、执行具体业务任务、上报心跳与执行结果 多实例集群,同AppName自动负载

2.2 注册与心跳机制

  1. 执行器启动后,主动向调度中心注册自身信息(AppName、IP、端口);
  2. 执行器每30s上报一次心跳;
  3. 调度中心每60s扫描注册表,90s 无心跳判定执行器离线并剔除;
  4. 通信基于 Netty HTTP,默认执行器端口 9999

2.3 核心调度执行流程

  1. 定时扫描:调度中心后台线程每秒轮询任务表,筛选待触发任务;
  2. 时间轮预加载:采用秒级时间轮缓存未来5s待执行任务,减少DB查询压力;
  3. 集群防重:调度中心多节点通过 MySQL 悲观锁 select ... for update,保证同一任务只被一个节点触发;
  4. 路由选择:根据配置路由策略(轮询、随机、一致性哈希、分片广播等)选中一台在线执行器;
  5. 远程调用:调度中心通过 HTTP 下发执行指令到目标执行器;
  6. 任务执行:执行器匹配 @XxlJob 标记的任务处理器,放入内置线程池异步执行;
  7. 结果回调:任务执行完毕,执行器异步回调执行状态、日志给调度中心;
  8. 日志持久化&告警:调度中心记录执行日志,失败则触发重试、钉钉/邮件告警。

2.4 高可用核心机制

  1. 调度中心HA:多节点集群 + 同库悲观锁,避免任务重复调度;
  2. 执行器HA:同AppName多实例,节点宕机自动路由到存活节点;
  3. 任务容错:支持失败重试、超时终止、三种阻塞策略(单机串行、丢弃后续调度、覆盖之前调度)。

三、XXL-JOB 内置核心工具类完整使用示例

依赖导入后,直接在任务方法中使用以下官方工具类。

3.1 日志工具:XxlJobLogger

日志可在调度中心控制台在线查看,替代 System.out

import com.xxl.job.core.log.XxlJobLogger;
import com.xxl.job.core.handler.annotation.XxlJob;
import com.xxl.job.core.biz.model.ReturnT;
import org.springframework.stereotype.Component;

@Component
public class DemoTask {

    @XxlJob("loggerDemoTask")
    public ReturnT<String> loggerDemoTask(String taskParam) {
        // 普通日志
        XxlJobLogger.log("任务开始执行");
        // 带参数占位打印
        XxlJobLogger.log("接收任务参数:{}", taskParam);
        // 异常堆栈打印
        try {
            int i = 1 / 0;
        } catch (Exception e) {
            XxlJobLogger.log(e, "业务执行异常");
        }
        return ReturnT.SUCCESS;
    }
}

3.2 任务上下文工具:XxlJobHelper

3.2.1 获取分片信息(大数据分片并行必备)

@XxlJob("shardTask")
public ReturnT<String> shardTask(String param) {
    // 当前分片索引:从0开始
    int shardIndex = XxlJobHelper.getShardIndex();
    // 总分片数量(等于在线执行器节点数)
    int shardTotal = XxlJobHelper.getShardTotal();

    XxlJobLogger.log("分片执行:当前{}/{}", shardIndex, shardTotal);
    // 业务场景:根据id取模分片  id % shardTotal == shardIndex
    return ReturnT.SUCCESS;
}

3.2.2 任务终止判断

手动停止任务时,可感知并优雅退出

@XxlJob("stopCheckTask")
public ReturnT<String> stopCheckTask(String param) {
    for (int i = 0; i < 100; i++) {
        // 判断是否被手动终止
        if (XxlJobHelper.isStopped()) {
            XxlJobLogger.log("任务被手动终止,退出执行");
            return ReturnT.FAIL;
        }
        // 模拟业务处理
        XxlJobLogger.log("执行进度:{}", i);
    }
    return ReturnT.SUCCESS;
}

3.2.3 获取任务元信息

// 当前任务ID
long jobId = XxlJobHelper.getJobId();
// 调度触发时间
Date triggerTime = XxlJobHelper.getTriggerTime();
// 获取任务自定义参数
String taskParams = XxlJobHelper.getJobParam();

3.3 任务返回值规范

// 执行成功
return ReturnT.SUCCESS;

// 执行失败,触发重试+告警
return ReturnT.FAIL;

// 失败并返回自定义描述
return new ReturnT<>(ReturnT.FAIL_CODE, "数据同步失败:数据库连接异常");

四、完整部署与 SpringBoot 集成实战

4.1 环境依赖

  • JDK 1.8+
  • MySQL 5.7 / 8.0
  • SpringBoot 2.x / 3.x
  • XXL-JOB 版本:2.4.0(稳定通用版)

4.2 初始化数据库

  1. 下载 XXL-JOB 源码:https://github.com/xuxueli/xxl-job
  2. 执行脚本:xxl-job/doc/db/tables_xxl_job.sql
  3. 自动创建 8 张系统表,核心表:
    • xxl_job_info:任务配置表
    • xxl_job_registry:执行器注册表
    • xxl_job_log:任务执行日志表

4.3 部署调度中心 xxl-job-admin

4.3.1 修改配置 application.properties

# 服务端口
server.port=8080
server.servlet.context-path=/xxl-job-admin

# 数据源配置
spring.datasource.url=jdbc:mysql://127.0.0.1:3306/xxl_job?useUnicode=true&characterEncoding=utf8&serverTimezone=Asia/Shanghai&allowMultiQueries=true
spring.datasource.username=root
spring.datasource.password=123456
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver

# 通信令牌(执行器必须和这里一致)
xxl.job.accessToken=default_token

4.3.2 启动访问

  • 启动 XxlJobAdminApplication
  • 访问地址:http://localhost:8080/xxl-job-admin
  • 默认账号密码:admin / 123456

4.4 SpringBoot 项目集成执行器

4.4.1 Maven 依赖

<dependency>
    <groupId>com.xuxueli</groupId>
    <artifactId>xxl-job-core</artifactId>
    <version>2.4.0</version>
</dependency>

4.4.2 配置文件 application.yml

xxl:
  job:
    # 调度中心地址,集群用逗号分隔
    admin:
      addresses: http://127.0.0.1:8080/xxl-job-admin
    # 执行器配置
    executor:
      appname: xxl-job-business-demo
      port: 9999
      logpath: /data/xxl-job/logs
      logretentiondays: 30
    # 通信令牌
    access-token: default_token

4.4.3 执行器配置类

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

@Configuration
public class XxlJobConfig {

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

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

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

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

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

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

    @Bean
    public XxlJobSpringExecutor xxlJobSpringExecutor() {
        XxlJobSpringExecutor executor = new XxlJobSpringExecutor();
        executor.setAdminAddresses(adminAddresses);
        executor.setAppname(appName);
        executor.setPort(port);
        executor.setLogPath(logPath);
        executor.setLogRetentionDays(logRetentionDays);
        executor.setAccessToken(accessToken);
        return executor;
    }
}

4.4.4 编写业务任务

@Component
public class BusinessTask {

    @XxlJob("cronTaskHandler")
    public ReturnT<String> cronTaskHandler(String param) {
        XxlJobLogger.log("CRON定时任务执行,参数:{}", param);
        // 自定义业务逻辑
        return ReturnT.SUCCESS;
    }
}

五、调度中心控制台完整配置步骤

5.1 新增执行器

执行器管理 → 新增

  • 执行器AppName:xxl-job-business-demo(和配置文件一致)
  • 名称:业务演示执行器
  • 注册方式:自动注册
  • 保存后可看到在线执行器节点信息

5.2 新增定时任务

任务管理 → 新增

  • 执行器:选择上面创建的执行器
  • 任务描述:测试定时任务
  • 调度类型:CRON
  • Cron表达式:*/5 * * * * ? 每5秒执行一次
  • 路由策略:轮询
  • JobHandler:cronTaskHandler(和 @XxlJob 注解名称完全一致)
  • 任务参数:自定义传入参数
  • 阻塞策略:单机串行
  • 失败重试次数:3次
  • 保存后启动任务

5.3 查看执行日志

任务列表 → 操作 → 日志,可查看执行记录、自定义日志、异常堆栈。


六、集群部署与生产最佳实践

6.1 调度中心集群

  1. 多节点部署 xxl-job-admin连接同一个MySQL
  2. 前端配置 Nginx 负载均衡,所有执行器配置 Nginx 地址;
  3. 依靠数据库悲观锁天然实现任务互斥,无需额外改造。

6.2 执行器集群

  1. 多个业务实例配置相同 AppName
  2. 调度中心自动感知,按路由策略负载均衡;
  3. 某节点宕机自动剔除,任务路由到其他节点。

6.3 生产规范

  1. 任务必须做幂等性,防止重试导致数据重复;
  2. 长耗时任务拆分,避免单任务阻塞线程池;
  3. 统一使用 XxlJobLogger 打印日志,方便线上排查;
  4. 大数据量同步优先使用分片广播
  5. 配置任务失败钉钉/企业微信/邮件告警
  6. 合理设置任务超时时间、阻塞策略、重试次数。

七、常见问题排查

  1. 执行器无法注册
    • 检查调度中心地址、accessToken 是否一致;
    • 服务器防火墙放行 8080、9999 端口;
  2. 任务配置正确但不执行
    • JobHandler 名称和注解不一致;
    • 任务未手动启动
    • CRON 表达式格式错误;
  3. 任务重复执行
    • 调度中心集群未共用同一个数据库;
    • 数据库锁机制失效;
  4. 日志看不到自定义打印
    • 必须使用 XxlJobLogger,不能用原生日志框架。

posted @ 2026-05-12 12:53  蓝迷梦  阅读(25)  评论(0)    收藏  举报