不出意外的話,我猜在座的各位同學,剛剛學編程的時候,80%以上的人寫的第一個項目不是學生管理系統,就是用戶的登錄、注冊;需求都是源于生活而高于生活,因為學生對這些場景最為熟悉,功能也相對簡單,拿來練手最適合不過了;但是,一個看似小小的登錄、注冊功能,要想把他真正的做好,并不是一件容易的事情;本文通過圖示及代碼的方式介紹用戶登錄流程及技術實現,內容包括用戶登錄,用戶驗證,如何獲取操作用戶的信息以及一些黑名單及匿名接口如何免驗證相關的實現。
對于用戶登錄來說、涉及到了用戶注冊、登錄驗證幾個方面,通過流程圖演示如何處理(新用戶/老用戶)登錄。
圖片
圖片
圖片
登錄驗證流程涉及到了兩個接口,兩個緩存:
通常我們 token 的過期時間是根據客戶端的類型來定義的,app 的過期時間會更長一些(通常一個星期)。
web 端過期時間以小時為單位,如果控制過期時間可以將 web 登錄和 app 登錄拆分為兩個接口(能夠分流,接口壓力更小),或者是根據請求頭信息進行判斷即可,是移動端就設置 7 天,是 web 端就設置兩小時。
登錄成功后,客戶端每次請求都會攜帶 token,通常我們會有一個網關來進行 token 驗證,網關用于登錄驗證的核心就是登錄成功后寫入的 token 作為 key,值為用戶基礎信息的緩存。
圖解如下:
圖片
驗證成功后,重寫內部請求頭,將用戶的的 id,賬號,昵稱信息放入請求頭中,這樣可以方便業務系統獲取當前操作用戶信息以及權限控制等等。
用戶攜帶 token 請求登出接口,登出接口對 token 對應的緩存進行刪除操作,返回 401 即可,客戶端獲取到 401 就會跳轉到登錄頁面。
通常匿名請求放行有兩種方案:
優點就是雖然是免登錄接口,但是接口的操作對象可以追溯,請求次數可控,避免被非法利用;缺點就是需要更多的編碼及配置工作。
技術實現:
這時候我們需要在上面的驗證流程圖基礎上進行升級:
圖片
請求次數檢查代碼實現:import org.springframework.beans.factory.annotation.Autowired;import org.springframework.data.redis.core.RedisTemplate;import org.springframework.stereotype.Component;import java.util.concurrent.TimeUnit;/** * 授權token請求限制緩存 */@Componentpublic class AuthTokenRequestLimitCache { @Autowired private RedisTemplate<String, Integer> redisTemplate; private static final String AUTH_TOKEN_LIMIT_KEY_PREFIX = "auth_token_limit"; /** * 請求次數+1并檢查是否超限 * * @param token * @return 是否放行 */ public boolean incrementWithCheck(String token) { // 1.獲取token請求次數限制,獲取為null代表授權配置已被修改,此token已經不具備權限 Integer limit = getLimit(token); if (limit == null) { return false; } // 2.組裝緩存key,讀取緩存 String key = String.join(":", AUTH_TOKEN_LIMIT_KEY_PREFIX, token); Integer count = redisTemplate.opsForValue().get(key); // 3.沒有值代表一分鐘內沒有請求產生了 if (count == null) { // 初始化值 redisTemplate.opsForValue().increment(key); // 設置過期時間 redisTemplate.expire(key, 1L, TimeUnit.MINUTES); return true; } // 自增并獲取當前值 大于限制的話 返回false 網關過濾器返回提示信息(如請求過于頻繁) Long inc = redisTemplate.opsForValue().increment(key); return inc <= limit; } /** * 獲取限值 * * @param token * @return */ public Integer getLimit(String token) { Object limit = redisTemplate.opsForHash().get("auth_token_limit", token); return limit == null ? null : (Integer) limit; }}
對于授權接口,通常是只允許 get 操作,對數據進行提交或者更新是不被允許的,當然這個是業務層面的,最終取決于系統設計。
我們在網關的配置文件中增加匿名接口規則,請求到網關時,檢查請求的路徑是否符合匿名接口規則,是則放行,不是則進行 token 校驗,方案比較簡單,只需要對網關進行處理即可。
對于一個系統來說,黑名單是最后一道關卡,所以為了安全我們需要對問題用戶進行黑名單操作。
具體實現也比較簡單:
用戶系統是非常基礎的系統,但是很多程序員工作中可能并沒有真正的參與到用戶系統的開發,通過此文可以對用戶登錄流程及配套功能有一個全面的了解。
本文鏈接:http://www.www897cc.com/showinfo-26-96762-0.html三年探索,登錄注冊之路仍漫漫
聲明:本網頁內容旨在傳播知識,若有侵權等問題請及時與本網聯系,我們將在第一時間刪除處理。郵件:2376512515@qq.com
下一篇: CSS的媒體查詢:響應式布局的利器