ServiceLoader
- ServiceLoder的SPI
 - ServiceLoader.load(Driver.class)的作用
 
- 代码详解
 - 出现的问题
 - 解决方式
 
ServiceLoder的SPI
ServiceLoader.load(Driver.class)的作用
java.util.ServiceLoader工具类方法会使用ClassLoad类的getResources方法获取指定目录下的文件,读取文件内容并解析获取所有接口实现类的全限路径,根据全限路径使用class.forName装载class文件到JVM,然后通过c.newInstance()实例化类转化接口类型并放入providers缓存提供者集合中,以供后面使用。
代码详解
这里是想加载接口Driver 的实体类,那么实体类有哪些呢
public interface Driver extends AutoCloseable {
    static Optional<Driver> get(DriverConfig config) {
        Asserts.checkNotNull(config, "数据源配置不能为空");
        ServiceLoader<Driver> drivers = ServiceLoader.load(Driver.class);
        for (Driver driver : drivers) {
            if (driver.canHandle(config.getType())) {
                return Optional.of(driver.setDriverConfig(config));
            }
        }
        return Optional.empty();
    }
}
 
①MySqlDriver extends AbstractJdbcDriver
 ②AbstractJdbcDriver extends AbstractDriver
 ③AbstractDriver implements Driver
 所以是MySqlDriver继承Driver
 
出现的问题
明明是MySqlDriver继承了Driver,
但是在进行:ServiceLoader drivers =ServiceLoader.load(Driver.class);的时候没有任何内容
我们这个接口所在的子项目是dlink-admin
 实际上就是在dlink-admin里面无法读取到com.dlink.metadata.driver.MySqlDriver这个类,所以到接口Driver的时候,没有落到实体类上
解决方式
在dlink-admin这个项目里面引入dlink-metadata-mysql
 在pom.xml文件里面,
 加上:
 <dependency>
    <groupId>com.dlink</groupId>
    <artifactId>dlink-metadata-mysql</artifactId>
</dependency>
 

 



















