柚子快報邀請碼778899分享:Dubbo SPI機制使用
柚子快報邀請碼778899分享:Dubbo SPI機制使用
Java SPI機制博客傳送門:https://blog.csdn.net/qq_42402854/article/details/125705159 注意:JDK SPI會一次性實例化擴展點的所有實現(xiàn)。
Dubbo沒有使用JDK的SPI機制,而是自己實現(xiàn)的一套SPI機制。在Dubbo的源碼中,很多地方會存在下面這樣的三種代碼:
//獲取自適應(yīng)擴展點
ExtensionLoader.getExtensionLoader(xxx.class).getAdaptiveExtension();
//獲取指定名稱的擴展點
ExtensionLoader.getExtensionLoader(xxx.class).getExtension(name);
//激活擴展點
ExtensionLoader.getExtensionLoader(xxx.class).getActivateExtension(url, key);
在Dubbo中,SPI貫穿整個Dubbo的核心,所以理解Dubbo中的SPI對于理解Dubbo的原理有著至關(guān)重要的作用。
在Java中,通過 java.util.ServiceLoader 來發(fā)現(xiàn)動態(tài)加載具體的實現(xiàn)類到JVM中。在Spring中,SpringFactoriesLoader這個類,它也是一種SPI機制。在Dubbo中,ExtensionLoader這個類,它也是一種SPI機制。
一、Dubbo SPI機制使用
1、Dubbo的 SPI機制
Dubbo的 SPI機制:來自《Apache Dubbo與實戰(zhàn)》一書中截圖。
1.1 擴展點注解
1.1.1 @SPI注解
@SPI注解可以使用在類,接口和枚舉上。
主要作用就是標記這個接口是一個 Dubbo SPI接口,即一個擴展點。 value,表示可以設(shè)置默認的實現(xiàn)類
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE})
public @interface SPI {
/**
* default extension name
*/
String value() default "";
}
1.1.2 @Adaptive注解
@Adaptive注解 可以標記在類、接口、枚舉類和方法上。
自適應(yīng)擴展點的知識,表示在運行時使用那個實現(xiàn)類。 當該注解使用在類上時,只能有一個實現(xiàn)類上可以加 @Adaptive注解,如果多個實現(xiàn)類都有該注解會拋出異常。
包裝類等其他的自行了解。
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.METHOD})
public @interface Adaptive {
String[] value() default {};
}
1.1.3 @Acticate注解
@Acticate注解 可以標記在類、接口、枚舉類和方法上。
默認自動激活,主要使用在多個擴展點實現(xiàn)、還可以根據(jù)不同條件被激活的場景中。
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.METHOD})
public @interface Activate {
String[] group() default {};
String[] value() default {};
String[] before() default {};
String[] after() default {};
int order() default 0;
}
2、獲取Protocol擴展點
public static void main(String[] args) {
ExtensionLoader
Protocol dubbo = extensionLoader.getExtension("dubbo");
System.out.println("dubbo 指定名稱的擴展點:" + dubbo);
System.out.println("dubbo 自適應(yīng)擴展點:" + extensionLoader.getAdaptiveExtension());
System.out.println("dubbo 默認擴展點協(xié)議:" + extensionLoader.getDefaultExtension());
System.out.println("dubbo 獲取所有擴展點協(xié)議:" + extensionLoader.getSupportedExtensions());
}
Protocol接口源碼如下:
二、自定義擴展點
這里寫個 demo 感受一下 dubbo的SPI機制。
1、定義擴展點和實現(xiàn)類
1.1 擴展點
@SPI注解:value,表示設(shè)置默認的實現(xiàn)類
@SPI("MyLog")
public interface MyLog {
void debug();
}
1.2 實現(xiàn)類
這里定義三個實現(xiàn)類。
@Activate
public class MyLog4j implements MyLog{
@Override
public void debug() {
System.out.println("==========dubbo MyLog4j");
}
}
@Activate
public class MyLogback implements MyLog{
@Override
public void debug() {
System.out.println("==========dubbo MyLogback");
}
}
@Adaptive
//@Activate
public class MyAdaptiveLog implements MyLog{
@Override
public void debug() {
System.out.println("==========dubbo MyAdaptiveLog");
}
}
2、創(chuàng)建配置文件
在項目resources目錄下新建一個 META-INF/dubbo/文件夾。
在 META-INF/dubbo/目錄下,創(chuàng)建一個文件,文件名為該SPI接口的全限定名。文件內(nèi)容是 key=具體實現(xiàn)類的全限定名,如果有多個,則用分行符分隔。
3、測試,加載實現(xiàn)類
在 代碼中通過 org.apache.dubbo.common.extension.ExtensionLoader來加載具體的實現(xiàn)類。
@Test
public void test() {
ExtensionLoader
MyLog myLogback = extensionLoader.getExtension("myLogback");
System.out.println("MyLog 指定名稱的擴展點:" + myLogback);
myLogback.debug();
// 獲取實現(xiàn)了@Adaptive注解的實現(xiàn)類
System.out.println("MyLog 自適應(yīng)擴展點:" + extensionLoader.getAdaptiveExtension());
System.out.println("MyLog 默認擴展點協(xié)議:" + extensionLoader.getDefaultExtension());
System.out.println("MyLog 獲取所有擴展點:" + extensionLoader.getSupportedExtensions());
}
– 求知若饑,虛心若愚。
柚子快報邀請碼778899分享:Dubbo SPI機制使用
參考閱讀
本文內(nèi)容根據(jù)網(wǎng)絡(luò)資料整理,出于傳遞更多信息之目的,不代表金鑰匙跨境贊同其觀點和立場。
轉(zhuǎn)載請注明,如有侵權(quán),聯(lián)系刪除。