优雅停机:调度中心停机,检测时间轮非空时主动等待调度完成;客户端停机,检测存在运行中任务时,停止接收新任务并主动等待任务执行完成;

3.3.2-release
xuxueli 4 weeks ago
parent ff4248c743
commit 9f33d7fb7a

@ -59,6 +59,7 @@ XXL-JOB是一个分布式任务调度平台其核心设计目标是开发迅
- 36、权限控制执行器维度进行权限控制管理员拥有全量权限普通用户需要分配执行器权限后才允许相关操作
- 37、AI任务原生提供AI执行器并内置多个AI任务Handler与spring-ai、ollama、dify等集成打通支持快速开发AI类任务。
- 38、审计日志记录任务操作敏感信息用于系统监控、审计和安全分析可快速追溯异常行为以及定位排查问题。
- 39、优雅停机调度中心停机检测时间轮非空时主动等待调度完成客户端停机检测存在运行中任务时停止接收新任务并主动等待任务执行完成
### 1.4 发展
@ -1824,6 +1825,10 @@ docker compose up -d
// 其他如需调整环境配置如Mysql密码、端口等可以在docker-compose.yml中修改另外如果需要修改Mysql数据持久化目录可以通过 MYSQL_PATH 变量在启动时快速设置;
MYSQL_PATH={自定义数据库持久化目录} docker compose up -d
```
### 5.24 优雅停机
针对任务调度场景,优雅停机包括调度中心与执行器两部分:
- 调度中心优雅停机:调度中心停机时,如果检测到时间轮非空则主动等待等待一段时间,等待调度处理完成;否则立即停机;
- 执行器优雅停机:执行器停机时,如果检测到存在运行中任务,在停止接收新任务后会主动等待一段时间,等待任务执行完成;否则立即停机;
## 六、调度中心/执行器 OpenApi
@ -2748,8 +2753,7 @@ public void execute() {
- 2、【优化】调度线程事务提交逻辑调整避免边界条件下线程异常退出增强健壮性
- 3、【优化】调度日志列表排序逻辑优化提升易读性
- 4、【优化】表格交互优化优化分页显示配置禁用分页循环多选行操作优化/默认单选;
- 5、【ING】优雅停机服务端停机检测时间轮非空sleep 5s
- 客户端停机检测任务运行中server停止后sleep5s
- 5、【优化】优雅停机调度中心停机检测时间轮非空时主动等待调度完成客户端停机检测存在运行中任务时停止接收新任务并主动等待任务执行完成
- 6、【TODO】任务调度触发后分批批量更新提升调度性能

@ -22,6 +22,7 @@ import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.TimeUnit;
/**
* Created by xuxueli on 2016/3/2 21:14.
@ -29,6 +30,11 @@ import java.util.concurrent.ConcurrentMap;
public class XxlJobExecutor {
private static final Logger logger = LoggerFactory.getLogger(XxlJobExecutor.class);
/*
* elegant shutdown wait seconds
*/
private static final long ELEGANT_SHUTDOWN_WAITING_SECONDS = 5;
// ---------------------- field ----------------------
private String adminAddresses;
private String accessToken;
@ -89,22 +95,31 @@ public class XxlJobExecutor {
initAdminBizList(adminAddresses, accessToken, timeout);
// init JobLogFileCleanThread
// 1、init JobLogFileCleanThread
JobLogFileCleanThread.getInstance().start(logRetentionDays);
// init TriggerCallbackThread
// 2、init TriggerCallbackThread
TriggerCallbackThread.getInstance().start();
// init executor-server
// 3、init executor-server
initEmbedServer(address, ip, port, appname, accessToken);
}
public void destroy(){
// destroy executor-server
// 1、destroy executor-server
stopEmbedServer();
// destroy jobThreadRepository
if (!jobThreadRepository.isEmpty()) {
// 1.1、elegant shutdown wait job finish
try {
TimeUnit.SECONDS.sleep(ELEGANT_SHUTDOWN_WAITING_SECONDS);
} catch (Throwable e) {
logger.error(e.getMessage(), e);
}
// 1.2、interupt all job-thread
for (Map.Entry<Integer, JobThread> item: jobThreadRepository.entrySet()) {
JobThread oldJobThread = removeJobThread(item.getKey(), "web container destroy and kill the job.");
// wait for job thread push result to callback queue
@ -121,10 +136,10 @@ public class XxlJobExecutor {
jobHandlerRepository.clear();
// destroy JobLogFileCleanThread
// 2、destroy JobLogFileCleanThread
JobLogFileCleanThread.getInstance().toStop();
// destroy TriggerCallbackThread
// 3、destroy TriggerCallbackThread
TriggerCallbackThread.getInstance().toStop();
}

Loading…
Cancel
Save