Hazelcast在OSGI中的classloading問題

前些日子在開發中用到了hazelcast,挺不錯的一個DD支持分佈式map,list等多種容器,並且實現了標準的JDK容器接口,實在是太讚了。和Spring配合使用,應該很是方便,測試的時候set一個標準的JDK容器實現,避免跑測試程序是每次啓動hazelcast,影響測試運行速度,運行時注入真正的IMap,IList實例,很是的方便。框架

很是不幸的是。整個系統框架是基於OSGI的,因爲Hazelcast是經過對象的序列化,從本機傳輸到遠端, 在遠端反序列化,來實現對象實例在再不一樣JVM之間的傳輸的。因而在OSGI嚴格的classloading機制下,各類ClassNotFound Exception 出現了。分佈式

在網上查了一下,發現hazcelcast聲稱已經解決了這個問題,有些帖子測試沒問題,有些帖子測試有問題。。有點混亂。在咱們的環境下是對於map,list等容器沒問題,對於executorservice,topic等Hazelcast有內部線程控制,有問題。測試

研究了一下當前的版本1.9.3發現,對於Map,list等容器類的實現,classloader採用的是當前線程的context class loader, 這點是很是巧妙的,由於當前線程必定能Load到目標集合中的類對象,這點也是Hazelcast針對OSGI ClassLoading問題的官方fix,(fix 以前原來使用的是configClassLoader, 簡單的說就是hazelcast初始化線程的context class loader).假設bundle A建立了hazelcast(hazelcast的默認classloader即爲A的bundle class loader),bundle B 中取得了一個 hazelcast map對象,向其中放了一個bean(bundle B 的類,沒有export) 對象,再取出, 此時若是hazelcast若是使用默認的classloader load bean 對象必定會出 class not found exception, 經過使用current thread 的context class loader(當前線程在B bundle中,固然能load 到本身的類), hazelcast的fix巧妙的解決了這個問題。線程

可是對於executorservice,topic等有hazelcast內生線程管理的服務,因爲服務的內部線程池都是在Hacelcast初始化的時候預先建立,因此統一使用configClassLoader,因而若是你的hazelcast是在bundle A 中建立好的,而後bundle B 中向executorservice添加了一個Brunnable對象,恭喜你,即便在hazelcast單機模式下,一樣會出現ClassNotFound Exception。由於如今hazelcast的內部線程使用的都是默認configClassLoader(A的bundle class loader)。對象

在這種狀況下只能經過dynamic import * 來解決問題。。接口

結論ssl

1.hazelcast和osgi在一塊兒工做挺難的,若是使用executorservice,topic等組件。開發

2.若是非要用。。。最好在使用exceutor service 或者 topic的bundle中首次初始化hazelcast,這樣能夠避免不少潛在的問題。 io

相關文章
相關標籤/搜索