2016-02-04 29 views
0

我使用GroovyClassLoader測試JARS的動態加載。我們會經常更新JAR,所以我們需要在不重新啓動JVM的情況下重新加載JAR(更具體地說,是類)。這可能嗎?我做了classLoader.addUrl(path)一次,並且JAR被加載到內存中。然後,我可以在後續腳本中生成實例,而無需再次加載類(這看起來像是緩存,這很好)。Groovy GroovyClassLoader JVM緩存和更新加載類

問題是我試圖做classLoader.clearCache(),它似乎沒有任何效果。 .classCache.sourceCache是空的。但是,我仍然可以生成實例。我試圖獲得父級加載程序,但它沒有顯示任何加載的程序包/類的跟蹤。我不確定它在哪裏生活。

我也讀過這篇文章,沒有我沒有在JVM中編譯的類。

Classes Loaded by GroovyClassLoader not listed

我不認爲我的代碼是相關的,但在這裏它是無論如何。

GroovyClassLoader classLoader = new GroovyClassLoader() 
def jarFile = new File("C:/sandbox-test-0.1.0-SNAPSHOT.jar") 
classLoader.addURL(jarFile.toURI().toURL()) 
def mySand = Class.forName("com.test.Sandbox").newInstance() 
println mySand.dump() 
+0

糾正我,如果我錯了,我的理解是,你正試圖用你的類路徑中更新版本的jar替換現有的jar。如果是這樣的話,不會使用新的jar路徑調用classLoader.addUrl(path),只需將新版本的jar添加到類路徑的末尾?我相信這樣做的結果是,你現在在classpath中有2個版本的jar,更重要的是,Java會在類路徑中找到第一個舊版本,並且不會從新jar中加載類,除非它們是新類原來的那個不存在。 – pczeus

+0

確實如此,事實上也是這個問題。在一位出色的Groovy專家的幫助下,我正在努力尋找以下解決方案:1.編寫一個新類,用於在開始時創建和操作新的UrlClassLoader(),然後加載所有JAR URL。該類加載器將作爲靜態變量存儲在JVM中,允許我的所有自定義代碼找到該類加載器。最重要的是,我的「更新程序」進程每10分鐘運行一次,如果它檢測到任何jar文件的更改,它會將該變量設置爲null,然後重新創建它,並在此過程中提取JARS的新副本。 – solvingJ

回答

0

Sascha向我展示了一個非常簡單的解決方法。

「更新」一個類加載器,可以簡單地廢除現有的一個和改造:

classloader = null 
classloader = new GroovyClassLoader() 
classLoader.addURL(jarFile.toURI().toURL()) 

所請求的類時,才需要的類加載器。

這在我的用例中很簡單。也許其他人會有更復雜的情況下,可能會使這不起作用。