组件化开发过程当中,随着组件愈来愈多,组件的以前的交互就会变得很是的复杂,此时组件间通讯变得尤为的重要,ServicePool就是为组件化而生,用最简单的方式进行组件间通讯。使用依赖注入,按需灵活注入组件。同时支持组件热插拔,达到组件即插即用的效果。可配置组件生命周期,作到组件按需建立和及时回收,充分利用懒加载的思想,有效解决组件初始化耗时致使的app启动速度问题。点击进入 项目地址java
ServicePool包含有 Activity路由, 组件路由等等最经常使用的组件化能力。除此以外,组件化开发过程当中有没有遇到过想使用某个已有的类,好比一个工具类的时候,发现这个工具类在当前类的上层,没法直接依赖和引用,而修改这个工具类的层级又会牵一发而动全身的问题? 有没有想要一个差别响应的能力,在不一样的组件中或者环境下,有着不一样的响应方式?有没有想要一个自适应场景的能力,自动适应当前环境(好比Java仍是Android环境,好比Debug环境仍是Release环境等等),从而使用最合适的功能。又有没有想过如何让组件作到像USB接口同样插上就能直接使用,拔掉也不影响主体功能的即插即用的效果。等等...。 下面就来具体介绍一下这个组件化神器——ServicePool!git
如上图所示:github
/**
* 服务池pool中
*
* IA.java
*/
public interface IA {
void aName();
}
/**
* 服务池pool
*
* IB.java
*/
public interface IB {
void bName();
}
复制代码
/** * 组件A * * AService.java */ @Service public class AService implements IA { @Override public String aName() { return "A Service"; } } 复制代码
/** * 组件B * * BService.java */ @Service public class BService implements IB { @Override public String bName() { return "B Service"; } } 复制代码
组件A中执行: IB b = ServicePool.getService(IB.class); System.out.println("I'm A Service, I can get " + b.bName()); 输出: I'm A Service, I can get B Service 组件B中执行: IA a = ServicePool.getService(IA.class); System.out.println("I'm B Service, I can get " + a.aName()); 输出: I'm B Service, I can get A Service 复制代码
因为全部示例涉及到依赖注入,这里提早对ServicePool的依赖注入作个说明。和其余注入框架不一样,ServicePool的注入方式很简单,只有一种注入方式就是直接经过Class注入。数组
@Service public class AImpl implements IA { @Override public String aName() { return "A Impl" } } 复制代码
ServicePool就是一个基于Class注入容器。最后经过ServicePool.getService(IA.class)方法注入对象, 也能够经过@Service标记成员变量的方式注入,这两个方法等价。缓存
public class MainActivity extends AppcompatActivity {
/**
* 等价于
* IA = ServicePool.getService(IA.class);
*/
@Service
private IA a;
@Override
public void onCreate(Bundle savedInstanceState) {
System.out.println(a.getName()); //输出 A Service
}
}
复制代码
ServicePool注入对象时,会根据Service配置的生命周期类型(scope)和优先级来决定当前是建立仍是直接返回缓存对象。bash
若是IA有多个实现,如上图所示,ServicePool会比较每一个实现优先级,来决定最终返回IA的哪一个实现微信
/**
* 服务池pool中
*
* IPriorityService.java
*/
public interface IPriorityService {
int getPriority();
}
复制代码
/** * 组件A中 * * PriorityService1.java * PriorityService2.java */ @Service(priority = 1) public class PriorityService1 implements IPriorityService { @Override public int getPriority() { return 1; } } @Service(priority = 2) public class PriorityService2 implements IPriorityService { @Override public int getPriority() { return 2; } } 复制代码
组件B中执行: IPriorityService priorityService = ServicePool.getService(IPriorityService.class); System.out.println("priority is " + priorityService.getPriority()); priorityService = ServicePool.getService(PriorityService1.class); System.out.println("priority is " + priorityService.getPriority()); priorityService = ServicePool.getService(PriorityService2.class); System.out.println("priority is " + priorityService.getPriority()); 输出: priority is 2 priority is 1 priority is 2 复制代码
每一个由ServicePool建立的service对象都有各自生命周期,service对象的生命周期由ServicePool管理, 并由@Service注解配置生命周期类型。markdown
组件A中
/**
*
* OnceService.java
*/
@Service(scope = IService.Scope.once)
public class OnceService implements LifecycleService {
}
/**
*
* TempService.java
*/
@Service(scope = IService.Scope.temp)
public class TempService implements LifecycleService {
}
/**
*
* GlobalService.java
*/
@Service(scope = IService.Scope.global)
public class GlobalService implements LifecycleService {
}
复制代码
组件B中执行: System.out.println(ServicePool.getService(OnceService.class) == ServicePool.getService(OnceService.class)); //System.out.println(ServicePool.getService(TempService.class) == ServicePool.getService(TempService.class));//不可靠 System.out.println(ServicePool.getService(GlobalService.class) == ServicePool.getService(GlobalService.class)); 输出: false true 复制代码
因为ServicePool是基于class作的注入操做, ServicePool内部会将path映射成Class,这个映射操做是在编译期完成的。app
/**
* 服务池pool中
*
* IPathService.java
*/
public interface IPathService {
String pathServiceName();
}
复制代码
/** * 组件A中 * * PathService */ @Service(path = "pathService") public class PathService implements IPathService { @Override public String pathServiceName() { return "Path Service"; } } 复制代码
IPathService是任意定义的接口,它能够有一个或多个实现类,只要在实现类上加@Service注解并指定path属性。咱们就能够经过ServicePool.getService(path)来找到或者建立他的实现类对象。框架
组件B中执行: IPathService pathService = ServicePool.getService("pathService"); System.out.println(pathService.pathServiceName()); 输出: Path Service 复制代码
app开发过程当中,确定少不了对组件进行初始化,不管是内部组件仍是引用外部库,不少都须要执行初始化操做。常规的方式是全部初始化操做都是放到Application的onCreate()/onAttachBaseContext()方法中执行。组件有不少而Application只有1个, 如何让每一个组件均可以拥有它本身的初始化类呢?
ServciePool中有一个@Init注解,任何被@Init注解标记的Service类被认为是一个须要执行操做初始化操做的Service类, 同时这个Service类须要实现IInitService接口。
@Init(lazy = false) //lazy = false表示禁用懒加载,则该Service会随Application初始化而初始化 @Service public class InitService implements IInitService { @Override public void onInit() { //do something. } } 复制代码
若是初始化组件想要随Application初始化而初始化,须要将@Init注解的lazy赋值为false,表示禁用懒加载。 除了lazy属性,@Init注解还有async,dependencies两个属性。
async属性顾名思义是异步执行,async默认为false,设置为true表示该组件初始化会在异步线程执行。
dependencies能够传递一个初始化组件类数组,表示当前组件初始化依赖这个数组中的全部组件。ServicePool会先初始化数组中的组件再去执行当前组件的初始化。
@Init @Service public class InitService1 implements IInitService { @Override public void onInit() { System.out.println("Service 1 Inited!!!"); } } @Init @Service public class InitService2 implements IInitService { @Override public void onInit() { System.out.println("Service 2 Inited!!!"); } } @Init(lazy = false, dependencies=[InitService1.class, InitService2.class]) @Service public class InitService3 implements IInitService { @Override public void onInit() { System.out.println("Service 3 Inited!!!"); } } 复制代码
因为InitService1, InitService2之间没有依赖关系,所以他两的执行顺序不肯定,InitService3同时依赖InitService1和InitService2,所以InitService3必定是最后执行的。
Application初始化后执行结果:
Service 2 Inited!!!
Service 1 Inited!!!
Service 3 Inited!!!
复制代码
ServicePool的初始化在如何优雅的管理多环境下的Android代码这篇文章的最后中有实际应用,也可作为示例参考。
全部初始化操做都随Application启动执行,一方面会致使Application很是臃肿,另外一方面虽然单个组件初始化时长很短,但n多个组件初始化时长结合在了一块儿就会致使启动时间超长。
懒加载是ServicePool的核心思想。全部组件只有在第一次被使用时才会被建立和执行初始化。而不是集中在Application初始化过程。分散初始化从而减轻App启动压力。举个🌰
微信分享是很经常使用的功能,咱们以微信分享为例,WXShareManager用来助力微信分享相关操做。
@Init @Service public class WXShareManager implement IInitService { public static final String appId = "wx499fa9b1ba4a93db"; public static final String userName = "gh_6619a14a139d"; @Override public void onInit() { IWXAPI wxApi = WXAPIFactory.createWXAPI(mContext, null); wxApi.registerApp(appId); } public void share(...) { //do wx share. } } 复制代码
shareManager注入对象的时候初始化操做会被执行。
public class ShareActivity extends AppcompatActivity {
@Service
private WXShareManager shareManager;//此时会触发WXShareManager的onInit初始化。
...
void onClick(View v) {
shareManager.share(...);
}
}
复制代码
未完待续....
快速接入ServicePool