动态

详情 返回 返回

RESTful接口的csrf防禦考慮 - 动态 详情

關於RESTful標準服務是否需要方法跨站請求攻擊,網上有很多討論,總結下來核心的關鍵點在於是否使用了cookie,而就目前而言,REST標準下的服務接口,即便API做到了無狀態,用户令牌(Token)也很經常會放到localStorage或者cookie中,這些情況下本質上與RESTful的無狀態標準定義不衝突,但是必須要考慮XSS(跨站腳本攻擊)、CSRF(跨站請求攻擊)的防範需求了。

Cookie中有個HttpOnly的屬性,如果沒有設置為true,使用js腳本可以拿到其中存儲的內容,惡意頁面可能會通過嵌入代碼拿到用户未保護的cookie值,如果存儲的是用户敏感身份信息,並且網站服務沒有更多的保護措施,那麼黑客便可以偽造用户的身份為所欲為了。localStorage同樣存在XSS安全風險,因此不應用來存儲敏感數據。

CSRF在用户打開了黑客的惡意頁面時發生,通過簡單的嵌入<img>標籤或者iframe,能在用户無感知的情況下使用用户的cookie數據訪問其他網站的GET、POST接口服務,雖然黑客得不到被保護cookie中的值,甚至無法解析響應報文內容,但是接口的隨意偽造調用帶來的風險巨大。因此一般情況下網站服務需要考慮csrf的安全防護。

但如果是REST標準的API服務方呢?

在REST標準下,GET方法不會產生數據修改,最多會產生一些額外的日誌數據和網絡流量,因此對於GET請求無需對csrf設防。而POST方法需要考慮其允許的Content-Type,如果僅支持application/json格式,那麼嵌入的iframe頁面中的form提交產生的form-data或者form-urlencoded請求無法成功,而使用XmlHttpRequest發起的post請求,因為瀏覽器的同源策略,又會要求發起預檢(preflight)請求,因此也不能夠成功。而其他Patch、Delete、Put方法的請求,既不能通過iframe達成,也無法跳過預檢請求步驟,因此在僅支持application/json的POST情況下,RESTful接口提供服務方可以不用考慮csrf安全防護。

凡事無絕對,在網上有一篇通過flash達成對application/json接口進行csrf攻擊的方法 : 服務的校驗Content-Type,只接收application/json格式的CSRF繞過方法。
不過考慮到主流瀏覽器對flash的支持均已下線,怎麼説呢...

Otherwise,就不得不考慮防禦下csrf攻擊了。如果面臨這種需求,可以從以下方法着手:

  1. 驗證請求Referer,對於使用非IE6非hack版本奇葩瀏覽器的正常用户,攔截下請求的Referer,只允許受信任的來源方發起的請求,基本上就是改動最小效果最快的csrf防禦手段了。
  2. 考慮下用户token真的需要保存到cookie中嗎?如果關閉瀏覽器就結束會話,下次重新登錄可以接收,那就不要寫cookie了;如果用户需要自動續簽token,要做到無感知自動登錄,可以寫個refresh_token用來在下次請求時重新續簽token(重新生成),這個token數據就存在瀏覽器內存變量中,然後在後續請求中攜帶上新的token信息,而不是寫到cookie裏。
  3. otherwise,用csrfToken,用户登錄成功後,或者驗證身份成功後,生成一個隨機csrfToken給前端,後續請求時帶上這個。csrfToken不用驗證身份,只需判斷是否是真實簽發過的就行,可以簡單放到redis集合數據中。

Add a new 评论

Some HTML is okay.