天天看點

Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理

JdbcTokenRepositoryImpl

簡介

SpringSecurity的令牌持久化接口PersistentTokenRepository的一個實作類JdbcTokenRepositoryImpl。

作用

将原本存于記憶體的session存入資料庫。

session持久化的優點

  1. 避免使用記憶體session,一旦使用者量大了,記憶體極有可能爆掉。
  2. 避免使用記憶體session,重新開機後需要重新登入。

使用方法

資料庫配置步驟省略。

1. 配置存儲器

Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理

2. 配置SpringSecurity過濾器鍊

Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理

3. 登入開啟記住我

Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理

4、 使用測試

  1. 登入成功關閉浏覽器。
  2. 再重新打開網頁,發現自動登入成功。

工作原理

1. JdbcTokenRepositoryImpl類簡介

基于Jdbc對資料庫進行操作,自身攜帶固定的表結構。

Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理

2. JdbcTokenRepositoryImpl建立的表結構

Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理

3. 将series和token使用base64進行加密,放入前端的remember-me的cookie中

Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理
Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理

3. remember-me cookie的簡介

SpringSecurity預設對認證用的建立的cookie是“閱後即焚”政策。而JdbcTokenRepositoryImpl會在使用者浏覽器建立一個浏覽器關閉不會消失的cookie(有一定時間限制),在進行登入時通過remember-me cookie作為SpringSecurity預設cookie不存在時的一個備用認證政策。

4. 源碼分析

  1. RememberMeAuthenticationFilter檢測到預設cookie不存在時,調用AbstractRememberMeServices的autoLogin。
  2. AbstractRememberMeServices擷取使用者傳來的rememberMeCookie,對rememberMeCookie進行解碼,擷取其中的series和token字段。
  3. AbstractRememberMeServices調用PersistentTokenBasedRememberMeServices#processAutoLoginCookie對rememberMeCookie進行驗證并解析使用者資料。
  4. PersistentTokenBasedRememberMeServices拿到series和token到資料庫比對,失敗抛出CookieTheftException,并清除使用者cookie、資料庫中該使用者的所有認證字段(意味着該賬戶密碼洩露,所有登入成功的端都将登入失效,需要重新登入)。
    Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理
  5. 若比對成功則series不變,token重新整理。将token重寫寫入資料庫、重設rememberMeCookie。生成使用者認證資訊,使用者登入成功。

JdbcTokenRepositoryImpl在實際場景下的作用

  1. 每次使用rememberMe進行登入,rememberMe中的token部分都會重新整理。
  2. 如果rememberMeCookie洩露給黑客,正常使用者在自動登入一次後會重新生成token,rememberMeCookie也得以更新。由于rememberMeCookie的更新便會使得黑客手中的rememberMeCookie失效(old)。
  3. 此時,黑客若再使用rememberMeCookie進行登入,在SpringSecurity取出rememberMeCookie中的series和token與資料庫中的最新的series和token比對時發現不比對,将判定為使用者rememberMeCookie洩露。
  4. rememberMeCookie洩露,将觸發删除所有該使用者的授權cookie與資料庫persistent_logins表中該使用者的所有與該使用者名關聯的資料行,最終導緻所有的使用者都将需要使用密碼重新登入。

綜上所述

我們可以總結persistent_logins各個字段的主要作用:

create table persistent_logins
(
    username  varchar(64)                         not null,
    series    varchar(64)                         not null
        primary key,
    token     varchar(64)                         not null,
    last_used timestamp default CURRENT_TIMESTAMP not null on update CURRENT_TIMESTAMP
);

           
Spring Security RememberMe的令牌持久化JdbcTokenRepositoryImpl的工作原理
username

與使用者表關聯的辨別符。

series

勾選記住我+使用者密碼登入時建立,之後除非删除否則不會改變,主要作用是作為該表id,用于查token。

token

使用rememberMeCookie自動登入時會重新整理,和series組合生成rememberMeCookie。每次使用“記住我”自動登入時重新整理,用來防止rememberMeCookie洩露。

last_used

使用rememberMeCookie自動登入時會重新整理,可以用來判斷認證資訊是否超過期限。