需求:如今的系統有一部分業務是經過hessian的遠程服務提供的,爲了應對不斷的增加的服務器壓力,須要對這個提供hessian服務的工程能承受的壓力有一個比較詳細的瞭解。
hessian走的http的協議,可是其數據傳輸跟通常用戶發起的http服務仍是不同的,作壓力的測試的開源工具仍是比較多的,相似jemeter,LoadRunner等均可以,可是這些都無法對hessian服務進行壓力測試。
方案1:建立一個web工程,在web工程提供一些http的服務,每一個服務會對應的發起一個hessian請求,而後使用某些壓力測試工具對這些http進行併發訪問。
方案2:本身寫java程序,模擬壓力測試,而後逐個測試hessian服務。
方案一就很少說了,建立web工程,壓力測試咱們用的apache的ab test。
方案二:
個人想法是一次性建立X個線程模擬X個併發,而後每一個線程循環Y次,每次發起一個hessian的請求,每次執行一次hessian請求,我會建立一個對象收集信息;而後建立一個監控線程,監控這些線程是否都執行完了,若是執行完了就對收集到的數據進行分析。
信息收集對象:java
public class StopWatch { private long startTime; private long endTime; // 一次hessian請求耗時 private long elapsedTime; //成功失敗 private boolean status; public StopWatch(){ this.startTime = 0L; this.endTime = 0L; this.elapsedTime = 0L; this.status = false; } public long getStartTime() { return startTime; } public void setStartTime(long startTime) { this.startTime = startTime; } public long getEndTime() { return endTime; } public void setEndTime(long endTime) { this.endTime = endTime; } public boolean isStatus() { return status; } public void setStatus(boolean status) { this.status = status; } public long getElapsedTime() { return elapsedTime; } public void setElapsedTime(long elapsedTime) { this.elapsedTime = elapsedTime; } }
壓力測試主程序:web
public class StressTest { private final static String url1 = "XXXXXXX"; public static void main(String args[]) throws Throwable{ HessianProxyFactory hpf = new HessianProxyFactory(); hpf.setChunkedPost(false); final UserManagerRemote userManagerRemote = (UserManagerRemote)hpf.create(url1); // 建立收集信息list final List<StopWatch> list = new ArrayList<StopWatch>(10000); //線程數量 int count = 150; final long start1 = System.currentTimeMillis(); //建立循環柵欄,初版我是建立了一個監控線程 final CyclicBarrier barrier = new CyclicBarrier(count, new Runnable(){ @Override public void run() { long end1 = System.currentTimeMillis(); //分析收集到的信息 analyseStopWatch(list, (end1-start1)); } } ); for(int i=0; i<count; i++){ Thread t = new Thread( new Runnable(){ @Override public void run() { for(int j=0; j<100; j++){ //建立收集信息對象 StopWatch sw = new StopWatch(); long startTime = System.currentTimeMillis(); sw.setStartTime(startTime); try { userManagerRemote.get(****L); sw.setStatus(true); } catch (Throwable e) { sw.setStatus(false); } long endTime = System.currentTimeMillis(); sw.setEndTime(endTime); sw.setElapsedTime(endTime-startTime); //將收集信息對象添加到list中 list.add(sw); } try { barrier.await(); } catch (InterruptedException e) { e.printStackTrace(); } catch (BrokenBarrierException e) { e.printStackTrace(); } } } ); if(i < 29){ t.setDaemon(true); } t.start(); } } private static void analyseStopWatch(List<StopWatch> stopWatchs, long totalSpend){ System.out.println("size = "+stopWatchs.size()); Collections.sort(stopWatchs, new Comparator<StopWatch>(){ @Override public int compare(StopWatch o1, StopWatch o2) { Long elapsedTime1 = o1.getElapsedTime(); Long elapsedTime2 = o2.getElapsedTime(); return elapsedTime1.compareTo(elapsedTime2); } }); int size = stopWatchs.size(); long min = 0; for(StopWatch sw : stopWatchs){ if(sw.getElapsedTime() > 0){ min = sw.getElapsedTime(); break; } } System.out.println("spend time min = "+min+"MS | max = "+stopWatchs.get(size-1).getElapsedTime()+"MS"); int failCount = 0; long spendTime = 0L; for(StopWatch sw : stopWatchs){ spendTime +=sw.getElapsedTime(); if(!sw.isStatus()){ failCount += 1; } } System.out.println("total spend time = "+totalSpend+"MS"); System.out.println("total request count = "+size); double d1 = totalSpend; double d2 = size; double averageST = d1/d2; System.out.println("average spend time = "+spendTime/size+"MS"); System.out.println("Transaction Per Second = "+(1000/averageST)); System.out.println("total fail count = "+failCount); } }