摘要: Token 是在服務(wù)端產(chǎn)生的华嘹。如果前端使用用戶名/密碼向服務(wù)端請(qǐng)求認(rèn)證,服務(wù)端認(rèn)證成功耙厚,那么在服務(wù)端會(huì)返回 Token 給前端。前端可以在每次請(qǐng)求的時(shí)候帶上 Token 證明自己的合法地位俯渤。
為什么要用 Token型宝?
因?yàn)樗芙鉀Q問(wèn)題!
可以解決哪些問(wèn)題呢诡曙?
Token 完全由應(yīng)用管理价卤,所以它可以避開(kāi)同源策略
Token 可以避免 CSRF 攻擊(http://dwz.cn/7joLzx)
Token 可以是無(wú)狀態(tài)的劝萤,可以在多個(gè)服務(wù)間共享
Token 是在服務(wù)端產(chǎn)生的慎璧。如果前端使用用戶名/密碼向服務(wù)端請(qǐng)求認(rèn)證,服務(wù)端認(rèn)證成功厌处,那么在服務(wù)端會(huì)返回 Token 給前端岁疼。前端可以在每次請(qǐng)求的時(shí)候帶上 Token 證明自己的合法地位。如果這個(gè) Token 在服務(wù)端持久化(比如存入數(shù)據(jù)庫(kù))瑰排,那它就是一個(gè)永久的身份令牌暖侨。
需要設(shè)置有效期嗎?
對(duì)于這個(gè)問(wèn)題字逗,我們不妨先看兩個(gè)例子宅广。一個(gè)例子是登錄密碼些举,一般要求定期改變密碼,以防止泄漏兽肤,所以密碼是有有效期的绪抛;另一個(gè)例子是安全證書(shū)电禀。SSL 安全證書(shū)都有有效期幢码,目的是為了解決吊銷(xiāo)的問(wèn)題尖飞,對(duì)于這個(gè)問(wèn)題的詳細(xì)情況政基,來(lái)看看知乎的回答(http://dwz.cn/7joMhq)。所以無(wú)論是從安全的角度考慮沮明,還是從吊銷(xiāo)的角度考慮,Token 都需要設(shè)有效期酱畅。
那么有效期多長(zhǎng)合適呢江场?
只能說(shuō),根據(jù)系統(tǒng)的安全需要址否,盡可能的短,但也不能短得離譜——想像一下手機(jī)的自動(dòng)熄屏?xí)r間樊诺,如果設(shè)置為 10 秒鐘無(wú)操作自動(dòng)熄屏帮匾,再次點(diǎn)亮需要輸入密碼,會(huì)不會(huì)瘋瘟斜?如果你覺(jué)得不會(huì)缸夹,那就親自試一試痪寻,設(shè)置成可以設(shè)置的最短時(shí)間,堅(jiān)持一周就好(不排除有人適應(yīng)這個(gè)時(shí)間虽惭,畢竟手機(jī)廠商也是有用戶體驗(yàn)研究的)橡类。
然后新問(wèn)題產(chǎn)生了,如果用戶在正常操作的過(guò)程中芽唇,Token 過(guò)期失效了顾画,要求用戶重新登錄……用戶體驗(yàn)豈不是很糟糕?
為了解決在操作過(guò)程不能讓用戶感到 Token 失效這個(gè)問(wèn)題匆笤,有一種方案是在服務(wù)器端保存 Token 狀態(tài)研侣,用戶每次操作都會(huì)自動(dòng)刷新(推遲) Token 的過(guò)期時(shí)間——Session 就是采用這種策略來(lái)保持用戶登錄狀態(tài)的。然而仍然存在這樣一個(gè)問(wèn)題炮捧,在前后端分離庶诡、單頁(yè) App 這些情況下咆课,每秒種可能發(fā)起很多次請(qǐng)求末誓,每次都去刷新過(guò)期時(shí)間會(huì)產(chǎn)生非常大的代價(jià)。如果 Token 的過(guò)期時(shí)間被持久化到數(shù)據(jù)庫(kù)或文件书蚪,代價(jià)就更大了喇澡。所以通常為了提升效率,減少消耗殊校,會(huì)把 Token 的過(guò)期時(shí)保存在緩存或者內(nèi)存中晴玖。
還有另一種方案,使用 Refresh Token箩艺,它可以避免頻繁的讀寫(xiě)操作窜醉。這種方案中,服務(wù)端不需要刷新 Token 的過(guò)期時(shí)間艺谆,一旦 Token 過(guò)期榨惰,就反饋給前端,前端使用 Refresh Token 申請(qǐng)一個(gè)全新 Token 繼續(xù)使用静汤。這種方案中琅催,服務(wù)端只需要在客戶端請(qǐng)求更新 Token 的時(shí)候?qū)?Refresh Token 的有效性進(jìn)行一次檢查,大大減少了更新有效期的操作虫给,也就避免了頻繁讀寫(xiě)藤抡。當(dāng)然 Refresh Token 也是有有效期的,但是這個(gè)有效期就可以長(zhǎng)一點(diǎn)了抹估,比如缠黍,以天為單位的時(shí)間。