(題圖: 某偏遠山溝小河 effected by google photos)apache
以前知道通常網站性能能夠經過 LoadRunner, JMeter, QTP 等相應的軟件進行測試, 印象中本科學習 「軟件測試」 這門課程時安裝並使用過, LoadRunner等不是一個小軟件, 安裝不是那麼的容易.vim
最近發現Apache還有一款小巧玲瓏的工具能夠直接用來作壓力測試, 相關文檔能夠參見 Apache ab 官網.windows
Mac 下自帶(具體記不清是由於我安裝了Apache仍是系統自帶的了)了這個 ab
工具(Apache HTTP server benchmarking tool), ab 我猜應該就是 Apache Benchmarking
的縮寫吧?微信
ab 用法
ab 命令參數以下,markdown
ab [ -A auth-username:password ] [ -b windowsize ] [ -B local-address ] [ -c concurrency ] [ -C cookie-name=value ] [ -d ] [ -e csv-file ] [ -f protocol ] [ -g gnuplot-file ] [ -h ] [ -H custom-header ] [ -i ] [ -k ] [ -l ] [ -m HTTP-method ] [ -n requests ] [ -p POST-file ] [ -P proxy-auth-username:password ] [ -q ] [ -r ] [ -s timeout ] [ -S ] [ -t timelimit ] [ -T content-type ] [ -u PUT-file ] [ -v verbosity] [ -V ] [ -w ] [ -x <table>-attributes ] [ -X proxy[:port] ] [ -y <tr>-attributes ] [ -z <td>-attributes ] [ -Z ciphersuite ] [http[s]://]host- name[:port]/path
不過經常使用的, 也就是, -n
跟請求數, -c
跟併發數.cookie
-n requests Number of requests to perform -c concurrency Number of multiple requests to make at a time
在對網站進行測試的時候, 可能須要登陸態進行測試, 能夠經過 -C
加 Cookie的方式進行測試, 測試以前, 最好確認這個命令用法是否正確, 只用1個請求看看響應的長度是否一致(能夠經過 與 curl
命令的結果進行對比).併發
例如, 經過 ab -c 1 -n 1 -C 'cookiedata=xxx' "http://shangtongdai.yxapp.xyz/loans"
獲得的 Document Length: 53218 bytes
和用 curl -b 'cookiedata=xxx' "http://shangtongdai.yxapp.xyz/loans"
獲得的Content-Length: 53218
一致.app
而後進行完整的測試, 能夠獲得詳細的結果報告.curl
# 200併發,一共10000請求 ab -c 200 -n 10000 -C 'cookiedata=xxx' "http://shangtongdai.yxapp.xyz/loans" # 結果 This is ApacheBench, Version 2.3 <$Revision: 1663405 $> Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/ Licensed to The Apache Software Foundation, http://www.apache.org/ Benchmarking shangtongdai.yxapp.xyz (be patient) Completed 1000 requests Completed 2000 requests Completed 3000 requests Completed 4000 requests Completed 5000 requests Completed 6000 requests Completed 7000 requests Completed 8000 requests Completed 9000 requests Completed 10000 requests Finished 10000 requests Server Software: Tengine/2.1.1 Server Hostname: shangtongdai.yxapp.xyz Server Port: 80 Document Path: /loans Document Length: 53218 bytes Concurrency Level: 200 Time taken for tests: 53.098 seconds Complete requests: 10000 Failed requests: 0 Total transferred: 534570000 bytes HTML transferred: 532180000 bytes Requests per second: 188.33 [#/sec] (mean) Time per request: 1061.967 [ms] (mean) Time per request: 5.310 [ms] (mean, across all concurrent requests) Transfer rate: 9831.59 [Kbytes/sec] received Connection Times (ms) min mean[+/-sd] median max Connect: 0 1 1.8 1 39 Processing: 38 1055 344.1 1046 2964 Waiting: 37 1051 345.5 1043 2959 Total: 39 1056 344.4 1047 2969 Percentage of the requests served within a certain time (ms) 50% 1047 66% 1170 75% 1252 80% 1311 90% 1477 95% 1657 98% 1860 99% 1986 100% 2969 (longest request)
ab post 「bug」
在某個場景下, 我須要對其中一個post的接口進行測試.
根據 ab 的 mannual 看到 post 時候, 須要將post的data用文件保存, 而後經過參數 -p postdata.file
傳輸.tcp
但在實際ab進行測試時, 發現返回的結果異常, 正常狀況下 response 的size比經過ab返回的response size大得多, 說明經過ab發送的http請求失敗了.
通過tcpdump抓包最後發現 ab
請求無效的緣由是: postdata 文件會多一個字符(文件末尾的換行符), 致使server端的 form 解析失敗, 於是返回異常的response.
這個坑是vim的默認配置致使的, vim默認會在文件末尾添加一個文件結束符, vim 默認配置 'endofline' 'eol' boolean (default on)
, 能夠經過 set noendofline
解決.
實際過程當中,(去掉文件末尾的換行符能夠解決), 或者將postdata多添加一個參數能夠解決(這個參數server端沒有用到時多餘的, form能夠正常解析, 所以 response 正常了).
下面來重現一下這個過程, 拿百度爲例吧.
➜ com~apple~CloudDocs$ cat postdata.txt a=65&b=66
用 curl 執行, curl -i -H "Content-Type: application/x-www-form-urlencoded" -d "a=65&b=66" "http://www.baidu.com"
.
用 ab 執行, ab -c 1 -n 1 -T 'application/x-www-form-urlencoded;' -p postdata.txt 'http://www.baidu.com/'
抓包獲得如下結果
用 curl 執行並抓包的結果是:
發現HTTP協議版本號不一樣, UA不一樣, Content-Length不一樣.
剛開始還覺得是ab的bug, 最後發現確實是 Content-Length
相差1, 而多的這個字符換行符致使了 server 段的 form 填充失敗(上例中體現不了, 反正post百度無效的請求).
➜ com~apple~CloudDocs$ wc -c postdata.txt 10 postdata.txt ➜ com~apple~CloudDocs$ ll postdata.txt -rw-r--r--@ 1 tanglei staff 10B 4 11 21:26 postdata.txt ➜ com~apple~CloudDocs$ cat postdata1.txt a=65&b=66% ➜ com~apple~CloudDocs$ wc -c postdata1.txt 9 postdata1.txt ➜ com~apple~CloudDocs$ ll postdata1.txt -rw-r--r--@ 1 tanglei staff 9B 4 11 21:26 postdata1.txt
最後去掉postdata文件末尾的結束符後, 得以成功.
本文分享自微信公衆號 - 程序猿石頭(tangleithu)。
若有侵權,請聯繫 support@oschina.cn 刪除。
本文參與「OSC源創計劃」,歡迎正在閱讀的你也加入,一塊兒分享。