• 使用SPI解耦服务调用


            在开发java组件时,一个功能组件往往需要支持多种规范,在客户端调用时需要根据不同情况,进行不同的服务调用。例如:客户端于服务端之间进行数据交互,数据交互协议有1.0、2.0、3.0。。。在组件开发时就需要至少开发出三个服务分别对应每种需求。

            客户端使用组件时,需要根据自身情况调用不同协议版本的服务。

            方案一:使用配置文件,通过外部挂载一个配置文件,客户端读取配置文件,根据配置类型调用组件的服务。

            方案二:使用SPI。不需要外挂配置文件,通过修改jar包的META-INF/services/全路径类型的文件(内容为需要使用的服务的全路径类名)的方式来实现。

            第一种方案参考:springBoot 配置项外提结合容器化_任庆 的博客-CSDN博客

            重点说一下第二种方式。JDK6开始支持 SPI(Service Provider Interface),提供服务的接口。能够通过配置jar包的方式指定调用哪个实现,从而降低了客户端和实现的耦合度。而且实现起来也很简便,如果是轻量级应用就很适合。

            第一步,new一个java Project(为了方便运行,我创建了一个springboot的项目)

            第二步,定义一个服务接口,也就是SPI指的那个接口:

    1. public interface Driver {
    2. void work();
    3. }

            第三步,定义两个实现类:

    1. public class DriverA implements Driver {
    2. @Override
    3. public void work() {
    4. System.out.println("DriverA is working");
    5. }
    6. }
    1. public class DriverB implements Driver {
    2. @Override
    3. public void work() {
    4. System.out.println("DriverB is working");
    5. }
    6. }

            第四步,通过SPI调用:

    1. @SpringBootApplication
    2. public class HttpserverApplication {
    3. public static void main(String[] args) {
    4. SpringApplication.run(HttpserverApplication.class, args);
    5. // 主要是下面这段
    6. ServiceLoader loadedDrivers = ServiceLoader.load(Driver.class);
    7. Iterator iterator = loadedDrivers.iterator();
    8. while(iterator.hasNext()) {
    9. Driver next = iterator.next();
    10. next.work();
    11. }
    12. }
    13. }

            第五步,build成jar包运行,这次是没有指定实现类的,因此Services是空,没有输出

             第六步,修改MEAT-INF/services/xxxx,重新运行

    1. 新建 com.yfgg.httpserver.spi.Driver
    2. com.yfgg.httpserver.spi.Driver中添加内容 com.yfgg.httpserver.spi.DriverB
    3. **** SPI路径和实现类的全路径以实际为准

             可以看到,指定DriverB运行成功。

            使用场景:客户端添加一些service选择逻辑,配合jar包的配置文件,灵活调用组件的实现。在JDBC连接上常见。

  • 相关阅读:
    Python+Django+vue的旅游信息网站系统项目源码介绍
    Mathcad的数组使用
    ROS报错:joint-state-publisher报错
    Jenkins+Svn+Docker搭建持续集成环境 自动部署
    Mysql和Redis数据如何保持一致
    【计算机网络】PPP和PPPoE协议
    数据库表设计优化
    Tomcat免安装版修改标题名称和进程
    Samba配置文件举例
    Python&C++相互混合调用编程全面实战-21依赖的QT环境安装和信号槽机制的讲解
  • 原文地址:https://blog.csdn.net/nickDaDa/article/details/126222500