k6是GitHub上提供的開源負載測試工具。它是用Go編寫的,並運行用JavaScript編寫的測試腳本。它受到了開發人員,測試人員和DevOps團隊的強烈興趣,並擁有超過4400名GitHub明星。k6是命令行驅動的,測試結果輸出到stdout或結果分析工具,如Load Impact Insights。css
JMeter也是一個開源負載測試工具,已存在多年。它很是受歡迎,擁有數千名用戶。它是一個Java應用程序,JMeter GUI用於建立測試腳本。此外,一些腳本語言可用於編寫JMeter函數,包括Java,Groovy和JavaScript。Groovy已成爲推薦的默認選項。可是,只能從命令行執行負載測試運行。java
在「大衛與歌利亞」的方式中,讓咱們看一下在k6中比在JMeter中更容易作的事情的幾個例子。程序員
在JMeter中:shell
添加Beanshell Postprocessor做爲請求的子項,返回您要查找的響應。瀏覽器
將代碼 vars.put(「response」, new String(data));
放入PostProcessor的「腳本」區域。 服務器
請根據${response}
須要參考提取的值 。網絡
在k6中,使用如下測試腳本代碼:架構
let response = http.get(「http://javame.cnblogs.com/」);
在這兩種狀況下,數據最終都在響應變量中。主要區別在於您必須在JMeter中向請求添加Beanshell PostProcessor,而後才能添加代碼段。
在JMeter中:併發
在測試下建立一個新的Response Assertion。在斷言的「要測試的響應字段」部分中,確保選中「忽略狀態」框。負載均衡
而後,您能夠添加其餘斷言,例如將「要測試的響應字段」中的無線電設置爲「響應代碼」,並將「要測試的模式」設置爲404。
圖1:顯示如何設置響應斷言的JMeter GUI。
在k6中,使用如下測試腳本代碼:
let response = http.get(「http://some.url/」); check(res, { "Status is 404": (r) => r.status === 404 });
這裏的主要區別在於,在JMeter中執行此操做須要您單擊GUI並在輸入字段中填入值,而使用k6則須要編寫幾行代碼。您能夠在版本控制系統(VCS)中輕鬆跟蹤和管理k6 JavaScript加載測試代碼,就像您的應用程序代碼同樣。
例如,假設您要調用logTransaction()
150個不一樣測試配置中的一個文件中定義的 函數。
在JMeter中:
將該行添加 beanshell.sampler.init=BeanShellSampler.bshrc
到user.properties文件(位於JMeter安裝的「bin」文件夾中)。
將logTransaction函數放在BeanShellSampler.bshrc文件中(相同位置,JMeter的「bin」文件夾)。
下次啓動JMeter時,您能夠在任何腳本中從任何Beanshell Sampler調用該函數。
在k6:
將logTransaction()函數放在JavaScript文件中,例如「logTransaction.js」
使用如下語句在任何腳本中導入該函數:從「/path/to/logTransaction.js」導入{logTransaction};
在k6中,任何Javascript文件均可以直接用做可導入模塊,它容許您以任何方式組織文件。您還能夠直接經過網絡導入模塊:
import { logTransaction } from "s3.amazonaws.com/path/to/logTransaction.js";
除了標準的ES6 JavaScript API以外,k6還捆綁了API來處理Cookie,加密,編碼,環境變量,HTML表單,HTML解析,多部分請求,TLS客戶端證書,TLS密碼和版本等等。
例如,您可能但願使用兩個參數測試servlet:X和Y,其中X和Y是0到100之間的隨機數。您須要一個嵌套循環,以下所示:
for(int x = 0 ; x <= 100 ; x ++) for(int y = 0 ; y <= 100 ; y ++) servlet ?param1 = x &param2 = y
在JMeter中:
您的架構可能以下所示:
Thread Group User Defined Variables maxX = 100 maxY = 100 Loop Controller X Loop Count: ${__BeanShell(Integer.parseInt(vars.get("maxX"))+1)} Counter X Start: 0 Increment: 1 Maximum: ${maxX} Reference Name: loopX Loop Controller Y Loop Count: ${__BeanShell(Integer.parseInt(vars.get("maxY"))+1)} Counter Y Start: 0 Increment: 1 Maximum: ${maxY} Reference Name: loopY YOUR HTTP Request servlet?param1=${loopX}¶m2=${loopY} . . .
在k6:
使用如下腳本代碼:
for(var x = 0 ; x <= 100 ; x ++) for(var y = 0 ; y <= 100 ; y ++) http.get(「http://some.domain/servlet?param1 =」+ x +「¶m2=」+ y);
固然,執行更復雜的邏輯分支是基於GUI的方法與直接在代碼中編寫邏輯相比常常變得很是笨重的地方。k6解決方案與用於描述問題的僞代碼很是類似。
咱們一般但願並行發出多個請求,就像瀏覽器在獲取網頁時所作的那樣。這使得服務器上的壓力比每一個虛擬用戶一次只發出一個請求要多得多。
在JMeter中:
JMeter提供同步計時器,容許對請求進行分組,以便它們能夠在同一時刻執行。只需在測試計劃中添加同步計時器,並確保:
它在兩個請求中都處於同一級別
線程組中的虛擬用戶數> = =同步計時器中設置的數量
在k6:
使用此 http.batch()
功能可並行發出多個請求。例如:
http.batch([ "http://test.loadimpact.com", "http://test.loadimpact.com/style.css", "http://test.loadimpact.com/images/logo.png" ]);
上述「解決方案」不具備100%的可比性。在JMeter狀況下,咱們仍然只容許每一個虛擬用戶(VU)一次發出一個請求。這意味着JMeter VU不是「真實用戶」的徹底準確模型。單我的類用戶將使用他們的Web瀏覽器同時發出多個請求,而JMeter VU一次只發出一個請求。
相反,JMeter所作的是同步VU,以便它們在同一時間發出請求。(對我來講彷佛不太有用 - 總吞吐量可能會降低,由於某些VU必須等待其餘VU完成請求)。
另外一方面,在所示的示例中,k6將容許每一個VU打開三個併發TCP鏈接,所以可以並行獲取這三個項目,就像Web瀏覽器同樣。這意味着在k6狀況下,100個VU能夠並行獲取300個項目。在Jmeter狀況下,100 VU將並行獲取100個項目。(注意:還有一個名爲Parallel Controller的 JMeter擴展可用於建立並行請求)。
推薦閱讀: