使用axis2構建webservice時,發現系統運行一段時間後用戶端的記憶體使用量一直不斷增高,導致應用伺服器無法承受而重啟,這裡提供了一種解決方案。
原因分析:用戶端以stub方式請求服務,stub對象是一個非常重量級的對象,每次用戶端向服務端請求服務時,stub對象不斷被建立,佔用大量系統資源
解決方案:考慮到所有的用戶端stub都繼承自org.apache.axis2.client.Stub類,考慮使用簡單原廠模式+簡單的對象池來提供stub對象執行個體,這樣只需首次需要stub對象時執行個體化一次,以後需要用的時候從stub對象池中取得,工廠類本身做成單例模式。
代碼實現:
public class StubFactory{<br /> //從設定檔中取用戶端應用context的絕對路徑<br /> public static final String path=ServiceConfig.getPath();<br /> //從設定檔中取服務url<br /> public static final String serviceUrl=ServiceConfig.getServiceUrl();</p><p> private static Map map=new HashMap();//這裡可以是一個同步的Map,也可以直接用Hashtable<br /> private static ConfigurationContext configurationContext=null;<br /> private static StubFactory stubFactory=new StubFactory();</p><p> private StubFactory(){};</p><p> static{<br /> try{<br /> configurationContext=ConfigurationContextFactory.createConfigurationContextFromFileSystem(path+"/WEB-INF",path+"/WEB-INF/conf/axis2.xml");<br /> }catch(AxisFault e){<br /> e.printStackTrace();<br /> }<br /> }</p><p> public Stub getStub(String type){<br /> Stub stub=null;<br /> if(map.get(type)==null){<br /> stub=(Stub)this.createStub(type);<br /> map.put(type,stub);<br /> }<br /> return (Stub)map.get(type);<br /> }</p><p> private Stub createStub(String type){<br /> Stub stub=null;<br /> String targetEndpoint=null;<br /> try{<br /> if("SearchServiceStub".equals(type)){<br />targetEndpoint=serviceUrl+"services/SearchService.SearchServiceHttpSoap12Endpoint/";<br /> stub=new SearchServiceStub(configurationContext,targetEndpoint);<br /> }<br /> if("CalculateServiceStub".equals(type)){<br />targetEndpoint=serviceUrl+"services/CalculateService.CalculateServiceHttpSoap12Endpoint/";<br /> stub=new CalculateServiceStub(configurationContext,targetEndpoint);<br /> }<br /> if("MessageServiceStub".equals(type)){<br />targetEndpoint=serviceUrl+"services/MessageService.MessageServiceHttpSoap12Endpoint/";<br /> stub=new MessageServiceStub(configurationContext,targetEndpoint);<br /> }<br /> }catch(Exception e){<br /> e.printStackTrace();<br /> }<br /> return stub;<br /> }</p><p> public static StubFactory getInstance(){<br /> return stubFactory;<br /> }<br />}
取stub對象只要如下代碼:
SearchServiceStub stub=(SearchServiceStub)StubFactory.getInstance().getStub("SearchServiceStub");