Jmeter接口性能測試(二)
一.jmeter內(nèi)存溢出原因及解決方法
jmeter是一個java開發(fā)的開源性能測試工具掌桩,在性能測試中可支持模擬并發(fā)壓測断楷,但有時候當(dāng)模擬并發(fā)請求較大或者腳本運行時間較長時,壓力機會出現(xiàn)卡頓甚至報異衬淘————內(nèi)存溢出,內(nèi)存溢出是指你應(yīng)用的內(nèi)存已經(jīng)不能滿足正常使用了近刘,堆棧已經(jīng)達到系統(tǒng)設(shè)置的最大值,進而導(dǎo)致崩潰橘沥,這事一種結(jié)果描述窗轩;
通常都是由于內(nèi)存泄露導(dǎo)致堆棧內(nèi)存不斷增大,從而引發(fā)內(nèi)存溢出座咆。
在利用jmeter測試過程中痢艺,如果內(nèi)存溢出的話,一般會出現(xiàn)這個提示:java.lang.OutOfMemoryError:?Java?heap?space:意思就是堆內(nèi)存溢出介陶,不夠用了堤舒。
內(nèi)存溢出解決方法:調(diào)整堆內(nèi)存大小
打開jmeter安裝文件(可以用notepad++打開),bin目錄下的jmeter.bat文件,找到set HEAP開頭的內(nèi)容哺呜,根據(jù)具體需要修改堆(heap)值大小舌缤,修改set HEAP=-Xms1g -Xmx1g -XX:MaxMetaspaceSize=256m 為
set HEAP=-Xms1g -Xmx1g -XX:MaxMetaspaceSize=2048m
堆的最大值不要超過物理內(nèi)存的一半,否則容易導(dǎo)致jmeter運行變慢、卡頓甚至內(nèi)存溢出
修改完成后国撵,關(guān)閉文件陵吸,重啟jmeter既可以
二.jmeter 分布式測試
?有時候為了盡量模擬業(yè)務(wù)場景,需要模擬大量的并發(fā)請求介牙,這個時候單臺壓力機就顯得有心無力壮虫。針對這個情況,jmeter的解決方案是支持分布式壓測环础,即將大量的模擬并發(fā)分配給
多臺壓力機囚似,來滿足這種大流量的并發(fā)請求場景。
原理:
1线得、分布式測試中谆构,選擇一臺作為管理機(Contorller),其他的機器作為測試執(zhí)行的代理機(Agent)框都;
2搬素、執(zhí)行測試時,由Contorller通過命令行將測試腳本發(fā)給Agent魏保,然后Agent執(zhí)行測試(不需要啟動GUI)熬尺,同時將測試結(jié)果發(fā)送給Contorller;
3谓罗、測試完成粱哼,可以在Contorller上的監(jiān)聽器里面看到Agent發(fā)來的測試結(jié)果,結(jié)果為多個Agent測試結(jié)果匯總而成檩咱;
步驟
[if !supportLists]1)?[endif]打開Contorller機下jmeter安裝文件下的bin目錄:jmeter.properties文件揭措,搜索remote_hosts=127.0.0.1,將Agent機的IP和端口寫在后面刻蚯,比如:
remote_hosts=127.0.0.1,192.168.74.30:81,192.168.74.31:82
其中192.168.74.30和192.168.74.31為Agent機的IP绊含,每個Agent機之間用英文半角逗號隔開,修改保存炊汹。
Contorller躬充、Agent機中jmeter.properties文件中server.rmi.ssl.disable=true
2)在服務(wù)端(slave)安裝目錄的bin文件夾下執(zhí)行jmeter-server.bat命令啟動jmeter服務(wù)就可以,啟動成功如下圖:
啟動jmeter-server.bat
注意事項
1讨便、保持Contorller和Agent機器的JDK充甚、jmeter以及插件等配置版本一致,host文件內(nèi)容保持一致霸褒;
2伴找、如果測試數(shù)據(jù)有用到CSV或者其他方式進行參數(shù)化,需要將data pools在每臺Agent上復(fù)制一份废菱,且讀取路徑必須保持一致技矮;
3眉反、確保Contorller和Agent機器在同一個子網(wǎng)里面;
4穆役、檢查防火墻是否被關(guān)閉寸五,端口是否被占用(防火墻會影響腳本執(zhí)行和測試結(jié)構(gòu)收集,端口占用會導(dǎo)致Agent機報錯)耿币;
5梳杏、分布式測試中,通過遠程啟動代理服務(wù)器淹接,默認查看結(jié)果樹中的響應(yīng)數(shù)據(jù)為空十性,只有錯誤信息會被報回;
6塑悼、如果并發(fā)較高劲适,建議將Contorller機設(shè)置為只啟動測試腳本和收集匯總測試結(jié)果,在配置文件里去掉Contorller機的IP厢蒜;
7霞势、分布式測試中,如果1S啟動100個模擬請求斑鸦,有5個Agent機愕贡,那么需要將腳本的線程數(shù)設(shè)置為20,否則模擬請求數(shù)會變成500巷屿,和預(yù)期結(jié)果相差太大固以。
一個完整的操作流程,需要先完成某個操作嘱巾,獲得某個值或數(shù)據(jù)信息憨琳,然后才能進行下一步的操作(也就是常說的關(guān)聯(lián)/將上一個請求的響應(yīng)結(jié)果作為下一個請求的參數(shù));
在jmeter中旬昭,可以利用json表達式 篙螟、正則表達式提取器來幫助我們完成這一動作
選中接口→右鍵添加→后置處理器→json提取器
例:獲取積分列表接口響應(yīng)中user_id值 傳給消費積分接口
積分列表響應(yīng):{
????"code": 200,
????"data": {
????????"stat": {
????????????"all_point": "3100",
????????????"all_money": "100"
????????},
????????"count": 1,
????????"list": [
????????????{
????????????????"goods_info": null,
????????????????"mall": {
"address": "萍水西街7號",
"province": "浙江省",
"city": "杭州市",
????????????????????"group_name": "",
"district": "拱墅區(qū)",
"name": "聯(lián)華超市",
????????????????????"is_cooperate": 1
????????????????},
????????????????"channel": "test",
????????????????"created_at": "2019-03-20T03:11:52.000Z",
????????????????"remark": null,
????????????????"user_grade": "Lv1",
????????????????"deleted_at": null,
????????????????"point": 3100,
????????????????"machine_code": null,
????????????????"trade_id": "07ce9951-000f-43d3-ab3f-844163b1dfa0_test",
????????????????"money": 100,
????????????????"updated_at": "2019-03-20T03:11:52.000Z",
????????????????"phone": "15603800797",
????????????????"user_id": 150,
????????????????"mall_id": 214,
????????????????"id": 66,
????????????????"is_use": 1
????????????}
????????]
????},
????"message": ""
}
填寫提取表達式設(shè)置變量
消費積分接口參數(shù)引用變量
成功獲取
$.data.list[0].user_id,JSON中l(wèi)ist 是一個對象數(shù)組稳懒, list[0] 代表取的是第一個數(shù)組的對象闲擦,
.data取的是data的值.list取的是list的值
響應(yīng)非json格式 可可以用正則表達式提取器
[if !supportLists]四、[endif]測試活動
一個接口的參數(shù)傳遞依賴上一個接口的響應(yīng)兩個接口之間需要加入間隔時間
使用測試活動組件
線程組--添加取樣器--測試活動
Duration值為300 ?意思為 A接口完成請求響應(yīng)后300ms场梆,提取到響應(yīng)中userid傳給B接口
五、有時候工作中我們需要對數(shù)據(jù)庫發(fā)起請求或者對數(shù)據(jù)庫施加壓力纯路,那么這時候就需要用到JDBC Request
JDBC Request可以向數(shù)據(jù)庫發(fā)送一個請求(sql語句)或油,一般它需要配合JDBC Connection?
線程組上面右鍵單擊選擇配置元件→?JDBC Connection?
設(shè)置好JDBC連接配置后,添加JDBC請求驰唬,界面如下:
寫要測試的sql語句
運行查看結(jié)果
六顶岸、websocke接口接口測試
線程組-添加取樣器-WebSocket Sampler
[if !supportLists]1.?[endif]Streaming Connection – 選擇這個TCP session要不要保持腔彰,如果勾上標(biāo)識連接會一直存在,如果沒有勾上辖佣,那么得到第一次響應(yīng)后該鏈接就會被關(guān)閉
[if !supportLists]2.?[endif]ws與wss霹抛, ws前綴是WebSocket連接的辨別標(biāo)識,wss前綴是WebSocket安全連接的辨別標(biāo)識卷谈。根據(jù)自己的實際情況填寫
Response Pattern – 采樣器將等待含有該標(biāo)識的消息并繼續(xù)通信(或者直到timeout杯拐,該連接關(guān)閉)4.Close Connection Pattern – 如果服務(wù)器返回的消息含有這樣的字符,就結(jié)束會話世蔗。5.Message Backlog – 定義服務(wù)器返回消息保留的最大長度端逼。
[if !supportLists]七.?[endif]dubbo接口測試
jmeter本身并不支持dubbo接口的測試,需要下載第三方插件污淋,然后將jar包放入jmeter\lib\ext路徑下顶滩,重啟即可。
下載dubbo測試插件
下載地址
啟動jmeter
添加線程組→Sampler→Listener寸爆,dubbo-sample界面如下
各參數(shù)說明如下:
Protocol:注冊協(xié)議礁鲁,包括zookeeper、multicast赁豆、Redis救氯、simple;
Address:注冊地址歌憨,dubbo服務(wù)的IP+Port:
①着憨、當(dāng)使用zk,address填入zk地址务嫡,集群地址使用","分隔甲抖;
②、使用dubbo直連心铃,address填寫直連地址和服務(wù)端口准谚;
Protocol:使用的dubbo協(xié)議,包括dubbo去扣、rmi柱衔、hessian、webservice愉棱、memcached唆铐、redis,根據(jù)自己的協(xié)議類型選擇對應(yīng)的選項即可奔滑;
Timeout:請求超時時間艾岂,單位ms,根據(jù)dubbo具體配置填寫朋其;
Version:版本王浴,dubbo不同版本之間差異較大脆炎,不同版本之間不能互相調(diào)用,這里指定dubbo版本氓辣,是為了方便識別和說明秒裕;
Retries:異常重試次數(shù)(類似這種分布式服務(wù)通信框架,大多都有重試機制钞啸,是為了保證事務(wù)成功率)几蜻;
Cluster:集群類型,包括failover爽撒、failfast入蛆、failsafe、failback硕勿、failking哨毁;
Group:組類型,如果有的話源武,根據(jù)配置填寫即可扼褪;
Connections:連接數(shù),同上粱栖,根據(jù)配置填寫话浇;
Async:服務(wù)處理類型,包括sync(同步)闹究、async(異步)幔崖,根據(jù)配置填寫;
Loadbalance:負載均衡策略渣淤,包括random(隨機)赏寇、roundrobin(輪詢)、leastactive(最少活躍數(shù))价认、consistenthash(一致性哈希)嗅定;
Interface:接口名(因為dubbo服務(wù)大多是開發(fā)根據(jù)規(guī)范自行命名的,因此這里需要填寫完整的接口名+包名)用踩;
Method:當(dāng)前接口下的方法名渠退,按照開發(fā)提供的API文檔填寫即可休蟹;
Args:接口報文峰尝,根據(jù)API文檔填寫芯义,如上圖所示忍燥,添加輸入行,輸入對應(yīng)的參數(shù)類型和值即可(參數(shù)類型和值如何定義填寫抵知,請參考上面的鏈接)堤魁;
①耕魄、paramType:參數(shù)支持任何類型晨川,包裝類直接使用java.lang下的包裝類证九,小類型使用:int、float共虑、shot愧怜、double、long妈拌、byte拥坛、boolean、char尘分,自定義類使用類完全名稱猜惋;
②、paramValue:基礎(chǔ)包裝類和基礎(chǔ)小類型直接使用值培愁,例如:int為1著摔,boolean為true等,自定義類與List或者Map等使用json格式數(shù)據(jù)定续;
[if !supportLists]8.?[endif]函數(shù)助手
函數(shù)助手的話谍咆,可以按照規(guī)則生成一些參數(shù),比如說隨機數(shù)取當(dāng)前時間私股,最常用的就是這兩種摹察。
隨機數(shù)__Random,可以在你指定的一個范圍內(nèi)取隨機值
取當(dāng)前時間__time倡鲸,如果在有一些需要傳時間的情況下可以使用供嚎,日期格式是:yyyy-MM-dd HH:mm:ss?? 年-月-日-小時:分鐘:秒
取唯一id,__UUID峭状,這個就是每次會生成一個隨機的uuid克滴,都是唯一的。