1. 程式人生 > 其它 >淺談Java中的SPI

淺談Java中的SPI

1.SPI 簡介

SPI 全稱為 Service Provider Interface,是一種服務發現機制。

SPI 的本質是將介面實現類的全限定名配置在檔案中,並由服務載入器讀取配置檔案,載入實現類。

這樣可以在執行時,動態為介面替換實現類。正因此特性,我們可以很容易的通過 SPI 機制為我們的程式提供拓展功能。

簡單來說,就是在程式執行的時候,通過/META-INF/services/下的配置檔案來決定載入實現類。

Java SPI

一般命名規則是介面包類名的全稱,比如 mysql-connector-java-5.1.49.jar 的檔名叫 java.sql.Driver但是裡面的內容就是實現類

的包類名全稱com.mysql.cj.jdbc.Driver

使用的時候,可以通過ServiceLoader<Robot> serviceLoader = ServiceLoader.load(Driver.class);來獲取配置載入實現類

舉個例子:
寫一個介面類,就叫WaiMai

package com.inkyi.blog.example.spi;

public interface Waimai {
    void songWaiMai();
}

再寫兩個子類 餓了麼 和 美團

package com.inkyi.blog.example.spi;

public class EleMeWm implements Waimai {
    @Override
    public void songWaiMai() {
        System.out.println("餓了麼送外賣");
    }
}
package com.inkyi.blog.example.spi;

public class MeituanWm implements Waimai {
    @Override
    public void songWaiMai() {
        System.out.println("美團送外賣");
    }
}

接著在META-INF/services下新建一個檔案,名字叫:com.inkyi.blog.example.spi.Waimai內容如下

com.inkyi.blog.example.spi.EleMeWm

最後我們編寫測試類

package com.inkyi.blog.example.spi;

import java.util.ServiceLoader;

public class SpiTest {
    public static void main(String[] args) {
        ServiceLoader<Waimai> load = ServiceLoader.load(Waimai.class);
        for (Waimai demo : load) {
            demo.songWaiMai();
        }
    }
}

執行後,Java會根據Waimai.class的包路徑,找到META-INF/services下的com.inkyi.blog.example.spi.Waimai檔案讀取裡面的內容,根據內容例項化類,然後執行songWaiMai()方法。

餓了麼送外賣

大概的流程就是這樣的,由於ServiceLoader實現了Iterable介面,所以com.inkyi.blog.example.spi.Waimai檔案中可以寫多個實現類,。
比如把美團和餓了麼都加上

com.inkyi.blog.example.spi.MeituanWm
com.inkyi.blog.example.spi.EleMeWm

那麼就會輸出:

美團送外賣
餓了麼送外賣

程式碼案例
META-INF/services