HTTP協議是無狀態的,每次HTTP請求響應後,就會斷開這次連接。如果客戶端再次發送請求,服務端也不能識別出這個客戶端是不是上次請求過的客戶端,HTTP協議不能進行會話跟蹤。而Cookie,Session,Token正是為了解決HTTP協議無狀態問題。
Cookie
Cookie機制是在客戶端實現,採用客戶端保持狀態的方案。Cookie由服務端生成,發送給客戶端(Set-Cookie),客戶端請求的時候會帶上這個Cookie。請求流程:
Cookie字段:名字、值、過期時間、路徑和域。路徑與域一起構成Cookie的作用範圍。通過Chrome的開發者工具中看到,在github.com上保存在客戶端的Cookie信息。
- Name:名字
- Value:值
- Domain:域
- Path:路徑
- Expaires/Max-Age:過期時間
上圖中logged_in和user_session兩個Cookie值表示登錄github.com後保存下來的登錄狀態和Session。
Session
Session是在服務端實現,當客戶端請求服務端時,服務端會檢查請求中是否包含Session標識(Session id),
- 如果沒有,那麼服務端就生成一個隨機的Session以及和它匹配的Session id,並將Session id返回給客戶端。
- 如果有,那麼服務器就在存儲中根據Session id 查找到對應的Session。
Token
Token也稱作令牌,由uid+time+sign[+固定參數]組成:
- uid:用戶唯一身份標識
- time:當前時間的時間戳
- sign:簽名, 使用 hash/encrypt 壓縮成定長的十六進制字符串,可以防止惡意第三方拼接Token請求服務器
以下幾點特性會讓你在程序中使用基於Token的身份驗證:
- 無狀態、可擴展
- 支持移動設備
- 跨程序調用
- 安全
Token是有客戶端來保存,用戶的狀態在服務端的內存中是不存儲的,所以這是一種無狀態的認證機制。而認證的具體流程如下:
客戶端使用用戶名跟密碼請求登錄服務端收到請求,去驗證用戶名與密碼驗證成功後,服務端會簽發一個 Token,再把這個 Token 發送給客戶端客戶端收到 Token 以後可以把它存儲起來,比如放在 Cookie 裡或者 Local Storage 裡客戶端每次向服務端請求資源的時候需要帶著服務端簽發的 Token服務端收到請求,然後去驗證客戶端請求裡面帶著的 Token,如果驗證成功,就向客戶端返回請求的數據
這是Token的一種應用場景,使用OAuth實現。OAuth(開放授權)是一個開放標準,允許用戶讓第三方應用訪問該用戶在某一網站上存儲的私密的資源(如照片,視頻,聯繫人列表),而無需將用戶名和密碼提供給第三方應用。OAuth允許用戶提供一個令牌,而不是用戶名和密碼來訪問他們存放在特定服務提供者的數據。我們看下github的授權流程:
區別
Cookie和Session
Token和Session
作為身份認證Token安全性比Session好。Session是一種HTTP存儲機制,目的是為無狀態的HTTP提供的持久機制。Token,如果指的是OAuth Token 或類似的機制的話,提供的是認證和授權 ,認證是針對用戶,授權是針對App。
參考
- Cookie、Session、Token那點事兒
- 徹底理解cookie,session,token
- 精讀《圖解HTTP》
閱讀更多 Coder淘金 的文章