SPI 简介

SPI 全称为(Service Provider Interface),是JDK内置的一种服务提供发现机制。

一个服务(Service)通常指的是已知的接口或者抽象类,服务提供方就是对这个接口或者抽象类的实现,然后按照SPI 标准存放到资源路径(resources)META-INF/services目录下,文件的命名为该服务接口的全限定名。如有一个服务接口:

package com.winner.spi;

/**
* @author winner_0715
* @date 2018/4/1
*/
public interface DemoService {
String sayHello(String name);
}

其服务实现类为:

package com.winner.spi.impl;

import com.winner.spi.DemoService;

/**
* @author winner_0715
* @date 2018/4/1
*/
public class DemoServiceImpl implements DemoService { @Override
public String sayHello(String name) {
return "hello , " + name;
}
}

那此时需要在META-INF/services中创建一个名为com.ricky.codelab.spi.DemoService的文件,其中的内容就为该实现类的全限定名:com.ricky.codelab.spi.impl.DemoServiceImpl。 
如果该Service有多个服务实现,则每一行写一个服务实现(#后面的内容为注释),并且该文件只能够是以UTF-8编码。

然后,我们可以通过ServiceLoader.load(Class class); 来动态加载Service的实现类了。

许多开发框架都使用了Java的SPI机制,如java.sql.Driver的SPI实现(mysql驱动、oracle驱动等)、common-logging的日志接口实现、dubbo的扩展实现等等。

SPI机制的约定

  • 在META-INF/services/目录中创建以Service接口全限定名命名的文件,该文件内容为Service接口具体实现类的全限定名,文件编码必须为UTF-8。
  • 使用ServiceLoader.load(Class class); 动态加载Service接口的实现类。
  • 如SPI的实现类为jar,则需要将其放在当前程序的classpath下。
  • Service的具体实现类必须有一个不带参数的构造方法。

1、项目结构

2、Service接口定义

package com.winner.spi;

/**
* @author winner_0715
* @date 2018/4/1
*/
public interface DemoService {
String sayHello(String name);
}

3、Service接口实现类

本示例中DemoService有两个实现类,分别为:EnglishDemoServiceImpl和ChineseDemoServiceImpl,代码如下: 
EnglishDemoServiceImpl.java

package com.winner.spi.impl;

import com.winner.spi.DemoService;

/**
* @author winner_0715
* @date 2018/4/1
*/
public class EnglishDemoServiceImpl implements DemoService { @Override
public String sayHello(String name) {
return "hello , " + name;
}
}

ChineseDemoServiceImpl.java

package com.winner.spi.impl;

import com.winner.spi.DemoService;

/**
* @author winner_0715
* @date 2018/4/1
*/
public class ChineseDemoServiceImpl implements DemoService { @Override
public String sayHello(String name) {
return "你好 , " + name;
}
}

META-INF/services/配置

在src/main/resources 下创建META-INF/services/目录,并新建com.winner.spi.DemoService文件,内容如下:

#English implementation
com.winner.spi.impl.EnglishDemoServiceImpl
#Chinese implementation
com.winner.spi.impl.ChineseDemoServiceImpl

加载Service实现类

import com.winner.spi.DemoService;

import java.util.Iterator;
import java.util.ServiceLoader; /**
* @author winner_0715
* @date 2018/4/1
*/
public class Test {
public static void main(String[] args) {
ServiceLoader<DemoService> serviceLoader = ServiceLoader.load(DemoService.class);
Iterator<DemoService> it = serviceLoader.iterator();
while (it.hasNext()) {
DemoService demoService = it.next();
System.out.println("class:" + demoService.getClass().getName()
+ "-->" + demoService.sayHello("World"));
}
}
}

执行结果:

import com.winner.spi.DemoService;

import java.util.Iterator;
import java.util.ServiceLoader; /**
* @author winner_0715
* @date 2018/4/1
*/
public class Test {
public static void main(String[] args) {
ServiceLoader<DemoService> serviceLoader = ServiceLoader.load(DemoService.class);
Iterator<DemoService> it = serviceLoader.iterator();
while (it.hasNext()) {
DemoService demoService = it.next();
System.out.println("class:" + demoService.getClass().getName()
+ "-->" + demoService.sayHello("World"));
}
}
}

Java SPI(Service Provider Interface)简介的更多相关文章

  1. JAVA SPI(Service Provider Interface)原理、设计及源码解析(其一)

    背景 团队内部轮流技术分享,其他人都是分享源码,我每次都是设计和架构,感觉自己太特立独行.这次我要合群点,分享点源码. 概念 Service Provider Interface:服务提供方接口.是一 ...

  2. Java SPI(Service Provider Interface)

    SPI 全称为 (Service Provider Interface) ,是JDK内置的一种服务提供发现机制. 目前有不少框架用它来做服务的扩展发现, 简单来说,它就是一种动态替换发现的机制, 举个 ...

  3. java的spi(Service Provider Interface)机制及源码(java8)

    1.什么是java的spi spi 全称为 service provider interface 即 服务提供接口,用来作为服务的扩展发现.在运行时动态添加接口的实现,是对接口的实现类的创建管理. 2 ...

  4. SPI: Service Provider Interface

    Service Provider Interface: JDK提供的一种服务发现的机制:主要是用于厂商实现JDK的只用. 比如说打印机,JDK提供了一个驱动接口com.printl.printerDr ...

  5. Java中的SPI(Service Provider Interface)

    转自:http://singleant.iteye.com/blog/1497259 最近看到公司的一些框架和之前看到的开源的一些框架的一些服务发现和接入都采用了java的spi机制. 所以简单的总结 ...

  6. SPI(Service Provider Interface)机制

    JAVA SPI 约定如下:当服务的提供者提供了服务接口的一种实现之后,在jar包的META-INF/services/ 目录中同时创建一个以服务接口命名的文件,该文件中的内容就是实现该服务接口的具体 ...

  7. SPI(Service Provider Interface)--通过接口获取服务

    spi 现在已有实现 jdk 提供实现 dubbo里的spi实现 一.jdk实现 配置 定义接口 定义实现类 配置资源文件 classpath下创建(META-INF/services/接口全面:ME ...

  8. Service Provider Interface

    @(Java)[SPI] Service Provider Interface API的一种设计方法,一般用于一些服务提供给第三方实现或者扩展,可以增强框架的扩展或者替换一些组件. 结构 Servic ...

  9. 【Java实战】源码解析Java SPI(Service Provider Interface )机制原理

    一.背景知识 在阅读开源框架源码时,发现许多框架都支持SPI(Service Provider Interface ),前面有篇文章JDBC对Driver的加载时应用了SPI,参考[Hibernate ...

随机推荐

  1. 002.Git日常基础使用

    一 获取git仓库 1.1 初始化仓库 [root@git ~]# cd /mystudy/ [root@git mystudy]# git init [root@git mystudy]# git ...

  2. springmvc springJDBC 简单实训银行账户管理系统

    springmvc springJDBC 简单实训银行账户管理系统 1.简单介绍一下,在校时每周结束都会有一次学习总结,简称“实训”,这次实训内容是spring,因为是最近热门框架,我就先从基础方面开 ...

  3. 反射调用 java bean的set和get方法

    一.使用java.beans.PropertyDescriptor import java.beans.IntrospectionException; import java.beans.Proper ...

  4. 十个问题带你了解和掌握java HashMap

    十个问题带你了解和掌握java HashMap 一.前言 本篇内容是源于 " 由阿里巴巴Java开发规约HashMap条目引发的故事",并在此基础上加了自己的对HashMap更多的 ...

  5. linux Shell 脚本编写

    1. http://www.jb51.net/article/28514.htm 2. http://www.runoob.com/linux/linux-shell.html

  6. django-QueryDict 对象

    在 HttpRequest 对象中,属性 GET 和 POST 得到的都是 django.http.QueryDict 所创建的实例.这是一个 django 自定义的类似字典的类,用来处理同一个键带多 ...

  7. luogu P2757 [国家集训队]等差子序列

    题目链接 luogu P2757 [国家集训队]等差子序列 题解 线段树好题 我选择暴力 代码 // luogu-judger-enable-o2 #include<cstdio> inl ...

  8. Codeforces Round #368 (Div. 2) D. Persistent Bookcase 离线 暴力

    D. Persistent Bookcase 题目连接: http://www.codeforces.com/contest/707/problem/D Description Recently in ...

  9. ant design table column 设置width不生效解决方案

    当td里的内容超出了width的范围时,会出现width不固定,也就是width不生效 解决方案: 设置scroll的width等于所有列宽之和(scroll={{x: 100%}})

  10. 使用Docker中国官方镜像的加速地址

    vi /etc/docker/daemon.json # 添加如下内容 { "registry-mirrors": ["https://registry.docker-c ...