前言
? ? ? ? ?廢話不多說,就是姐姐我在最近的兩個前后端分離的項目做接口測試,遇到了登錄驗證的問題,就是所謂的XSRF驗證問題。現在提筆將配置方法總結到文中。
一、概念學習(ps:如果都知曉,可以跳過該步驟,直接去二章節,因為我也是copy的哈哈哈)
1.明確概念:cookie和session
①cookie數據存放在客戶的瀏覽器上,session數據放在服務器上。
②cookie不是很安全,別人可以分析存放在本地的cookie并進行cookie欺騙,考慮到安全應當使用session。
③session會在一定時間內保存在服務器上。當訪問增多,會比較占用你服務器的性能考慮到減輕服務器性能方面,應當使用cookie。
④單個cookie保存的數據不能超過4K,很多瀏覽器都限制一個站點最多保存20個cookie。
⑥所以將登錄信息,個人賬戶資料等重要信息存放為session;其他不會泄露個人隱私的信息如果需要保留,可以放在cookie中。
2.Cookie
添加方式:線程組-配置元件-HTTP Cookie 管理器,如下圖:
Cookie的傳遞流程:
1.瀏覽器向某個URL發起HTTP請求(可以是任何請求,比如GET一個頁面、POST一個登錄表單、DELETE某條評論、PUT某條更新等)
2.對應的服務器收到該HTTP請求,并計算應當返回給瀏覽器的HTTP響應(HTTP響應包括請求頭和請求體兩部分)
3.在響應頭加入Set-Cookie字段,它的值是要設置的Cookie。
4.瀏覽器收到來自服務器的HTTP響應。
5.瀏覽器在響應頭中發現Set-Cookie字段,就會將該字段的值保存在內存或者硬盤中(Set-Cookie字段的值可以是很多項Cookie,每一項都可以指定過期時間Expires。 默認的過期時間是用戶關閉瀏覽器時。)
6.瀏覽器下次給該服務器發送HTTP請求時, 會將服務器設置的Cookie附加在HTTP請求的頭字段Cookie中。(瀏覽器可以存儲多個域名下的Cookie,但只發送當前請求的域名曾經指定的Cookie, 這個域名也可以在Set-Cookie字段中指定)。)
7.服務器收到這個HTTP請求,發現請求頭中有Cookie字段, 便知道之前就和這個用戶打過交道了.
8.過期的Cookie會被瀏覽器刪除。
總之,服務器通過Set-Cookie響應頭字段來指示瀏覽器保存Cookie, 瀏覽器通過Cookie請求頭字段來告訴服務器之前的狀態。 Cookie中包含若干個鍵值對,每個鍵值對可以設置過期時間。
3.Session
添加方式:線程組-前置處理器 -HTTP URL 重寫修飾符,如下圖:
session的傳遞流程:
1.用戶提交包含用戶名和密碼的表單,發送HTTP請求。
2.服務器驗證用戶發來的用戶名密碼。
3.如果正確則把當前用戶名(通常是用戶對象)存儲到redis中,并生成它在redis中的ID。這個ID稱為Session ID,通過Session ID可以從Redis中取出對應的用戶對象, 敏感數據(比如authed=true)都存儲在這個用戶對象中。
4.設置Cookie為sessionId=xxxxxx|checksum并發送HTTP響應, 仍然為每一項Cookie都設置簽名。
5.用戶收到HTTP響應后,便看不到任何敏感數據了。在此后的請求中發送該Cookie給服務器。
6.服務器收到此后的HTTP請求后,發現Cookie中有SessionID,進行放篡改驗證。
7.如果通過了驗證,根據該ID從Redis中取出對應的用戶對象, 查看該對象的狀態并繼續執行業務邏輯。實現上述過程,在Web應用中可以直接獲得當前用戶。 相當于在HTTP協議之上,通過Cookie實現了持久的會話。這個會話便稱為Session。
4.Token認證
1、支持跨域訪問: Cookie是不允許垮域訪問的,這一點對Token機制是不存在的,前提是傳輸的用戶認證信息通過HTTP頭傳輸。(垮域訪問:兩個域名之間不能跨過域名來發送請求或者請求數據)
2、無狀態(也稱:服務端可擴展行):Token機制在服務端不需要存儲session信息,因為Token 自身包含了所有登錄用戶的信息,只需要在客戶端的cookie或本地介質存儲狀態信息.
3、更適用CDN: 可以通過內容分發網絡請求你服務端的所有資料(如:javascript,HTML,圖片等),而你的服務端只要提供API即可.
4、去耦: 不需要綁定到一個特定的身份驗證方案。Token可以在任何地方生成,只要在你的API被調用的時候,你可以進行Token生成調用即可.
5、更適用于移動應用: 當你的客戶端是一個原生平臺(iOS, Android,Windows 8等)時,Cookie是不被支持的(你需要通過Cookie容器進行處理),這時采用Token認證機制就會簡單得多。
6、CSRF:因為不再依賴于Cookie,所以你就不需要考慮對CSRF(跨站請求偽造)的防范。
7、性能: 一次網絡往返時間(通過數據庫查詢session信息)總比做一次HMACSHA256計算 的Token驗證和解析要費時得多.
8、不需要為登錄頁面做特殊處理: 如果你使用Protractor 做功能測試的時候,不再需要為登錄頁面做特殊處理.
9、基于標準化:你的API可以采用標準化的 JSON Web Token (JWT). 這個標準已經存在多個后端庫(.NET, Ruby, Java,Python, PHP)和多家公司的支持(如:Firebase,Google, Microsoft).
使用Token的方法
不是在每一次請求時提供用戶名和密碼的憑證。我們可以讓用戶通過token交換憑證(we can allow the client to exchange valid credentials for a token),這個token提供用戶訪問服務器的權限。Token通常比密碼更加長而且復雜。比如說,JWTs通常會應對長達150個字符。一旦獲得了token,在每次調用API的時候都要附加上它。然后,這仍然比直接發送賬戶和密碼更加安全,哪怕是HTTPS。
把token想象成一個安全的護照。你在一個安全的前臺驗證你的身份(通過你的用戶名和密碼),如果你成功驗證了自己,你就可以取得這個。當你走進大樓的時候(試圖從調用API獲取資源),你會被要求驗證你的護照,而不是在前臺重新驗證。
獲取一個Token我們需要做的第一件事就是讓客戶端通過他們的賬號密碼交換token。這里有2種可能的方法在RESTful API里面。第一種是使用POST請求來通過驗證,使服務端發送帶有token的響應。除此之外,你可以使用GET請求,這需要他們使用參數提供憑證(指URL),或者更好的使用請求頭。
二、實戰演練
xxx項目,后臺語言-java,機制為cookie+session驗證
測試計劃構建步驟:
1.添加線程組
2.在線程組下添加HTTP Cookie 管理器
3.在線程組下HTTP請求默認值,在這里配置協議、IP、端口號
4.在線程組下添加全部請求的察看結果樹
5.在線程組下添加HTTP請求1(可以用ID+接口名來重命名)
6.在HTTP請求1添加HTTP信息頭管理器
7.在HTTP請求1添加當前請求的察看結果樹
8.重復步驟5-7可以多添加幾個接口
各步驟配置詳情:
1.HTTP Cookie 管理器
①jmeter的bin目錄下jmeter.properties的文件,開放這個:CookieManager.save.cookies=true
②抓包工具查看cookie命名,若命名為tt_sessionid,或者通過前臺debug查看(我是通過debug看的)
③則在整個測試計劃需要獲取的cookie值為${COOKIE_tt_sessionid},前面的COOKIE為jmeter命名規則
2.HTTP請求默認值
3.HTTP請求1
4.在HTTP請求1下的HTTP信息頭管理器
配置好了,大膽地run run run,當你看到如下畫面,證明你成功了!
xx項目,后臺語言-python,機制為session驗證
測試計劃構建步驟(無HTTP Cookie 管理器):
1.添加線程組
2.在線程組下HTTP請求默認值,在這里配置協議、IP、端口號
3.在線程組下添加全部請求的察看結果樹
4.在線程組下添加HTTP請求1(可以用ID+接口名來重命名)
5.在HTTP請求1添加HTTP信息頭管理器
6.在HTTP請求1添加當前請求的察看結果樹
7.重復步驟4-6可以多添加幾個接口
各步驟配置詳情:
1.get/delete方法的HTTP信息頭管理器
2.post/put方法的HTTP信息頭管理器
異常錯誤:
1.jmeter報錯“org.apache.http.NoHttpResponseException”
就是第一個通過,后面全失敗,報錯為:? org.apache.http.NoHttpResponseException: xxxxIP?failed to respond
原因:在JMeter下,發送http 請求時,默認選擇了use keepAlive(Keep-Alive通俗地講,就是所謂的持久連接,對于http這種大量的短連接的服務來說,開啟持久連接的好處可節省大量的TCP連接過程的開銷,據apache的官方文檔稱對包含大量圖片的HTML文檔造成的延時起到50%的加速作用),這個是連接協議,JMeter坑就在這里,默認勾選了這個(如果不勾選的話,也不會保存),但其配置JMeter.properties中的時間設置默認卻是注銷的,不會等待,一旦連接空閑,則立即斷開了,導致壓測中出現了事務失敗的情形。
可訪問https://wiki.apache.org/jmeter/JMeterSocketClosed查看官網解釋
解決方法:
①找到jmeter安裝路徑bin下的jmeter.properties,編輯,設置httpclient4.idletimeout=,注意單位是ms,設置成覺得合理的時間,一般可設置成10-60s(表示連接空閑10s后才會斷開)。修改完成后再次壓測,錯誤就沒出現。
例:httpclient4.idletimeout=3000,意思是連接空閑3s才會斷開
②去掉勾選 Use KeepAlive (日常在瀏覽器查看請求頭也可看到KeepAlive)
再來run時,問題解決,我在這糾纏了好久,哇哇哇,是不是很開森。。。
2.服務器相應數據中文為亂碼
看到這不認識的符號,是不是很懵逼,說好的中文名字呢???
別著急,都是字符集惹的禍
解決辦法:
再來run,是不是中文名字回來了
至此,over!