TBSchedule原理与实践

原文地址:http://blog.csdn.net/taosir_zhang/article/details/50728362

淘宝开源定时任务调度框架

1. 淘宝代码库TBSchedule(使用说明附源码下载)

下载TBSchedule源码http://code.taobao.org/p/tbschedule/wiki/index 
内容包括两部分:TBSchedule开发依赖包tbschedule、调度控制台ScheduleConsole.war(后续详解)

2. 引入源码Demo开发示例

源码可作为普通工程依赖入任务工程,也可将其打包成jar并引入依赖,此处下载版本为3.2.2.2

PS:若打包失败,请检查编译插件版本及jdk编译版本。

maven依赖

<dependency>
    <groupId>com.taobao.pamirs.schedule</groupId>
    <artifactId>tbschedule</artifactId>
    <version>3.3.3.2</version>
</dependency>

调度任务实现IScheduleTaskDealSingle,并实现selectTasksexecute方法,详细示例:

Component("iScheduleTaskDealSingleTest")
public class IScheduleTaskDealSingleTest implements IScheduleTaskDealSingle<TaskModel> {

    private static final Logger LOG = LoggerFactory.getLogger(IScheduleTaskDealSingleTest.class);

    @Override
    public Comparator<TaskModel> getComparator() {
        return null;
    }

    @Override
    public List<TaskModel> selectTasks(String taskParameter, String ownSign, int taskQueueNum,
            List<TaskItemDefine> taskItemList, int eachFetchDataNum) throws Exception {

        LOG.info("IScheduleTaskDealSingleTest配置的参数,taskParameter:{},ownSina:{},taskQueueNum:{},taskItemList:{}, eachFetchDataNum:{}", taskParameter, ownSign, taskQueueNum, taskItemList, eachFetchDataNum);

        LOG.info("IScheduleTaskDealSingleTest选择任务列表开始啦..........");
        List<TaskModel> models = new ArrayList<TaskModel>();
        models.add(new TaskModel(String.valueOf(System.currentTimeMillis()), "taosirTest1"));
        models.add(new TaskModel(String.valueOf(System.currentTimeMillis()), "taosirTest2"));

        return models;

    }

    @Override
    public boolean execute(TaskModel model, String ownSign) throws Exception {

        LOG.info("IScheduleTaskDealSingleTest执行开始啦.........." + new Date());
        System.out.println(model);
        return true;

    }

}

其中selectTasks方法获取需要处理的列表(用集合装着),循环集合中的元素并调用execute方法执行。子计时任务启动,会直到获取不到数据后才停止等待下一个子计时开始,参数后面详细介绍。

将调度任务注册到zookeeper中心,spring中引入如下配置:

<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd">
<beans default-autowire="byName">
    <bean id="scheduleManagerFactory"
        class="com.taobao.pamirs.schedule.strategy.TBScheduleManagerFactory"
        init-method="init">
        <property name="zkConfig">
            <map>
                <entry key="zkConnectString" value="${schedule.zookeeper.address}" />
                <entry key="rootPath" value="${schedule.root.catalog}" />
                <entry key="zkSessionTimeout" value="${schedule.timeout}" />
                <entry key="userName" value="${schedule.username}" />
                <entry key="password" value="${schedule.password}" />
                <entry key="isCheckParentPath" value="true" />
            </map>
        </property>
    </bean>
</beans>

环境属性配置文件增加如下配置:

#注册中心地址
schedule.zookeeper.address=172.26.50.86:2181
#定时任务根目录,任意指定,调度控制台配置时对应
schedule.root.catalog=/tbschedule/example
#账户,任意指定,调度控制台配置时对应
schedule.username=username
#密码,任意指定,调度控制台配置时对应
schedule.password=password
#超时配置
schedule.timeout=60000

启动容器,iScheduleTaskDealSingleTest就完成了到zookeeper中心的注册。

说明:tbschdule提供了IScheduleTaskDealSingleIScheduleTaskDealMulti两个接口,个人在测试中发现两者除了execute方法上参数不同外,功能上并没有别的不同,只是语义上的区分,在处理模式为SLEEPgetComparator没有用。

3. 控制台配置任务调度

将控制台ScheduleConsole.war部署到tomcat容器。

PS:我通过ant运行源码中的build.xml重新构建控制台,部署运行失败,报找不到ConsoleManager类,目前没有查找到原因,这种情况下:

使用方式一,直接用下载包中的控制台部署即可。 
使用方式二,新建一web工程,把代码拷贝过去,打成war包,这灵活,还可以自定义修改,源文件不支持中文,可将编码改成utf-8支持。

向注册中心注册配置(跟任务注册用同一根目录,官方wiki图示)

http://{server}:{port}/ScheduleConsole/schedule/config.jsp

配置调度任务(官方wiki图示)

http://{server}:{port}/ScheduleConsole/schedule/index.jsp

4. selectTasks方法参数说明

taskParameter:对应控制台自定义参数,可自定义传入做逻辑上的操作

taskQueueNum:对应控制台任务项数量

taskItemList:集合中TaskItemDefine的id值对应任务项值,多线程处理时,根据任务项协调数据一致性和完整性

eachFetchDataNum:对应控制台每次获取数量,由于子计时单元开始后,会不断的去取数据进行处理,直到取不到数据子计时才停止,等待下一个子计时开始。可以限制每次取数,防止一次性数据记录过大,内存不足。

ownSign:环境参数,一般没什么用

5. 创建调度策略参数说明

策略名称:策略标示,可任意填写

任务类型:一般保持默认Schedule

任务名称:对应任务栏被调度任务名称

任务参数:一般不用,保持默认

单JVM最大线程组数量:单个JVM允许开启的线程数

最大线程组数量:多处理机情况下的线程总数限制(总线程为2,任务项线程为4是没有意义的)

IP地址127.0.0.1或者localhost会在所有机器上运行,注意多处理机若没有根据任务子项划分数据处理,会导致多处理机重复处理数据,谨慎配置

创建示例,官方wiki上有图示,上面主要各参数的复合含义。

6. 创建任务参数说明

任务名称:策略调度的标示,一旦创建保存,不可更改

任务处理的SpringBean:注册到spring的任务bean,如iScheduleTaskDealSingleTest

心跳频率/假定服务死亡时间/处理模式/没有数据时休眠时长/执行结束时间:一般保持默认即可

线程数:处理该任务的线程数,在没有划分多任务项的情况下,多线程是没有意义的,且线程数量大于任务项也是没有意义的(线程数小于等于任务项),注意如果开启多线程,必须对数据做任务项过滤

单线程组最大任务项:配置单JVM处理的最大任务项数量,多任务项情况下,可按需限制,一般默认,多执行机会均衡分配

每次获取数量:子计时单元开始,线程会不断的去获取数据(每次获取的限制)并处理数据,直到获取不到数据子计时才结束(方法内不用就可以随意配置)

每次执行数量://还没测试过(可能是将获取的数量拆分多次执行)

每次处理完休眠时间:子计时单元开始,只要有数据,就会不停的获取不停的处理,这个时间设置后,子计时单元开始每次获取执行后,不管还有没有待数据,都先歇会儿再获取处理

自定义参数:可自定义控制任务逻辑操作

任务项:这项很重要,在多线程情况下,划分任务项是有意义的,但是要注意必须通过任务项参数,协调待处理数据,否则多线程会重复处理

创建示例,官方wiki上有图示,上面主要各参数的复合含义。

7. 多处理机多线程多调度机可靠性保障

网络部署架构

这里写图片描述

1)调度机的高可用有保障,多调度机向注册中心注册后,共享调度任务,且同一调度任务仅由一台调度机执行调度,当前调度机异常宕机后,其余的调度机会接上。

2)执行机的高可用有保障,多执行机向注册中心注册后,配置执行机单线程(多机总线程为1)执行任务,调度机会随机启动一台执行机执行,当前执行异常机宕机后,调度机会会新调度一台执行机。

3)执行机的并行高效保障,配置执行机多线程且划分多任务子项后,各任务子项均衡分配到所有执行机,各执行机均执行,多线程数据一致性协调由任务项参数区分。

4)弹性扩展失效转移保障,运行中的执行机宕机,或新增执行机,调度机将在下次任务执行前重新分配任务项,不影响正常执行机任务(崩溃的执行机当前任务处理失效);运行中的调度机宕机或动态新增调度机,不影响执行机当前任务,调度机宕机后动态切换。

8. 几款定时任务框架对比

1)QuartzJava事实上的定时任务标准。但Quartz关注点在于定时任务而非数据,并无一套根据数据处理而定制化的流程。虽然Quartz可以基于数据库实现作业的高可用,但缺少分布式并行执行作业的功能

2)CrontabLinux系统级的定时任务执行器,缺乏分布式和集中管理功能

3)elastic-job:当当网最近开源项目,功能跟TBSchedule几乎一样(批斗TBSchedule文档缺失严重),一台服务器只能开启一个任务实例,基于Ip不基于IpPort,单机难调试集群功能

4)TBSchedule:淘宝早期开源,稳定性可以保证,京东金融集团当前使用定时任务框架。

9. TBSchedule特性【摘】

1)TBSchedule的目的是让一种批量任务或者不断变化的任务,能够被动态的分配到多个主机的JVM中,不同的线程组中并行执行。所有的任务能够被不重复,不遗漏的快速处理。

2)调度的Manager可以动态的随意增加和停止。

3)可以通过JMX控制调度服务的创建和停止。

4)可以指定调度的时间区间。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值