ServiceLoader简要说明
第一次遇到ServiceLoader是在Apollo的Client端源码阅读时,觉得很新奇。其在Apollo Client中主要作用是,通过文件制定的方式来确定用哪种DI注入的方式,Apollo Client中默认使用的是Guice的DI方式。使用了ServiceLoader这种方式之后,可以在使用Client的时候使用其他的DI方式。
我们先来看看ServiceLoader的官方的说明: A simple service-provider loading facility.ServiceLoader在JDK3的时候已经引入,但是仅仅作为内部使用的一个工具类。在JDK6后开放使用,但设置为final, 是不允许用户继承使用的。
ServiceLoader Step By Step
定义一个接口,比如com.ok.IHelloService, 定义了sayHello的方法。
完成两个Service来实现该接口
com.ok.DefaultHelloService
com.ok.AnotherHelloService
3. ServiceProvider定义
在项目的resource目录下,建立META-INF/services目录,然后构建一个文件,文件名为com.ok.IHelloService,内容为
com.ok.DefaultHelloService
com.ok.AnotherHelloService
4. 建立测试类,代码如下:
public static void main(String[] args) {
ServiceLoader<ISPIHelloService> loaders = ServiceLoader.load(ISPIHelloService.class);
for(ISPIHelloService service : loaders) {
System.out.println(service.sayHello());
}
}
如果引用端需要使用自定义的ServiceProvider,那么也需要建立相应的META-INF/services目录以及文件,并实现该服务。
SPI (Service Provider Interface)
我是SPI,我让框架更加优雅了!在该文中描述了一个场景:为了支持不同格式的歌曲,架构组通过SPI的方式来实现了不同的支持歌曲解析项目,比如MP3解析器、MP4解析器。使用者只要在使用的时候导入需要的项目包就可以了。这种方式借鉴了JDBC的实现方式, jdk中的java.sql包为了实现支持不同的connector, 而采用SPI,在实际的开发中,只需要引入不同的数据库连接包即可,比如引入mysql-connector.jar。实现方式都是差不多,通过采用ServerLoader的方式,在启动的时候,mysql-connector会将自己的驱动实例注册到DriveManager中,然后后续就可以通过DriveManager.getconnection()来获取数据库连接。
网友评论