背景
很早之前接触了RxJava的工作流操作,感觉这种将简单业务流通过一个个操作符拆解开来,造成一条条条理清晰的function, 让人写起来直呼过瘾.其实这就是责任链模式的一种利用.
然而RxJava的性能切实是太强大了, 如果仅仅是应用它来解决这些业务流我感觉还是有些大材小用了.
之前也做过一段时间的利用性能优化, 其中当然就包含利用冷启动优化, 两头有波及过启动器的概念, 过后也查阅了一些现有的开源框架, 也应用过其中一些, 然而总感觉并不是很好用, 用起来不是很棘手.
作为一名资深Android开源框架卷王, 过后我脑海里就萌生一种想法, 为啥我不本人写一个工作流执行的框架呢?想到这, 我就抽出了我的一部分业余时间(女朋友都不陪了), 撸出了这个XTask框架, 自我感觉十分nice, 在这分享给大家.
简介
XTask是一个拓展性极强的Android工作执行框架。
可自在定义和组合工作来实现你想要的性能,尤其实用于解决简单的业务流程,可灵便增加前置工作或者调整执行程序。例如:利用的启动初始化流程。
我的项目地址
- github: https://github.com/xuexiangjys/XTask
- gitee: https://gitee.com/xuexiangjys/XTask
特色
- 反对6种线程类型形式执行工作。
- 反对工作链中各工作的执行线程调度和管制。
- 反对快捷工作创立,同时反对自定义工作。
- 反对串行和并行等组工作。
- 反对工作间数据共享。
- 反对自由组合工作执行。
- 反对工作链执行勾销。
- 反对勾销所有工作链和指定名称的工作链。
- 反对工作链调用程序记录和查问。
- 反对自定义工作执行的线程池。
设计思维
框架主体应用责任链的设计模式,辅以建造者模式、工厂模式、适配器模式、组合模式、外观模式以及代理模式来实现。
组成构造
- 工作链
ITaskChainEngine
:工作链执行引擎,负责兼顾调度各工作步骤。 - 工作步骤
ITaskStep
:负责具体任务逻辑解决。 - 数据存储仓库
IDataStore
:存放数据的仓库,次要用于保留工作参数中的数据。 - 工作参数
ITaskParam
:负责工作门路记录以及工作产生的参数治理。 - 工作执行后果
ITaskResult
:寄存工作最终执行的后果以及产生的数据。 - 工作组
IGroupTaskStep
:负责兼顾调度各子工作步骤。
点击查看框架UML设计图
日志一览
集成指南
增加Gradle依赖
1.先在我的项目根目录的 build.gradle
的 repositories
增加:
allprojects { repositories { ... maven { url "https://jitpack.io" } }}
2.而后在dependencies增加:
dependencies { ... // XTask implementation 'com.github.xuexiangjys:XTask:xtask-core:1.0.0'}
应用办法
XTask作为对外对立的API入口,所有罕用的办法都能从中找到。
关上调试模式
当须要定位问题,须要进行调试时,可关上调试模式,这样便可开启框架的日志。
XTask.debug(true);
XTask的API介绍
办法名 | 形容 |
---|---|
debug | 设置是否关上调试 |
setLogger | 自定义日志打印 |
setIsLogTaskRunThreadName | 设置是否打印工作执行所在的线程名,默认false |
getTaskChain | 获取工作链执行引擎 |
getTask | 获取简化的工作 |
getTaskBuilder | 获取简化工作的构建者 |
getConcurrentGroupTask | 获取并行任务组 |
getSerialGroupTask | 获取串行工作组 |
cancelTaskChain | 勾销指定工作链执行 |
postToMain | 执行工作到主线程 |
submit | 执行一般异步工作 |
emergentSubmit | 执行紧急异步工作 |
backgroundSubmit | 执行后盾异步工作 |
ioSubmit | 执行io耗时的异步工作 |
groupSubmit | 执行分组异步工作 |
如何执行一条工作链
上面是一整个残缺的例子:
// 1.创立一条工作链(必须)final TaskChainEngine engine = XTask.getTaskChain();// 2.设置工作链的初始化参数(可选)engine.setTaskParam(TaskParam.get("chainName", engine.getName()));TaskParam taskParam = TaskParam.get("param1", 100) .put("param2", true);// 3.创立多个工作,并向工作链中增加(必须)XTaskStep taskStep = XTask.getTask(new TaskCommand() { @Override public void run() { ITaskParam param = getTaskParam(); Log.e(TAG, getName() + " start, param1:" + param.get("param1") + ", chainName:" + param.get("chainName")); param.put("param1", 200); param.put("param3", "this is param3!"); }}, taskParam);engine.addTask(taskStep) .addTask(XTask.getTask(new TaskCommand() { @Override public void run() { ITaskParam param = getTaskParam(); Log.e(TAG, getName() + " start, param1:" + param.get("param1") + ", param3:" + param.get("param3")); param.put("param2", false); } }));// 4.设置工作链执行回调(可选)ICanceller canceller = engine.setTaskChainCallback(new TaskChainCallbackAdapter() { @Override public void onTaskChainCompleted(@NonNull ITaskChainEngine engine, @NonNull ITaskResult result) { Log.e(TAG, "task chain completed, thread:" + Thread.currentThread().getName()); Map<String, Object> data = result.getDataStore().getData(); for (Map.Entry<String, Object> entry : data.entrySet()) { Log.e(TAG, "key:" + entry.getKey() + ", value:" + entry.getValue()); } }// 5.工作链执行(必须)}).start();
1.创立一条工作链.(必须)
TaskChainEngine engine = XTask.getTaskChain();
2.设置工作链的初始化参数.(可选)
engine.setTaskParam(TaskParam.get("chainName", engine.getName()));
3.创立多个工作,并向工作链中增加.(必须)
// 设置工作初始化参数TaskParam taskParam = TaskParam.get("param1", 100) .put("param2", true);XTaskStep taskStep = XTask.getTask(new TaskCommand() { @Override public void run() { // ...执行工作 }}, taskParam);engine.addTask(taskStep) .addTask(XTask.getTask(new TaskCommand() { @Override public void run() { // ...执行工作 } }));
【留神】对于工作执行实现,须要留神以下两点:
- 如果工作执行胜利,就调用
notifyTaskSucceed
,工作执行失败,就调用notifyTaskFailed
。这里工作无论胜利还是失败,只有执行实现都须要调用notifyTaskXXX
告诉工作链该工作实现,否则工作将无奈失常执行。 TaskCommand
和SimpleTaskStep
默认提供了主动告诉执行后果的性能,然而AbstractTaskStep没有提供,须要手动告诉。
4.设置工作链执行回调.(可选)
调用setTaskChainCallback设置工作链执行回调。
engine.setTaskChainCallback(new TaskChainCallbackAdapter() { @Override public boolean isCallBackOnMainThread() { // 回调是否返回主线程, 默认是true return false; } @Override public void onTaskChainStart(@NonNull ITaskChainEngine engine) { Log.e(TAG, "task chain start"); } @Override public void onTaskChainCompleted(@NonNull ITaskChainEngine engine, @NonNull ITaskResult result) { Log.e(TAG, "task chain completed, thread:" + Thread.currentThread().getName()); } @Override public void onTaskChainError(@NonNull ITaskChainEngine engine, @NonNull ITaskResult result) { Log.e(TAG, "task chain error"); }})
5.工作链执行.(必须)
调用start执行工作链。
ICanceller canceller = engine.start();
工作创立
创立工作有两种形式:
- 通过XTask.getTask构建
- 继承
SimpleTaskStep
/AbstractTaskStep
实现工作的自定义
通过XTask创立
通过XTask.getTask, 传入对应的属性进行构建
属性名 | 形容 |
---|---|
name | 工作步骤名称 |
command | 工作执行内容 |
threadType | 线程执行类型 |
taskParam | 工作参数 |
taskHandler | 工作解决者 |
isAutoNotify | 是否主动告诉工作执行后果 |
XTaskStep taskStep = XTask.getTask(new TaskCommand() { @Override public void run() { // todo }}, ThreadType.ASYNC, taskParam);
通过继承创立
通过继承SimpleTaskStep
或者AbstractTaskStep
实现具体性能。
public class StepATask extends SimpleTaskStep { @Override public void doTask() throws Exception { // todo // 不须要手动告诉工作链工作实现 }}public class StepBTask extends AbstractTaskStep { @Override public void doTask() throws Exception { // todo // 需手动告诉工作链工作实现 notifyTaskSucceed(TaskResult.succeed()); } @Override public String getName() { return "StepATask"; }}
工作执行准则
每一个工作都是依靠于工作链进行流程管制。任何工作都须要遵循以下准则:
- 任何工作无论失败还是胜利,都须要调用
notifyTaskSucceed
或者notifyTaskFailed
去告诉工作链工作的实现状况。TaskCommand
和SimpleTaskStep
默认提供了主动告诉执行后果的性能。 - 一旦工作链中某个工作执行失败,整个链路都进行工作。
工作类型 | 工作执行阐明 |
---|---|
TaskCommand | 主动告诉执行后果。如需手动告诉,只需设置isAutoNotify 为false即可 |
SimpleTaskStep | 主动告诉执行后果。如需手动告诉,只需重写isAutoNotify 办法为false即可 |
AbstractTaskStep | 需手动告诉执行后果 |
TaskCommand手动告诉执行后果
在通过XTask.getTask传入TaskCommand构建Task的时候,设置isAutoNotify
为false即可手动告诉执行后果。
final TaskChainEngine engine = XTask.getTaskChain();for (int i = 0; i < 5; i++) { int finalI = i; engine.addTask(XTask.getTask(new TaskCommand() { @Override public void run() { try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } if (finalI == 2) { notifyTaskFailed(404, "工作执行失败!"); } else { notifyTaskSucceed(TaskResult.succeed()); } } }, false)); // 设置手动告诉执行后果}engine.start();
SimpleTaskStep手动告诉执行后果
重写SimpleTaskStep
的isAutoNotify
办法为false即可手动告诉执行后果。
public class StepATask extends SimpleTaskStep { @Override public void doTask() throws Exception { // todo // 手动告诉工作链工作实现 notifyTaskSucceed(); } @Override protected boolean isAutoNotify() { return false; }}
参数传递
- 任何TaskStep咱们都能够通过
getTaskParam
获取工作参数和工作执行后果ITaskParam
。 - 上一个TaskStep保留解决过的工作参数会主动带入到下一个TaskStep中去,因而最初一个TaskStep领有之前所有工作的参数数据。
XTask.getTask(new TaskCommand() { @Override public void run() { ITaskParam param = getTaskParam(); Log.e(TAG, getName() + " start, param1:" + param.get("param1") + ", param3:" + param.get("param3")); param.put("param2", false); }})
线程管制
设置工作的threadType类型,即可实现对工作运行线程的管制。目前反对6种线程解决形式。
类型 | 形容 | 线程池形成 |
---|---|---|
MAIN | 主线程(UI线程) | / |
ASYNC | 异步线程(开子线程,一般线程池) | 外围线程数和最大线程为CPU数,0s keepTime,LinkedBlockingQueue(128),线程优先级5 |
ASYNC_IO | 异步线程(开子线程,io线程池) | 外围线程数和最大线程为(2*CPU数+1),30s keepTime,LinkedBlockingQueue(128),线程优先级5 |
ASYNC_EMERGENT | 异步线程(开子线程,紧急线程池) | 外围线程数为2,最大线程为∞,60s keepTime,SynchronousQueue(不阻塞),线程优先级10 |
ASYNC_BACKGROUND | 异步线程(开子线程,优先级较低线程池) | 外围线程数和最大线程为2,0s keepTime,LinkedBlockingQueue(128),线程优先级1 |
SYNC | 同步线程(间接执行) | / |
// 1.结构时传入线程XTaskStep taskStep = XTask.getTask(new SimpleTaskCommand(1000), ThreadType.ASYNC_EMERGENT);// 2.设置线程的办法taskStep.setThreadType(ThreadType.ASYNC_IO);
工作组
目前共有串行工作组(SerialGroupTaskStep)和并行任务组(ConcurrentGroupTaskStep)
串行工作组
串行工作组是按程序顺次执行,和工作链的解决形式相似。应用XTask.getSerialGroupTask获取。
final TaskChainEngine engine = XTask.getTaskChain();SerialGroupTaskStep group1 = XTask.getSerialGroupTask("group1");for (int i = 0; i < 5; i++) { group1.addTask(XTask.getTask(new SimpleTaskCommand(500)));}SerialGroupTaskStep group2 = XTask.getSerialGroupTask("group2");for (int i = 0; i < 5; i++) { group2.addTask(XTask.getTask(new SimpleTaskCommand(1000)));}ICanceller canceller = engine.addTask(group1) .addTask(group2) .setTaskChainCallback(new TaskChainCallbackAdapter() { @Override public void onTaskChainCompleted(@NonNull ITaskChainEngine engine, @NonNull ITaskResult result) { Log.e(TAG, "task chain completed, path:" + result.getPath()); } }) .start();addCanceller(canceller);
并行任务组
并行任务组是组内所有工作同时执行,待所有工作都实现后才视为工作组实现。应用XTask.getConcurrentGroupTask获取。
final TaskChainEngine engine = XTask.getTaskChain();ConcurrentGroupTaskStep group1 = XTask.getConcurrentGroupTask("group1");for (int i = 0; i < 5; i++) { group1.addTask(XTask.getTask(new SimpleTaskCommand(100 * (i + 1))));}ConcurrentGroupTaskStep group2 = XTask.getConcurrentGroupTask("group2");for (int i = 0; i < 5; i++) { group2.addTask(XTask.getTask(new SimpleTaskCommand(200 * (i + 1))));}ICanceller canceller = engine.addTask(group1) .addTask(group2) .setTaskChainCallback(new TaskChainCallbackAdapter() { @Override public void onTaskChainCompleted(@NonNull ITaskChainEngine engine, @NonNull ITaskResult result) { Log.e(TAG, "task chain completed, path:" + result.getPath()); } }) .start();addCanceller(canceller);
最初
如果你感觉这个我的项目对你有所帮忙, 你能够点击star进行珍藏或者将其分享进来, 让更多的人晓得这个我的项目!
我是xuexiangjys,一枚酷爱学习,喜好编程,致力于Android架构钻研以及开源我的项目教训分享的技术up主。获取更多资讯,欢送微信搜寻公众号:【我的Android开源之旅】