2009-11-18 80 views
3

我正在編寫一個庫,允許人們使用插件框架提供某些接口的實現(如果您熟悉,則爲JPF)。插件不存儲在類路徑中。該框架爲我提供了每個插件的ClassLoader,因此當請求接口「MyInterface」的名爲「MyImpl」的實現時,我可以找到正確的插件,然後使用該插件的ClassLoader加載類,從中我可以創建一個實例如果我知道關於構造函數的東西。到現在爲止還挺好。如何使用用不同的Java classloader加載的實現?

但是,現在我有一種情況,我需要調用只在該特定實現上可用的方法。因此,有兩種方法,我可以嘗試這樣做:

方法1:

// Makes sure that MyImpl has been loaded, using the custom classloader 
Plugins.getClass(MyInterface.class, "MyImpl"); 
// This line will not compile because MyImpl is not available at build time 
MyImpl foo = new MyImpl(); 
// If I could get this far, this line would work: 
foo.methodOnlyInMyImpl(); 

方法2:

// This call will get an instance of MyImpl (already written and tested) 
MyInterface foo = Plugins.getInstance(MyInterface.class, "MyImpl"); 
// Compiler error because there is no MyInterface.methodOnlyInMyImpl method. 
foo.methodOnlyInMyImpl() 

方法1是兩個的清潔劑,因爲它是最類似於如果類是「正常」且不能通過插件訪問的話你將如何編寫代碼。但是,沒有編譯。

選項我想出迄今:
A.使用方法2,但在使用反射做methodOnlyInMyImpl方法調用(!請,否)
B.將在構建路徑的插件類和然後使用方法1進行編譯。 (我目前最喜歡的)
C. B +安裝插件時,在類文件複製到另一個目錄是在classpath中,這樣系統類加載器可以加載它們(導致其他問題)

所以,我的問題是:

  1. 我是否錯過了另一個更好的想法?
  2. 如果我做B,我會在運行時遇到問題嗎?畢竟,使用MyImpl的類大概會使用系統類加載器加載。所以,只要它看到MyImpl foo,是不是會嘗試使用系統類加載器加載MyImpl,這將失敗(即使Plugins.newInstance調用將提供MyImpl的實例)?

回答

3

首先,當你需要針對真正的實現實現時,從插件機制中獲得什麼優勢?插件應該實現一個接口,你可以通過接口使用實現。

我不是JPF類似的,但是當由不同的類加載器加載時,java類永遠不兼容。但是,有兩種可能的途徑:

  1. 的接口是在你的類加載器,插件類加載器有你的類加載器的父,所以它的界面是一樣的你。當方法在接口中聲明時,代碼2應該與此一起工作。

  2. 您可以使用序列化。這是一種有限的方式,可以在獨立類加載器之間更有用地傳輸數據對象。我需要在兩個webapps之間使用這個參數進行跨請求參數的調度。

+0

舉例說明優點:我有接口X和Y.有一個返回Y的X.getY()方法。我有四個插件提供X實現Xa和Xb,Y實現Yc和Yd。現在,Xa和Xb都需要在內部使用實現Yc,所以這是我需要具體實現的地方。應用程序只能與X和Y交互,但插件需要特定的實現。 JPF幫助處理插件依賴關係。 –

+0

+1 - OP正試圖忽略使用接口所暗示的合同。如果插件是唯一關心實現類的插件,那麼他/她將不得不提供編譯時訪問實現類,使用強制轉換,並處理可能的ClassCastException。 – kdgregory

+0

不幸的是,我無法預測所有的接口。序列化(Arne),在運行時(kdgregory)和TransLoader(Carl)都需要類在當前類加載器中以某種方式可用,這在我的情況中不是這樣 - 它涉及到在運行時使用反射或放置需求classpath包含插件dirs。我選擇了後者。由於關鍵短語「由不同的類加載器加載的Java類永遠不兼容」而接受此答案。謝謝,如果我有代表,我會+1。 –

2

在上一個問題中提到了一個名爲TransLoader的庫。以下是來源的網址:http://code.google.com/p/transloader/

+1

這很有幫助,如果我的要求不同,會有所幫助。謝謝。如果我有代表,我會+1。 –

+0

+1回到atcha,很高興我有代表。對不起,我無法更深入地辨別並滿足您的要求。 –

相關問題