java spi

容器希望中间件只提供相关的connector依赖给业务方使用,而不是具体的实现。通过connector带来的好处就是,中间件升级jar包,不会影响业务方的使用,业务方对其无感知。并且业务代码里也不会引入多于的jar包,导致不必要的jar冲突。

Java 6 has introduced a feature for discovering and loading implementations matching a given interface: Service Provider Interface (SPI).

SPI能够将接口和实现类解耦,给业务方相关的接口类,接口的实现类在放在某个classpath下,通过SPI来做到接口匹配对应的实现类。

http://or0f3pi7r.bkt.clouddn.com/18-10-8/72515828.jpg

基于自定义ClassLoaderSPI来做到上图的内容

//定义接口模块
public interface Person {
 
    void greet(String name);
}
//定义接口实现模块
public class YoungPerson implements Person {
    public void greet(final String name) {
        System.out.println("hello old person");
    }
}
public class OldPerson implements Person {
 
    public void greet(final String name) {
        System.out.println("hello young person");
    }
}
//在META-INF/services下添加com.laomei.test.Person
com.laomei.spi.test.OldPerson
com.laomei.spi.test.YoungPerson
//测试模块,测试模块只依赖接口模块,不依赖实现模块
public class Main {
    public static void main(String[] args) throws MalformedURLException {
        URLClassLoader customClassLoader = customClassLoader();
        Thread.currentThread().setContextClassLoader(customClassLoader);
        ServiceLoader<Person> person = ServiceLoader.load(Person.class);
        Iterator<Person> iterator = person.iterator();
        while (iterator.hasNext()) {
            Person customPerson = iterator.next();
            customPerson.greet(" user");
        }
    }
 
    public static URLClassLoader customClassLoader() throws MalformedURLException {
        String path = "jar:file:///opt/spi-test-implement.jar!/";
        return new URLClassLoader(new URL[]{ new URL(path) });
    }
}
//结果
hello young person
hello old person
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值