基于http协议的api接口对于客户端的身份认证方式以及安全措施[转]
基于http協(xié)議的api接口對于客戶端的身份認證方式以及安全措施
?由于http是無狀態(tài)的,所以正常情況下在瀏覽器瀏覽網(wǎng)頁,服務(wù)器都是通過訪問者的cookie(cookie中存儲的jsessionid)來辨別客戶端的身份的,當客戶端進行登錄服務(wù)器也會將登錄信息存放在服務(wù)器并與客戶端的cookie中的jsessionid關(guān)聯(lián)起來,這樣客戶端再次訪問我們就可以識別用戶身份了。
? ? 但是對于api服務(wù)器,我們不能讓訪問者先登錄再進行訪問這樣不安全,也不友好。所以一般情況我們都是需要客戶端提供一個key(每個key跟用戶是一對一關(guān)聯(lián)的)來識別請求者的身份。
? ? 由HTTP協(xié)議進行通信的數(shù)據(jù)大都是未經(jīng)加密的明文,包括請求參數(shù)、返回值、 cookie、 head等等數(shù)據(jù),因此,外界通過對通信的監(jiān)聽,輕而易舉便可根據(jù)請求和響應(yīng)雙方的格式,偽造請求與響應(yīng),修改和竊取各種信息。所以我們還需要對每次請求進行認證,來判斷發(fā)起請求的是不是就是該用戶,以及請求信息是否被篡改。一般采用對請求信息(請求uri,參數(shù))進行摘要的方法來解決上述問題。由于摘要算法的不可逆性,因此這種方式能夠在一定程度上防止信息被篡改,保障通信的安全。
1、MD5方式
用戶需要先在網(wǎng)站上申請key、secret,然后校驗流程如下:
客戶端:
1.參數(shù)排序
2.將參數(shù)串接起來加上secret,生成待摘要字符串
3.使用MD5等摘要算法生成摘要串signature
4.將key,signature放入header中一并傳給服務(wù)器
服務(wù)器:
1.參數(shù)排序?
2.將參數(shù)串接起來加上secret(通過header中的key在數(shù)據(jù)庫獲取),生成待摘要字符串?
3.使用MD5等摘要算法生成摘要串?
4.服務(wù)端生成的摘要串與客戶端通過header傳遞過來的摘要串進行比較
?
2、HmacSHA256方式
用戶需要先在網(wǎng)站上申請key、secret,然后校驗流程如下:
客戶單:
1.將請求參數(shù)封裝成json字符串,也就是請求體body
2.使用HmacSHA256算法加secret對(請求url+nonce+body)加密生成摘要signature??
3.將key,signature放入header中一并傳給服務(wù)器
服務(wù)器:
1.獲取請求中的請求體body字符串
2.使用HmacSHA256算法加secret(通過header中的key在數(shù)據(jù)庫獲取)對(請求url+nonce+body)加密生成摘要signature?
3.服務(wù)端生成的摘要串與客戶端通過header傳遞過來的摘要串進行比較
注意使用HmacSHA256更加安全,而且我們可以直接將請求參數(shù)封裝成json字符串放入請求體中(也就是通過io流)進行傳遞。
?
實際使用中遇到的問題:
1、帶有下劃線的header被過濾
? ? 當我們在使用HmacSHA256進行認證的時候,需要客戶端將請求key,signature放入header,name設(shè)置為api_key,api_signature,這時出現(xiàn)一個問題是服務(wù)器怎么都獲取不到這兩個值,但是我在本機測試時沒有問題的。后來才想起來是不是由于使用nginx做集群而部分頭被過濾了,查看過后果然是nginx將帶有下劃線的header name過濾了,后來修改nginx配置便可以正常獲取頭信息。不過后來服務(wù)器使用了第三方的動態(tài)加速再次把帶有下劃線的header name給過濾了,為了避免麻煩索性修改程序?qū)eader name中的下劃線都去掉了。
2、確保每次請求唯一性
? ? 由于http都是明文請求,雖然我們可以通過摘要進行一定的安全保證確保信息不被篡改,但是我們無法保證每次請求的唯一性,也就是如果請求數(shù)據(jù)被別人獲取再次請求,此時也可能帶來很嚴重的安全性問題。于是我們便需要用戶在每次請求中設(shè)置一個遞增的參數(shù)nonce,來確保每次請求都是唯一的。不過這樣也可能帶來一個問題,就是如果用戶近乎同時發(fā)起兩個請求a b,由于網(wǎng)絡(luò)阻塞,可能后發(fā)起的b先到達服務(wù)器,這樣當a達到的時候,服務(wù)器會認為a的nonce已過期請求非法而拒絕。為了解決這樣的問題我們允許用戶設(shè)置一個expire值來避免nonce認證帶來的問題。
3、SNI
? ? 由于當時我們有不同的工程(不同的域名,跟不同的證書)位于同一臺服務(wù)器,這樣有的客戶端訪問我們api工程會拋異常,說http握手失敗或者說請求域名與服務(wù)器證書不匹配而失敗。所以我們需要客戶端程序支持sni,它允許客戶端在發(fā)起SSL握手請求時(具體說來,是客戶端發(fā)出SSL請求中的ClientHello階段),就提交請求的Host信息,使得服務(wù)器能夠切換到正確的域并返回相應(yīng)的證書。對于java語言來說jdk7的后續(xù)版本已經(jīng)支持sni,或者使用httpclient 4.3及以后版本都可以很好的支持sni了。
轉(zhuǎn)載于:https://www.cnblogs.com/lobby/p/5361820.html
總結(jié)
以上是生活随笔為你收集整理的基于http协议的api接口对于客户端的身份认证方式以及安全措施[转]的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 仿照支付宝账单界面--listview分
- 下一篇: rtsp摘要认证协议(Response计