HTTP性能測試工具wrk安裝及使用

来源:https://www.cnblogs.com/guoew/archive/2019/02/14/10381115.html
-Advertisement-
Play Games

wrk 是一個很簡單的 http 性能測試工具,沒有Load Runner那麼複雜,他和 apache benchmark(ab)同屬於HTTP性能測試工具,但是比 ab 功能更加強大,並且可以支持lua腳本來創建複雜的測試場景。 wrk 的一個很好的特性就是能用很少的線程壓出很大的併發量,原因是它 ...


wrk 是一個很簡單的 http 性能測試工具,沒有Load Runner那麼複雜,他和 apache benchmark(ab)同屬於HTTP性能測試工具,但是比 ab 功能更加強大,並且可以支持lua腳本來創建複雜的測試場景。

wrk 的一個很好的特性就是能用很少的線程壓出很大的併發量,原因是它使用了一些操作系統特定的高性能 io 機制, 比如 select, epoll, kqueue 等.

其實它是復用了 redis 的 ae 非同步事件驅動框架. 確切的說 ae 事件驅動框架並不是 redis 發明的, 它來至於 Tcl的解釋器 jim, 這個小巧高效的框架, 因為被 redis 採用而更多的被大家所熟知。

wrk 是開源的, 代碼在 github 上. https://github.com/wg/wrk

安裝

wrk 支持大多數類 UNIX 系統,不支持 windows。需要操作系統支持LuaJIT 和 OpenSSL,不過不用擔心,大多數類 Unix 系統都支持。安裝 wrk 非常簡單,只要從 github 上下載 wrk 源碼,在項目路徑下執行 make 命令即可。

Unbuntu/Debian下的安裝
sudo apt-get install build-essential libssl-dev git -y
git clone https://github.com/wg/wrk.git wrk
cd wrk
make
# 把生成的wrk移到一個PATH目錄下麵, 比如
sudo cp wrk /usr/local/bin
CentOs/RedHat/Fedora 下的安裝
sudo yum groupinstall 'Development Tools'
sudo yum install openssl-devel
sudo yum install git
git clone https://github.com/wg/wrk.git wrk
cd wrk
make
# 把生成的 wrk 移到一個 PATH 目錄下麵, 比如
sudo cp wrk /usr/local/bin
mac 下快捷安裝
brew install wrk

基本使用

wrk -t12 -c400 -d30s http://127.0.0.1:8080/index.html

使用 12 個線程運行 30 秒, 400 個 http 併發

命令行選項

使用方法: wrk <選項> <被測HTTP服務的URL>
  Options:
    -c, --connections <N>  跟伺服器建立並保持的 TCP 連接數量
    -d, --duration    <T>  壓測時間
    -t, --threads     <N>  使用多少個線程進行壓測
    -s, --script      <S>  指定 Lua 腳本路徑
    -H, --header      <H>  為每一個 HTTP 請求添加 HTTP 頭
        --latency          在壓測結束後,列印延遲統計信息
        --timeout     <T>  超時時間
    -v, --version          列印正在使用的 wrk 的詳細版本信息

  <N>代表數字參數,支持國際單位 (1k, 1M, 1G)
  <T>代表時間參數,支持時間單位 (2s, 2m, 2h)

做一次簡單壓測,分析下結果

wrk -t8 -c200 -d30s --latency  "http://www.bing.com"

輸出:
Running 30s test @ http://www.bing.com
  8 threads and 200 connections
  Thread Stats   Avg      Stdev     Max   +/- Stdev
    Latency    46.67ms  215.38ms   1.67s    95.59%
    Req/Sec     7.91k     1.15k   10.26k    70.77%
  Latency Distribution
     50%    2.93ms
     75%    3.78ms
     90%    4.73ms
     99%    1.35s
  1790465 requests in 30.01s, 684.08MB read
Requests/sec:  59658.29
Transfer/sec:     22.79MB

以上使用 8 個線程 200 個連接,對 bing 首頁進行了 30 秒的壓測,並要求在壓測結果中輸出響應延遲信息。以下對壓測結果進行簡單註釋:

Running 30s test @ http://www.bing.com (壓測時間30s)
  8 threads and 200 connections (共8個測試線程,200個連接)
  Thread Stats   Avg      Stdev     Max   +/- Stdev
              (平均值) (標準差)(最大值)(正負一個標準差所占比例)
    Latency    46.67ms  215.38ms   1.67s    95.59%
    (延遲)
    Req/Sec     7.91k     1.15k   10.26k    70.77%
    (處理中的請求數)
  Latency Distribution (延遲分佈)
     50%    2.93ms
     75%    3.78ms
     90%    4.73ms
     99%    1.35s (99分位的延遲)
  1790465 requests in 30.01s, 684.08MB read (30.01秒內共處理完成了1790465個請求,讀取了684.08MB數據)
Requests/sec:  59658.29 (平均每秒處理完成59658.29個請求)
Transfer/sec:     22.79MB (平均每秒讀取數據22.79MB)

可以看到,wrk 使用方便,結果清晰。並且因為非阻塞 IO 的使用,可以在普通的測試機上創建出大量的連接,從而達到較好的壓測效果。

lua腳本壓測

在基本壓測中, 每次發送的請求都是一樣的,很多時候我們壓測的請求體是每個請求都不一樣, 這時候就要寫lua基本來壓測

使用 POST 方法壓測
wrk.method = "POST"
wrk.body   = "foo=bar&baz=quux"
wrk.headers["Content-Type"] = "application/x-www-form-urlencoded"
wrk -t2 -d30s -c1k -s xxx.lua http://192.168.17.1/
每個 request 的參數都不一樣
request = function()
   uid = math.random(1, 10000000)
   path = "/test?uid=" .. uid
   return wrk.format(nil, path)
end

解釋一下 wrk.format 這個函數

wrk.format 這個函數的作用,根據參數和全局變數 wrk 生成一個 http 請求
函數簽名: function wrk.format(method, path, headers, body)
method:http方法,比如GET/POST等
path: url上的路徑(含函數)
headers: http header
body: http body
每個線程先登錄然後壓測
token = nil
path  = "/authenticate"

request = function()
   return wrk.format("GET", path)
end

response = function(status, headers, body)
   if not token and status == 200 then
      token = headers["X-Token"]
      path  = "/resource"
      wrk.headers["X-Token"] = token
   end
end

發送 json

request = function()
    local headers = { }
    headers['Content-Type'] = "application/json"
    body = {
        mobile={"1533899828"},
        params={code=math.random(1000,9999)}
    }

    local cjson = require("cjson")
    body_str = cjson.encode(body)
    return wrk.format('POST', nil, headers, body_str)
end

若運行的時候報錯找不到cjson, 可以安裝 luarocks install lua-cjson

wrk lua腳本說明

wrk 壓測腳本有3個生命周期, 分別是 啟動階段,運行階段和結束階段,每個線程都有自己的lua運行環境

image

啟動階段
function setup(thread)
在腳本文件中實現setup方法,wrk就會在測試線程已經初始化但還沒有啟動的時候調用該方法。wrk會為每一個測試線程調用一次setup方法,並傳入代表測試線程的對象thread作為參數。setup方法中可操作該thread對象,獲取信息、存儲信息、甚至關閉該線程。
-- thread提供了1個屬性,3個方法
-- thread.addr 設置請求需要打到的ip
-- thread:get(name) 獲取線程全局變數
-- thread:set(name, value) 設置線程全局變數
-- thread:stop() 終止線程

運行階段

function init(args)
-- 每個線程僅調用1次,args 用於獲取命令行中傳入的參數, 例如 --env=pre

function delay()
-- 每次請求調用1次,發送下一個請求之前的延遲, 單位為ms

function request()
-- 每次請求調用1次,返回http請求

function response(status, headers, body)
-- 每次請求調用1次,返回 http 響應

init由測試線程調用,只會在進入運行階段時,調用一次。支持從啟動wrk的命令中,獲取命令行參數; delay在每次發送request之前調用,如果需要delay,那麼delay相應時間; request用來生成請求;每一次請求都會調用該方法,所以註意不要在該方法中做耗時的操作; reponse在每次收到一個響應時調用;為提升性能,如果沒有定義該方法,那麼wrk不會解析headers和body; 結束階段

結束階段

function done(summary, latency, requests)

latency.min              -- minimum value seen
latency.max              -- maximum value seen
latency.mean             -- average value seen
latency.stdev            -- standard deviation
latency:percentile(99.0) -- 99th percentile value
latency(i)               -- raw value and count

summary = {
  duration = N,  -- run duration in microseconds
  requests = N,  -- total completed requests
  bytes    = N,  -- total bytes received
  errors   = {
    connect = N, -- total socket connection errors
    read    = N, -- total socket read errors
    write   = N, -- total socket write errors
    status  = N, -- total HTTP status codes > 399
    timeout = N  -- total request timeouts
  }
}

該方法在整個測試過程中只會調用一次,可從參數給定的對象中,獲取壓測結果,生成定製化的測試報告。

線程變數

wrk = {
    scheme  = "http",
    host    = "localhost",
    port    = nil,
    method  = "GET",
    path    = "/",
    headers = {},
    body    = nil,
    thread  = <userdata>,
}

-- 生成整個request的string,例如:返回
-- GET / HTTP/1.1
-- Host: tool.lu
function wrk.format(method, path, headers, body)
-- method: http方法, 如GET/POST/DELETE 等
-- path:   url的路徑, 如 /index, /index?a=b&c=d
-- headers: 一個header的table
-- body:    一個http body, 字元串類型

-- 獲取功能變數名稱的IP和埠,返回table,例如:返回 `{127.0.0.1:80}`
function wrk.lookup(host, service)
-- host:一個主機名或者地址串(IPv4的點分十進位串或者IPv6的16進位串)
-- service:服務名可以是十進位的埠號,也可以是已定義的服務名稱,如ftp、http等

-- 判斷addr是否能連接,例如:`127.0.0.1:80`,返回 true 或 false
function wrk.connect(addr)

原文轉載自: https://www.ruoxiaozh.com/blog/article/84


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • python裝飾器的作用是在不改變原有函數的基礎上,對函數的功能進行增加或者修改。 裝飾器語法是python語言更加優美且避免很多繁瑣的事情,flask中配置路由的方式便是裝飾器。 首先python中一個函數也是可以當做一個對象進行傳遞的。 輸出結果為 上面代碼相當於 帶參數的裝飾器 結果: 相當於 ...
  • Spring MVC從接收請求到返迴響應的流程 客戶端發起request請求,DispatcherServlet接收用戶請求。 DispatcherServlet請求HandlerMapping查找用戶請求對應的Handler(處理器/控制器)。 HandlerMapping將查找到的Handler ...
  • 以下是安裝語句: 然而編寫依賴 的程式,發現無法調用 的`CMake`文件,錯誤提示如下所示: 在 的`issue CMake`安裝時,如果第三方依賴在未指明的情況下,預設均通過 源碼安裝 ,如果無法通過 源碼安裝 ,則無法生成 gRPCTargets.cmake 文件): 因此需要指定第三方依賴是 ...
  • 本文包括組件的下載以及配置,持續更新中…… 1 JDK 官網:https://www.oracle.com 下載:https://www.oracle.com/technetwork/java/javase/downloads/index.html 驗證安裝成功: 2 Python 官網:https ...
  • 日期運算代碼如下: ...
  • 模塊:模塊是一系列常用功能的集合體,一個py文件就是一個模塊1、從文件級別組織程式,更方便管理隨著程式的發展,功能越來越多,為了方便管理,我們通常將程式分成一個個的文件,這樣做程式的結構更清晰,方便管理。這時我們不僅僅可以把這些文件當做腳本去執行,還可以把他們當做模塊來導入到其他的模塊中,實現了功能 ...
  • 春節假期結束了,大家陸續地重回到原來的生活軌道上。假期是一個很好的休息與調節的機會,同時,春節還有辭舊迎新的本意,它是新的輪迴的開端。 在 Python 社區里,剛發生了一件大事,同樣有開啟新紀元的意義:在"Python 之父" Guido van Rossum 宣佈卸任 BDFL(終身仁慈獨裁者) ...
  • 本著做題的心態,上了東莞理工學院的 oj 網;看了一下題目不想動手,在選擇難度的時候發現有些通過率和難度可能存在著某些關係,於是決定爬下這些數據簡單查看一下是否存在關係。 一、新建項目 我是用 Scrapy 框架爬取的(因為剛學沒多久,順便練練手)。首先,先新建 project (下載 Scarpy ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...