作者:yummyLau
背景
一年前多,想找一个适合项目的 Android 启动任务框架时,找到了 alpha 。 alpha 是一个阿里巴巴开源的,基于PERT图构建的Android异步启动框架,协助应用启动时正确执行依赖任务。集成了之后发现满足不了项目的应用场景,当时并没有很好的解决方法,迫于项目需求当晚就 clone 下了源码研究了实现,略感失落,但也找到了优化的方向。
alpha 的缺陷
- 启动节点粒度不够细
alpha 封装了 Task 类用于表示一个异步任务, 衍生出Project 及 AnchorTask 用于处理多个 task 对象构成的图结构。其外层业务只需要继承 Task 或者同个构建 Project 来编写业务依赖逻辑,理想的结构应该如下
但是如果你添加 Task 启动的时候,会收到 xxxTask cannot be cast to com.alibaba.android.alpha.Project。 从源码层上看确实不能从一个 task 启动,缺乏灵活性。
2.无法满足同异步初始化依赖并阻塞 Application#onCreate
alpha 定位为异步启动框架。在执行启动任务时判断其是否是主线程执行,如果是则通过 handler#post 发送出去排队处理, 否则交给线程池处理。任务处理完成之后通知依赖该任务的任务进行依赖检查, 此时若依赖其的所有依赖都已完成,则启动该任务。
定义一个任务 T,其启动任务时刻为 tTStart,结束任务时刻为 tTEnd。若存在以下依赖任务,
D(异步)-> C(异步) ->B (同步)->A(同步)
则 alpha 中恒满足 tAStart < tAEnd < tBStart < tBEnd < tCStart < tCEnd < tDStart < tDEnd。
由于同步任务时通过队列排队处理,任务的执行并不是与代码块的上下文严格同步,当 Application#onCreate() 中要求严格的代码执行同步时,如
则后置代码块会优先被执行。当tCode 为代码块执行时刻时,恒满足 tCode < txStart (x = {A,B,C,D})
尽管 alpha 中提供 AlphaManager#waitUntilFinish 用于阻塞执行线程,但是存在很大缺陷:
假如在UI线程等待,则会造成死锁。其原因在于当前执行代码处等待解锁,而只有等到所有在主线程执行的 task 执行完才可能解锁,而 task 被 post 到消息队列里面,只有当解锁之后才能执行到消息队列的 task。
3.缺乏任务执行同步支持,同异步混合链支持及调度优化
很多应用都会在 application#onCreate 前保证某些初