AVt天堂网 手机版,亚洲va久久久噜噜噜久久4399,天天综合亚洲色在线精品,亚洲一级Av无码毛片久久精品

當前位置:首頁 > 科技  > 軟件

再見,Shiro !你好,Sa-Token!

來源: 責編: 時間:2023-11-30 09:30:30 290觀看
導讀Sa-Token 介紹Sa-Token 是一個輕量級 Java 權限認證框架,主要解決:登錄認證、權限認證、單點登錄、OAuth2.0、分布式Session會話、微服務網關鑒權 等一系列權限相關問題。Sa-Token 旨在以簡單、優雅的方式完成系統的權

Sa-Token 介紹

Sa-Token 是一個輕量級 Java 權限認證框架,主要解決:登錄認證、權限認證、單點登錄、OAuth2.0、分布式Session會話、微服務網關鑒權 等一系列權限相關問題。M9928資訊網——每日最新資訊28at.com

Sa-Token 旨在以簡單、優雅的方式完成系統的權限認證部分,以登錄認證為例,你只需要:M9928資訊網——每日最新資訊28at.com

// 會話登錄,參數填登錄人的賬號id StpUtil.login(10001);

無需實現任何接口,無需創建任何配置文件,只需要這一句靜態代碼的調用,便可以完成會話登錄認證。M9928資訊網——每日最新資訊28at.com

如果一個接口需要登錄后才能訪問,我們只需調用以下代碼:M9928資訊網——每日最新資訊28at.com

// 校驗當前客戶端是否已經登錄,如果未登錄則拋出 `NotLoginException` 異常StpUtil.checkLogin();

在 Sa-Token 中,大多數功能都可以一行代碼解決:M9928資訊網——每日最新資訊28at.com

踢人下線:M9928資訊網——每日最新資訊28at.com

// 將賬號id為 10077 的會話踢下線 StpUtil.kickout(10077);

權限認證:M9928資訊網——每日最新資訊28at.com

// 注解鑒權:只有具備 `user:add` 權限的會話才可以進入方法@SaCheckPermission("user:add")    public String insert(SysUser user) {    // ...     return "用戶增加";}

路由攔截鑒權:M9928資訊網——每日最新資訊28at.com

// 根據路由劃分模塊,不同模塊不同鑒權 registry.addInterceptor(new SaInterceptor(handler -> {    SaRouter.match("/user/**", r -> StpUtil.checkPermission("user"));    SaRouter.match("/admin/**", r -> StpUtil.checkPermission("admin"));    SaRouter.match("/goods/**", r -> StpUtil.checkPermission("goods"));    SaRouter.match("/orders/**", r -> StpUtil.checkPermission("orders"));    SaRouter.match("/notice/**", r -> StpUtil.checkPermission("notice"));    // 更多模塊... })).addPathPatterns("/**");

當你受夠 Shiro、SpringSecurity 等框架的三拜九叩之后,你就會明白,相對于這些傳統老牌框架,Sa-Token 的 API 設計是多么的簡單、優雅!M9928資訊網——每日最新資訊28at.com

Sa-Token 功能一覽

Sa-Token 目前主要五大功能模塊:登錄認證、權限認證、單點登錄、OAuth2.0、微服務鑒權。M9928資訊網——每日最新資訊28at.com

  • 登錄認證 —— 單端登錄、多端登錄、同端互斥登錄、七天內免登錄
  • 權限認證 —— 權限認證、角色認證、會話二級認證
  • Session會話 —— 全端共享Session、單端獨享Session、自定義Session
  • 踢人下線 —— 根據賬號id踢人下線、根據Token值踢人下線
  • 賬號封禁 —— 登錄封禁、按照業務分類封禁、按照處罰階梯封禁
  • 持久層擴展 —— 可集成Redis、Memcached等專業緩存中間件,重啟數據不丟失
  • 分布式會話 —— 提供jwt集成、共享數據中心兩種分布式會話方案
  • 微服務網關鑒權 —— 適配Gateway、ShenYu、Zuul等常見網關的路由攔截認證
  • 單點登錄 —— 內置三種單點登錄模式:無論是否跨域、是否共享Redis,都可以搞定
  • OAuth2.0認證 —— 輕松搭建 OAuth2.0 服務,支持openid模式
  • 二級認證 —— 在已登錄的基礎上再次認證,保證安全性
  • Basic認證 —— 一行代碼接入 Http Basic 認證
  • 獨立Redis —— 將權限緩存與業務緩存分離
  • 臨時Token認證 —— 解決短時間的Token授權問題
  • 模擬他人賬號 —— 實時操作任意用戶狀態數據
  • 臨時身份切換 —— 將會話身份臨時切換為其它賬號
  • 前后臺分離 —— APP、小程序等不支持Cookie的終端
  • 同端互斥登錄 —— 像QQ一樣手機電腦同時在線,但是兩個手機上互斥登錄
  • 多賬號認證體系 —— 比如一個商城項目的user表和admin表分開鑒權
  • Token風格定制 —— 內置六種Token風格,還可:自定義Token生成策略、自定義Token前綴
  • 注解式鑒權 —— 優雅的將鑒權與業務代碼分離
  • 路由攔截式鑒權 —— 根據路由攔截鑒權,可適配restful模式
  • 自動續簽 —— 提供兩種Token過期策略,靈活搭配使用,還可自動續簽
  • 會話治理 —— 提供方便靈活的會話查詢接口
  • 記住我模式 —— 適配[記住我]模式,重啟瀏覽器免驗證
  • 密碼加密 —— 提供密碼加密模塊,可快速MD5、SHA1、SHA256、AES、RSA加密
  • 全局偵聽器 —— 在用戶登陸、注銷、被踢下線等關鍵性操作時進行一些AOP操作
  • 開箱即用 —— 提供SpringMVC、WebFlux等常見web框架starter集成包,真正的開箱即用

SpringBoot 集成 Sa-Token

一、添加maven依賴

<!-- Sa-Token 權限認證,在線文檔:https://sa-token.cc --><dependency>  <groupId>cn.dev33</groupId>  <artifactId>sa-token-spring-boot-starter</artifactId>  <version>1.34.0</version></dependency>

注:如果你使用的 SpringBoot 3.x,只需要將 sa-token-spring-boot-starter 修改為 sa-token-spring-boot3-starter 即可。M9928資訊網——每日最新資訊28at.com

二、設置配置文件

你可以零配置啟動項目 ,但同時你也可以在 application.yml 中增加如下配置,定制性使用框架:M9928資訊網——每日最新資訊28at.com

server:    # 端口    port: 8081############## Sa-Token 配置 (文檔: https://sa-token.cc) ##############sa-token:     # token名稱 (同時也是cookie名稱)    token-name: satoken    # token有效期,單位s 默認30天, -1代表永不過期     timeout: 2592000    # token臨時有效期 (指定時間內無操作就視為token過期) 單位: 秒    activity-timeout: -1    # 是否允許同一賬號并發登錄 (為true時允許一起登錄, 為false時新登錄擠掉舊登錄)     is-concurrent: true    # 在多人登錄同一賬號時,是否共用一個token (為true時所有登錄共用一個token, 為false時每次登錄新建一個token)     is-share: true    # token風格    token-style: uuid    # 是否輸出操作日志     is-log: false

三、創建案例

@RestController    @RequestMapping("/user/")    public class UserController {        // 測試登錄,瀏覽器訪問:http://localhost:8081/user/doLogin?username=zhang&password=123456        @RequestMapping("doLogin")        public String doLogin(String username, String password) {            // 此處僅作模擬示例,真實項目需要從數據庫中查詢數據進行比對             if("iron".equals(username) && "123456".equals(password)) {                StpUtil.login(10001);                return "登錄成功";            }            return "登錄失敗";        }        // 查詢登錄狀態,瀏覽器訪問:http://localhost:8081/user/isLogin        @RequestMapping("isLogin")        public String isLogin() {            return "當前會話是否登錄:" + StpUtil.isLogin();        }    }

登錄認證

設計思路

對于一些登錄之后才能訪問的接口(例如:查詢我的賬號資料),我們通常的做法是增加一層接口校驗:M9928資訊網——每日最新資訊28at.com

  • 如果校驗通過,則:正常返回數據。
  • 如果校驗未通過,則:拋出異常,告知其需要先進行登錄。

那么,判斷會話是否登錄的依據是什么?我們先來簡單分析一下登錄訪問流程:M9928資訊網——每日最新資訊28at.com

  1. 用戶提交 name + password 參數,調用登錄接口。
  2. 登錄成功,返回這個用戶的 Token 會話憑證。
  3. 用戶后續的每次請求,都攜帶上這個 Token。
  4. 服務器根據 Token 判斷此會話是否登錄成功。

所謂登錄認證,指的就是服務器校驗賬號密碼,為用戶頒發 Token 會話憑證的過程,這個 Token 也是我們后續判斷會話是否登錄的關鍵所在。M9928資訊網——每日最新資訊28at.com

登錄與注銷

根據以上思路,我們需要一個會話登錄的函數:M9928資訊網——每日最新資訊28at.com

// 會話登錄:參數填寫要登錄的賬號id,建議的數據類型:long | int | String, 不可以傳入復雜類型,如:User、Admin 等等StpUtil.login(Object id);

只此一句代碼,便可以使會話登錄成功,實際上,Sa-Token 在背后做了大量的工作,包括但不限于:M9928資訊網——每日最新資訊28at.com

  1. 檢查此賬號是否之前已有登錄
  2. 為賬號生成 Token 憑證與 Session 會話
  3. 通知全局偵聽器,xx 賬號登錄成功
  4. 將 Token 注入到請求上下文
  5. 等等其它工作……

你暫時不需要完整的了解整個登錄過程,你只需要記住關鍵一點:Sa-Token 為這個賬號創建了一個Token憑證,且通過 Cookie 上下文返回給了前端。M9928資訊網——每日最新資訊28at.com

所以一般情況下,我們的登錄接口代碼,會大致類似如下:M9928資訊網——每日最新資訊28at.com

// 會話登錄接口 @RequestMapping("doLogin")    public SaResult doLogin(String name, String pwd) {    // 第一步:比對前端提交的賬號名稱、密碼    if("iron".equals(name) && "123456".equals(pwd)) {        // 第二步:根據賬號id,進行登錄         StpUtil.login(10001);        return SaResult.ok("登錄成功");    }    return SaResult.error("登錄失敗");}

如果你對以上代碼閱讀沒有壓力,你可能會注意到略顯奇怪的一點:此處僅僅做了會話登錄,但并沒有主動向前端返回 Token 信息。是因為不需要嗎?嚴格來講是需要的,只不過 StpUtil.login(id) 方法利用了 Cookie 自動注入的特性,省略了你手寫返回 Token 的代碼。M9928資訊網——每日最新資訊28at.com

如果你對 Cookie 功能還不太了解,也不用擔心,我們會在之后的 [ 前后端分離 ] 章節中詳細的闡述 Cookie 功能,現在你只需要了解最基本的兩點:M9928資訊網——每日最新資訊28at.com

  • Cookie 可以從后端控制往瀏覽器中寫入 Token 值。
  • Cookie 會在前端每次發起請求時自動提交 Token 值。

因此,在 Cookie 功能的加持下,我們可以僅靠 StpUtil.login(id) 一句代碼就完成登錄認證。M9928資訊網——每日最新資訊28at.com

除了登錄方法,我們還需要:M9928資訊網——每日最新資訊28at.com

// 當前會話注銷登錄StpUtil.logout();// 獲取當前會話是否已經登錄,返回true=已登錄,false=未登錄StpUtil.isLogin();// 檢驗當前會話是否已經登錄, 如果未登錄,則拋出異常:`NotLoginException`StpUtil.checkLogin();

異常 NotLoginException 代表當前會話暫未登錄,可能的原因有很多:前端沒有提交 Token、前端提交的 Token 是無效的、前端提交的 Token 已經過期 …… 等等,可參照此篇:未登錄場景值,了解如何獲取未登錄的場景值。M9928資訊網——每日最新資訊28at.com

會話查詢

// 獲取當前會話賬號id, 如果未登錄,則拋出異常:`NotLoginException`StpUtil.getLoginId();// 類似查詢API還有:StpUtil.getLoginIdAsString();    // 獲取當前會話賬號id, 并轉化為`String`類型StpUtil.getLoginIdAsInt();       // 獲取當前會話賬號id, 并轉化為`int`類型StpUtil.getLoginIdAsLong();      // 獲取當前會話賬號id, 并轉化為`long`類型// ---------- 指定未登錄情形下返回的默認值 ----------// 獲取當前會話賬號id, 如果未登錄,則返回null StpUtil.getLoginIdDefaultNull();// 獲取當前會話賬號id, 如果未登錄,則返回默認值 (`defaultValue`可以為任意類型)StpUtil.getLoginId(T defaultValue);

Token 查詢

// 獲取當前會話的token值StpUtil.getTokenValue();// 獲取當前`StpLogic`的token名稱StpUtil.getTokenName();// 獲取指定token對應的賬號id,如果未登錄,則返回 nullStpUtil.getLoginIdByToken(String tokenValue);// 獲取當前會話剩余有效期(單位:s,返回-1代表永久有效)StpUtil.getTokenTimeout();// 獲取當前會話的token信息參數StpUtil.getTokenInfo();

有關TokenInfo參數詳解,請參考:TokenInfo參數詳解M9928資訊網——每日最新資訊28at.com

來個小測試,加深一下理解

新建 LoginController,復制以下代碼M9928資訊網——每日最新資訊28at.com

/** * 登錄測試  */@RestController@RequestMapping("/acc/")public class LoginController {    // 測試登錄  ---- http://localhost:8081/acc/doLogin?name=zhang&pwd=123456    @RequestMapping("doLogin")    public SaResult doLogin(String name, String pwd) {        // 此處僅作模擬示例,真實項目需要從數據庫中查詢數據進行比對         if("iron".equals(name) && "123456".equals(pwd)) {            StpUtil.login(10001);            return SaResult.ok("登錄成功");        }        return SaResult.error("登錄失敗");    }    // 查詢登錄狀態  ---- http://localhost:8081/acc/isLogin    @RequestMapping("isLogin")    public SaResult isLogin() {        return SaResult.ok("是否登錄:" + StpUtil.isLogin());    }    // 查詢 Token 信息  ---- http://localhost:8081/acc/tokenInfo    @RequestMapping("tokenInfo")    public SaResult tokenInfo() {        return SaResult.data(StpUtil.getTokenInfo());    }    // 測試注銷  ---- http://localhost:8081/acc/logout    @RequestMapping("logout")    public SaResult logout() {        StpUtil.logout();        return SaResult.ok();    }}

權限認證

設計思路

所謂權限認證,核心邏輯就是判斷一個賬號是否擁有指定權限:M9928資訊網——每日最新資訊28at.com

  • 有,就讓你通過。
  • 沒有?那么禁止訪問!

深入到底層數據中,就是每個賬號都會擁有一個權限碼集合,框架來校驗這個集合中是否包含指定的權限碼。M9928資訊網——每日最新資訊28at.com

例如:當前賬號擁有權限碼集合 ["user-add", "user-delete", "user-get"],這時候我來校驗權限 "user-update",則其結果就是:驗證失敗,禁止訪問。M9928資訊網——每日最新資訊28at.com

所以現在問題的核心就是:M9928資訊網——每日最新資訊28at.com

  1. 如何獲取一個賬號所擁有的的權限碼集合?
  2. 本次操作需要驗證的權限碼是哪個?

獲取當前賬號權限碼集合

因為每個項目的需求不同,其權限設計也千變萬化,因此 [ 獲取當前賬號權限碼集合 ] 這一操作不可能內置到框架中, 所以 Sa-Token 將此操作以接口的方式暴露給你,以方便你根據自己的業務邏輯進行重寫。M9928資訊網——每日最新資訊28at.com

你需要做的就是新建一個類,實現 StpInterface接口,例如以下代碼:M9928資訊網——每日最新資訊28at.com

/** * 自定義權限驗證接口擴展 */@Component    // 保證此類被SpringBoot掃描,完成Sa-Token的自定義權限驗證擴展 public class StpInterfaceImpl implements StpInterface {    /**     * 返回一個賬號所擁有的權限碼集合      */    @Override    public List<String> getPermissionList(Object loginId, String loginType) {        // 本list僅做模擬,實際項目中要根據具體業務邏輯來查詢權限        List<String> list = new ArrayList<String>();            list.add("101");        list.add("user.add");        list.add("user.update");        list.add("user.get");        // list.add("user.delete");        list.add("art.*");        return list;    }    /**     * 返回一個賬號所擁有的角色標識集合 (權限與角色可分開校驗)     */    @Override    public List<String> getRoleList(Object loginId, String loginType) {        // 本list僅做模擬,實際項目中要根據具體業務邏輯來查詢角色        List<String> list = new ArrayList<String>();            list.add("admin");        list.add("super-admin");        return list;    }}

參數解釋:M9928資訊網——每日最新資訊28at.com

  • loginId:賬號id,即你在調用 StpUtil.login(id) 時寫入的標識值。
  • loginType:賬號體系標識,此處可以暫時忽略,在 [ 多賬戶認證 ] 章節下會對這個概念做詳細的解釋。

可參考代碼:碼云:StpInterfaceImpl.javaM9928資訊網——每日最新資訊28at.com

注意: StpInterface 接口在需要鑒權時由框架自動調用,開發者只需要配置好就可以使用下面的鑒權方法或后面的注解鑒權M9928資訊網——每日最新資訊28at.com

權限校驗

然后就可以用以下api來鑒權了M9928資訊網——每日最新資訊28at.com

// 獲取:當前賬號所擁有的權限集合StpUtil.getPermissionList();// 判斷:當前賬號是否含有指定權限, 返回 true 或 falseStpUtil.hasPermission("user.add");        // 校驗:當前賬號是否含有指定權限, 如果驗證未通過,則拋出異常: NotPermissionException StpUtil.checkPermission("user.add");        // 校驗:當前賬號是否含有指定權限 [指定多個,必須全部驗證通過]StpUtil.checkPermissionAnd("user.add", "user.delete", "user.get");        // 校驗:當前賬號是否含有指定權限 [指定多個,只要其一驗證通過即可]StpUtil.checkPermissionOr("user.add", "user.delete", "user.get");

擴展:NotPermissionException 對象可通過 getLoginType() 方法獲取具體是哪個 StpLogic 拋出的異常M9928資訊網——每日最新資訊28at.com

角色校驗

在Sa-Token中,角色和權限可以獨立驗證M9928資訊網——每日最新資訊28at.com

// 獲取:當前賬號所擁有的角色集合StpUtil.getRoleList();// 判斷:當前賬號是否擁有指定角色, 返回 true 或 falseStpUtil.hasRole("super-admin");        // 校驗:當前賬號是否含有指定角色標識, 如果驗證未通過,則拋出異常: NotRoleExceptionStpUtil.checkRole("super-admin");        // 校驗:當前賬號是否含有指定角色標識 [指定多個,必須全部驗證通過]StpUtil.checkRoleAnd("super-admin", "shop-admin");        // 校驗:當前賬號是否含有指定角色標識 [指定多個,只要其一驗證通過即可] StpUtil.checkRoleOr("super-admin", "shop-admin");

擴展:NotRoleException 對象可通過 getLoginType() 方法獲取具體是哪個 StpLogic 拋出的異常M9928資訊網——每日最新資訊28at.com

權限通配符

Sa-Token允許你根據通配符指定泛權限,例如當一個賬號擁有art.*的權限時,art.add、art.delete、art.update都將匹配通過M9928資訊網——每日最新資訊28at.com

// 當擁有 art.* 權限時StpUtil.hasPermission("art.add");        // trueStpUtil.hasPermission("art.update");     // trueStpUtil.hasPermission("goods.add");      // false// 當擁有 *.delete 權限時StpUtil.hasPermission("art.delete");      // trueStpUtil.hasPermission("user.delete");     // trueStpUtil.hasPermission("user.update");     // false// 當擁有 *.js 權限時StpUtil.hasPermission("index.js");        // trueStpUtil.hasPermission("index.css");       // falseStpUtil.hasPermission("index.html");      // false

上帝權限:當一個賬號擁有 "*" 權限時,他可以驗證通過任何權限碼 (角色認證同理)M9928資訊網——每日最新資訊28at.com

如何把權限精確到按鈕級?

權限精確到按鈕級的意思就是指:權限范圍可以控制到頁面上的每一個按鈕是否顯示。M9928資訊網——每日最新資訊28at.com

思路:如此精確的范圍控制只依賴后端已經難以完成,此時需要前端進行一定的邏輯判斷。M9928資訊網——每日最新資訊28at.com

如果是前后端一體項目,可以參考:Thymeleaf 標簽方言,如果是前后端分離項目,則:M9928資訊網——每日最新資訊28at.com

  1. 在登錄時,把當前賬號擁有的所有權限碼一次性返回給前端。
  2. 前端將權限碼集合保存在localStorage或其它全局狀態管理對象中。
  3. 在需要權限控制的按鈕上,使用 js 進行邏輯判斷,例如在Vue框架中我們可以使用如下寫法:
<button v-if="arr.indexOf('user.delete') > -1">刪除按鈕</button>

其中:arr是當前用戶擁有的權限碼數組,user.delete是顯示按鈕需要擁有的權限碼,刪除按鈕是用戶擁有權限碼才可以看到的內容。M9928資訊網——每日最新資訊28at.com

注意:以上寫法只為提供一個參考示例,不同框架有不同寫法,大家可根據項目技術棧靈活封裝進行調用。M9928資訊網——每日最新資訊28at.com

踢人下線

所謂踢人下線,核心操作就是找到指定 loginId 對應的 Token,并設置其失效。M9928資訊網——每日最新資訊28at.com

強制注銷

StpUtil.logout(10001);                    // 強制指定賬號注銷下線 StpUtil.logout(10001, "PC");              // 強制指定賬號指定端注銷下線 StpUtil.logoutByTokenValue("token");      // 強制指定 Token 注銷下線

踢人下線

StpUtil.kickout(10001);                    // 將指定賬號踢下線 StpUtil.kickout(10001, "PC");              // 將指定賬號指定端踢下線StpUtil.kickoutByTokenValue("token");      // 將指定 Token 踢下線

強制注銷 和 踢人下線 的區別在于:M9928資訊網——每日最新資訊28at.com

  • 強制注銷等價于對方主動調用了注銷方法,再次訪問會提示:Token無效。
  • 踢人下線不會清除Token信息,而是將其打上特定標記,再次訪問會提示:Token已被踢下線。

注解鑒權

有同學表示:盡管使用代碼鑒權非常方便,但是我仍希望把鑒權邏輯和業務邏輯分離開來,我可以使用注解鑒權嗎?當然可以!M9928資訊網——每日最新資訊28at.com

注解鑒權 —— 優雅的將鑒權與業務代碼分離!M9928資訊網——每日最新資訊28at.com

  • @SaCheckLogin: 登錄校驗 —— 只有登錄之后才能進入該方法。
  • @SaCheckRole("admin"): 角色校驗 —— 必須具有指定角色標識才能進入該方法。
  • @SaCheckPermission("user:add"): 權限校驗 —— 必須具有指定權限才能進入該方法。
  • @SaCheckSafe: 二級認證校驗 —— 必須二級認證之后才能進入該方法。
  • @SaCheckBasic: HttpBasic校驗 —— 只有通過 Basic 認證后才能進入該方法。
  • @SaIgnore:忽略校驗 —— 表示被修飾的方法或類無需進行注解鑒權和路由攔截器鑒權。
  • @SaCheckDisable("comment"):賬號服務封禁校驗 —— 校驗當前賬號指定服務是否被封禁。

Sa-Token 使用全局攔截器完成注解鑒權功能,為了不為項目帶來不必要的性能負擔,攔截器默認處于關閉狀態因此,為了使用注解鑒權,你必須手動將 Sa-Token 的全局攔截器注冊到你項目中M9928資訊網——每日最新資訊28at.com

1、注冊攔截器

以SpringBoot2.0為例,新建配置類SaTokenConfigure.javaM9928資訊網——每日最新資訊28at.com

@Configurationpublic class SaTokenConfigure implements WebMvcConfigurer {    // 注冊 Sa-Token 攔截器,打開注解式鑒權功能     @Override    public void addInterceptors(InterceptorRegistry registry) {        // 注冊 Sa-Token 攔截器,打開注解式鑒權功能         registry.addInterceptor(new SaInterceptor()).addPathPatterns("/**");        }}

保證此類被springboot啟動類掃描到即可M9928資訊網——每日最新資訊28at.com

2、使用注解鑒權

然后我們就可以愉快的使用注解鑒權了:M9928資訊網——每日最新資訊28at.com

// 登錄校驗:只有登錄之后才能進入該方法 @SaCheckLogin                            @RequestMapping("info")    public String info() {    return "查詢用戶信息";}// 角色校驗:必須具有指定角色才能進入該方法 @SaCheckRole("super-admin")            @RequestMapping("add")    public String add() {    return "用戶增加";}// 權限校驗:必須具有指定權限才能進入該方法 @SaCheckPermission("user-add")            @RequestMapping("add")    public String add() {    return "用戶增加";}// 二級認證校驗:必須二級認證之后才能進入該方法 @SaCheckSafe()            @RequestMapping("add")    public String add() {    return "用戶增加";}// Http Basic 校驗:只有通過 Basic 認證后才能進入該方法 @SaCheckBasic(account = "sa:123456")    @RequestMapping("add")    public String add() {    return "用戶增加";}// 校驗當前賬號是否被封禁 comment 服務,如果已被封禁會拋出異常,無法進入方法 @SaCheckDisable("comment")                    @RequestMapping("send")    public String send() {    return "查詢用戶信息";}

注:以上注解都可以加在類上,代表為這個類所有方法進行鑒權M9928資訊網——每日最新資訊28at.com

3、設定校驗模式

@SaCheckRole與@SaCheckPermission注解可設置校驗模式,例如:M9928資訊網——每日最新資訊28at.com

// 注解式鑒權:只要具有其中一個權限即可通過校驗 @RequestMapping("atJurOr")@SaCheckPermission(value = {"user-add", "user-all", "user-delete"}, mode = SaMode.OR)        public SaResult atJurOr() {    return SaResult.data("用戶信息");}

mode有兩種取值:M9928資訊網——每日最新資訊28at.com

  • SaMode.AND, 標注一組權限,會話必須全部具有才可通過校驗。
  • SaMode.OR, 標注一組權限,會話只要具有其一即可通過校驗。

4、角色權限雙重 “or校驗”

假設有以下業務場景:一個接口在具有權限 user.add 或角色 admin 時可以調通。怎么寫?M9928資訊網——每日最新資訊28at.com

// 角色權限雙重 “or校驗”:具備指定權限或者指定角色即可通過校驗@RequestMapping("userAdd")@SaCheckPermission(value = "user.add", orRole = "admin")        public SaResult userAdd() {    return SaResult.data("用戶信息");}

orRole 字段代表權限認證未通過時的次要選擇,兩者只要其一認證成功即可通過校驗,其有三種寫法:M9928資訊網——每日最新資訊28at.com

  • 寫法一:orRole = "admin",代表需要擁有角色 admin 。
  • 寫法二:orRole = {"admin", "manager", "staff"},代表具有三個角色其一即可。
  • 寫法三:orRole = {"admin, manager, staff"},代表必須同時具有三個角色。

5、忽略認證

使用 @SaIgnore 可表示一個接口忽略認證:M9928資訊網——每日最新資訊28at.com

@SaCheckLogin@RestControllerpublic class TestController {    // ... 其它方法     // 此接口加上了 @SaIgnore 可以游客訪問     @SaIgnore    @RequestMapping("getList")    public SaResult getList() {        // ...         return SaResult.ok();     }}

如上代碼表示:TestController 中的所有方法都需要登錄后才可以訪問,但是 getList 接口可以匿名游客訪問。M9928資訊網——每日最新資訊28at.com

  • @SaIgnore 修飾方法時代表這個方法可以被游客訪問,修飾類時代表這個類中的所有接口都可以游客訪問。
  • @SaIgnore 具有最高優先級,當 @SaIgnore 和其它鑒權注解一起出現時,其它鑒權注解都將被忽略。
  • @SaIgnore 同樣可以忽略掉 Sa-Token 攔截器中的路由鑒權,在下面的 [路由攔截鑒權] 章節中我們會講到。

6、在業務邏輯層使用注解鑒權

疑問:我能否將注解寫在其它架構層呢,比如業務邏輯層?M9928資訊網——每日最新資訊28at.com

使用攔截器模式,只能在Controller層進行注解鑒權,如需在任意層級使用注解鑒權,請參考:AOP注解鑒權M9928資訊網——每日最新資訊28at.com

自定義 Token 風格

自定義token前綴

sa-token:     # token前綴    token-prefix: Bearer

內置風格

Sa-Token默認的token生成策略是uuid風格,其模樣類似于:623368f0-ae5e-4475-a53f-93e4225f16ae。如果你對這種風格不太感冒,還可以將token生成設置為其他風格。M9928資訊網——每日最新資訊28at.com

怎么設置呢?只需要在yml配置文件里設置 sa-token.token-style=風格類型 即可,其有多種取值:M9928資訊網——每日最新資訊28at.com

// 1. token-style=uuid    —— uuid風格 (默認風格)"623368f0-ae5e-4475-a53f-93e4225f16ae"http:// 2. token-style=simple-uuid    —— 同上,uuid風格, 只不過去掉了中劃線"6fd4221395024b5f87edd34bc3258ee8"http:// 3. token-style=random-32    —— 隨機32位字符串"qEjyPsEA1Bkc9dr8YP6okFr5umCZNR6W"http:// 4. token-style=random-64    —— 隨機64位字符串"v4ueNLEpPwMtmOPMBtOOeIQsvP8z9gkMgIVibTUVjkrNrlfra5CGwQkViDjO8jcc"http:// 5. token-style=random-128    —— 隨機128位字符串"nojYPmcEtrFEaN0Otpssa8I8jpk8FO53UcMZkCP9qyoHaDbKS6dxoRPky9c6QlftQ0pdzxRGXsKZmUSrPeZBOD6kJFfmfgiRyUmYWcj4WU4SSP2ilakWN1HYnIuX0Olj"http:// 6. token-style=tik    —— tik風格"gr_SwoIN0MC1ewxHX_vfCW3BothWDZMMtx__"

自定義 Token 生成策略

如果你覺著以上風格都不是你喜歡的類型,那么你還可以自定義token生成策略,來定制化token生成風格。M9928資訊網——每日最新資訊28at.com

怎么做呢?只需要重寫 SaStrategy 策略類的 createToken 算法即可:M9928資訊網——每日最新資訊28at.com

參考步驟如下:

1、在SaTokenConfigure配置類中添加代碼:M9928資訊網——每日最新資訊28at.com

@Configurationpublic class SaTokenConfigure {    /**     * 重寫 Sa-Token 框架內部算法策略      */    @Autowired    public void rewriteSaStrategy() {        // 重寫 Token 生成策略         SaStrategy.me.createToken = (loginId, loginType) -> {            return SaFoxUtil.getRandomString(60);    // 隨機60位長度字符串        };    }}

2、再次調用 StpUtil.login(10001)方法進行登錄,觀察其生成的token樣式:M9928資訊網——每日最新資訊28at.com

fuPSwZsnUhwgz08GTCH4wOgasWtc3odP4HLwXJ7NDGOximTvT4OlW19zeLHM9928資訊網——每日最新資訊28at.com

集成JWT的Token風格

引入依賴

首先在項目已經引入 Sa-Token 的基礎上,繼續添加:M9928資訊網——每日最新資訊28at.com

<!-- Sa-Token 整合 jwt --><dependency>  <groupId>cn.dev33</groupId>  <artifactId>sa-token-jwt</artifactId>  <version>1.34.0</version></dependency>

注意: sa-token-jwt 顯式依賴 hutool-jwt 5.7.14 版本,意味著:你的項目中要么不引入 Hutool,要么引入版本 >= 5.7.14 的 Hutool 版本M9928資訊網——每日最新資訊28at.com

配置密鑰

在 application.yml 配置文件中配置 jwt 生成秘鑰:M9928資訊網——每日最新資訊28at.com

sa-token:    # jwt秘鑰     jwt-secret-key: asdasdasifhueuiwyurfewbfjsdafjk

注入jwt實現

根據不同的整合規則,插件提供了三種不同的模式,你需要 選擇其中一種 注入到你的項目中M9928資訊網——每日最新資訊28at.com

@Configurationpublic class SaTokenConfigure {    // Sa-Token 整合 jwt (Simple 簡單模式)    @Bean    public StpLogic getStpLogicJwt() {        return new StpLogicJwtForSimple();    }     // Sa-Token 整合 jwt (Mixin 混入模式)    @Bean    public StpLogic getStpLogicJwt() {        return new StpLogicJwtForMixin();    }     // Sa-Token 整合 jwt (Stateless 無狀態模式)    @Bean    public StpLogic getStpLogicJwt() {        return new StpLogicJwtForStateless();    }}

不同模式策略對比

注入不同模式會讓框架具有不同的行為策略,以下是三種模式的差異點(為方便敘述,以下比較以同時引入 jwt 與 Redis 作為前提):M9928資訊網——每日最新資訊28at.com

功能點M9928資訊網——每日最新資訊28at.com

Simple 簡單模式M9928資訊網——每日最新資訊28at.com

Mixin 混入模式M9928資訊網——每日最新資訊28at.com

Stateless 無狀態模式M9928資訊網——每日最新資訊28at.com

Token風格M9928資訊網——每日最新資訊28at.com

jwt風格M9928資訊網——每日最新資訊28at.com

jwt風格M9928資訊網——每日最新資訊28at.com

jwt風格M9928資訊網——每日最新資訊28at.com

登錄數據存儲M9928資訊網——每日最新資訊28at.com

Redis中M9928資訊網——每日最新資訊28at.com

Token中M9928資訊網——每日最新資訊28at.com

Token中M9928資訊網——每日最新資訊28at.com

Session存儲M9928資訊網——每日最新資訊28at.com

Redis中M9928資訊網——每日最新資訊28at.com

Redis中M9928資訊網——每日最新資訊28at.com

無SessionM9928資訊網——每日最新資訊28at.com

注銷下線M9928資訊網——每日最新資訊28at.com

前后端雙清數據M9928資訊網——每日最新資訊28at.com

前后端雙清數據M9928資訊網——每日最新資訊28at.com

前端清除數據M9928資訊網——每日最新資訊28at.com

踢人下線APIM9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

頂人下線APIM9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

登錄認證M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

角色認證M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

權限認證M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

timeout 有效期M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

activity-timeout 有效期M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

id反查TokenM9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

會話管理M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

部分支持M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

注解鑒權M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

路由攔截鑒權M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

賬號封禁M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

身份切換M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

二級認證M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

支持M9928資訊網——每日最新資訊28at.com

模式總結M9928資訊網——每日最新資訊28at.com

Token風格替換M9928資訊網——每日最新資訊28at.com

jwt 與 Redis 邏輯混合M9928資訊網——每日最新資訊28at.com

完全舍棄Redis,只用jwtM9928資訊網——每日最新資訊28at.com

擴展參數

你可以通過以下方式在登錄時注入擴展參數:M9928資訊網——每日最新資訊28at.com

// 登錄10001賬號,并為生成的 Token 追加擴展參數nameStpUtil.login(10001, SaLoginConfig.setExtra("name", "zhangsan"));// 連綴寫法追加多個StpUtil.login(10001, SaLoginConfig              .setExtra("name", "zhangsan")              .setExtra("age", 18)              .setExtra("role", "超級管理員"));// 獲取擴展參數 String name = StpUtil.getExtra("name");// 獲取任意 Token 的擴展參數 String name = StpUtil.getExtra("tokenValue", "name");

在多賬戶模式中集成 jwt

sa-token-jwt 插件默認只為 StpUtil 注入 StpLogicJwtFoxXxx 實現,自定義的 StpUserUtil 是不會自動注入的,我們需要幫其手動注入:M9928資訊網——每日最新資訊28at.com

/** * 為 StpUserUtil 注入 StpLogicJwt 實現  */@Autowiredpublic void setUserStpLogic() {    StpUserUtil.setStpLogic(new StpLogicJwtForSimple(StpUserUtil.TYPE));}

自定義 SaJwtUtil 生成 token 的算法

如果需要自定義生成 token 的算法(例如更換sign方式),直接重寫 SaJwtTemplate 對象即可:M9928資訊網——每日最新資訊28at.com

/** * 自定義 SaJwtUtil 生成 token 的算法  */@Autowiredpublic void setSaJwtTemplate() {    SaJwtUtil.setSaJwtTemplate(new SaJwtTemplate() {        @Override        public String generateToken(JWT jwt, String keyt) {            System.out.println("------ 自定義了 token 生成算法");            return super.generateToken(jwt, keyt);        }    });}

注意點

1、使用 jwt-simple 模式后,is-share=false 恒等于 false。M9928資訊網——每日最新資訊28at.com

is-share=true 的意思是每次登錄都產生一樣的 token,這種策略和 [ 為每個 token 單獨設定 setExtra 數據 ] 不兼容的, 為保證正確設定 Extra 數據,當使用 jwt-simple 模式后,is-share 配置項 恒等于 false。M9928資訊網——每日最新資訊28at.com

2、使用 jwt-mixin 模式后,is-concurrent 必須為 true。M9928資訊網——每日最新資訊28at.com

is-concurrent=false 代表每次登錄都把舊登錄頂下線,但是 jwt-mixin 模式登錄的 token 并不會記錄在持久庫數據中, 技術上來講無法將其踢下線,所以此時頂人下線和踢人下線等 API 都屬于不可用狀態,所以此時 is-concurrent 配置項必須配置為 true。M9928資訊網——每日最新資訊28at.com

全局偵聽器

工作原理

Sa-Token 提供一種偵聽器機制,通過注冊偵聽器,你可以訂閱框架的一些關鍵性事件,例如:用戶登錄、退出、被踢下線等。M9928資訊網——每日最新資訊28at.com

事件觸發流程大致如下:M9928資訊網——每日最新資訊28at.com

框架默認內置了偵聽器 SaTokenListenerForLog 實現:代碼參考 ,功能是控制臺 log 打印輸出,你可以通過配置sa-token.is-log=true開啟。M9928資訊網——每日最新資訊28at.com

要注冊自定義的偵聽器也非常簡單:M9928資訊網——每日最新資訊28at.com

  1. 新建類實現 SaTokenListener 接口。
  2. 將實現類注冊到 SaTokenEventCenter 事件發布中心。

自定義偵聽器實現

新建實現類:

新建MySaTokenListener.java,實現SaTokenListener接口,并添加上注解@Component,保證此類被SpringBoot掃描到:M9928資訊網——每日最新資訊28at.com

/** * 自定義偵聽器的實現  */@Componentpublic class MySaTokenListener implements SaTokenListener {    /** 每次登錄時觸發 */    @Override    public void doLogin(String loginType, Object loginId, String tokenValue, SaLoginModel loginModel) {        System.out.println("---------- 自定義偵聽器實現 doLogin");    }    /** 每次注銷時觸發 */    @Override    public void doLogout(String loginType, Object loginId, String tokenValue) {        System.out.println("---------- 自定義偵聽器實現 doLogout");    }    /** 每次被踢下線時觸發 */    @Override    public void doKickout(String loginType, Object loginId, String tokenValue) {        System.out.println("---------- 自定義偵聽器實現 doKickout");    }    /** 每次被頂下線時觸發 */    @Override    public void doReplaced(String loginType, Object loginId, String tokenValue) {        System.out.println("---------- 自定義偵聽器實現 doReplaced");    }    /** 每次被封禁時觸發 */    @Override    public void doDisable(String loginType, Object loginId, String service, int level, long disableTime) {        System.out.println("---------- 自定義偵聽器實現 doDisable");    }    /** 每次被解封時觸發 */    @Override    public void doUntieDisable(String loginType, Object loginId, String service) {        System.out.println("---------- 自定義偵聽器實現 doUntieDisable");    }    /** 每次二級認證時觸發 */    @Override    public void doOpenSafe(String loginType, String tokenValue, String service, long safeTime) {        System.out.println("---------- 自定義偵聽器實現 doOpenSafe");    }    /** 每次退出二級認證時觸發 */    @Override    public void doCloseSafe(String loginType, String tokenValue, String service) {        System.out.println("---------- 自定義偵聽器實現 doCloseSafe");    }    /** 每次創建Session時觸發 */    @Override    public void doCreateSession(String id) {        System.out.println("---------- 自定義偵聽器實現 doCreateSession");    }    /** 每次注銷Session時觸發 */    @Override    public void doLogoutSession(String id) {        System.out.println("---------- 自定義偵聽器實現 doLogoutSession");    }    /** 每次Token續期時觸發 */    @Override    public void doRenewTimeout(String tokenValue, Object loginId, long timeout) {        System.out.println("---------- 自定義偵聽器實現 doRenewTimeout");    }}
2.2、將偵聽器注冊到事件中心:

以上代碼由于添加了 @Component 注解,會被 SpringBoot 掃描并自動注冊到事件中心,此時我們無需手動注冊。M9928資訊網——每日最新資訊28at.com

如果我們沒有添加 @Component 注解或者項目屬于非 IOC 自動注入環境,則需要我們手動將這個偵聽器注冊到事件中心:M9928資訊網——每日最新資訊28at.com

// 將偵聽器注冊到事件發布中心SaTokenEventCenter.registerListener(new MySaTokenListener());

事件中心的其它一些常用方法:M9928資訊網——每日最新資訊28at.com

// 獲取已注冊的所有偵聽器 SaTokenEventCenter.getListenerList(); // 重置偵聽器集合 SaTokenEventCenter.setListenerList(listenerList); // 注冊一個偵聽器 SaTokenEventCenter.registerListener(listener); // 注冊一組偵聽器 SaTokenEventCenter.registerListenerList(listenerList); // 移除一個偵聽器 SaTokenEventCenter.removeListener(listener); // 移除指定類型的所有偵聽器 SaTokenEventCenter.removeListener(cls); // 清空所有已注冊的偵聽器 SaTokenEventCenter.clearListener(); // 判斷是否已經注冊了指定偵聽器  SaTokenEventCenter.hasListener(listener); // 判斷是否已經注冊了指定類型的偵聽器   SaTokenEventCenter.hasListener(cls);
2.3、啟動測試:

在 TestController 中添加登錄測試代碼:M9928資訊網——每日最新資訊28at.com

// 測試登錄接口 @RequestMapping("login")public SaResult login() {    System.out.println("登錄前");    StpUtil.login(10001);            System.out.println("登錄后");    return SaResult.ok();}

3、其它注意點

3.1、你可以通過繼承SaTokenListenerForSimple快速實現一個偵聽器:
@Componentpublic class MySaTokenListener extends SaTokenListenerForSimple {    /*     * SaTokenListenerForSimple 對所有事件提供了空實現,通過繼承此類,你只需重寫一部分方法即可實現一個可用的偵聽器。     */    /** 每次登錄時觸發 */    @Override    public void doLogin(String loginType, Object loginId, String tokenValue, SaLoginModel loginModel) {        System.out.println("---------- 自定義偵聽器實現 doLogin");    }}3.2、使用匿名內部類的方式注冊:// 登錄時觸發 SaTokenEventCenter.registerListener(new SaTokenListenerForSimple() {    @Override    public void doLogin(String loginType, Object loginId, String tokenValue, SaLoginModel loginModel) {        System.out.println("---------------- doLogin");    }});
3.3、使用 try-catch 包裹不安全的代碼:

如果你認為你的事件處理代碼是不安全的(代碼可能在運行時拋出異常),則需要使用 try-catch 包裹代碼,以防因為拋出異常導致 Sa-Token 的整個登錄流程被強制中斷。M9928資訊網——每日最新資訊28at.com

// 登錄時觸發 SaTokenEventCenter.registerListener(new SaTokenListenerForSimple() {    @Override    public void doLogin(String loginType, Object loginId, String tokenValue, SaLoginModel loginModel) {        try {            // 不安全代碼需要寫在 try-catch 里             // ......          } catch (Exception e) {            e.printStackTrace();        }    }});
3.4、疑問:一個項目可以注冊多個偵聽器嗎?

可以,多個偵聽器間彼此獨立,互不影響,按照注冊順序依次接受到事件通知。M9928資訊網——每日最新資訊28at.com

單點登錄

技術選型:[ 單點登錄 ] VS [ OAuth2.0 ]

功能點M9928資訊網——每日最新資訊28at.com

SSO單點登錄M9928資訊網——每日最新資訊28at.com

OAuth2.0M9928資訊網——每日最新資訊28at.com

統一認證M9928資訊網——每日最新資訊28at.com

支持度高M9928資訊網——每日最新資訊28at.com

支持度高M9928資訊網——每日最新資訊28at.com

統一注銷M9928資訊網——每日最新資訊28at.com

支持度高M9928資訊網——每日最新資訊28at.com

支持度低M9928資訊網——每日最新資訊28at.com

多個系統會話一致性M9928資訊網——每日最新資訊28at.com

強一致M9928資訊網——每日最新資訊28at.com

弱一致M9928資訊網——每日最新資訊28at.com

第三方應用授權管理M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

支持度高M9928資訊網——每日最新資訊28at.com

自有系統授權管理M9928資訊網——每日最新資訊28at.com

支持度高M9928資訊網——每日最新資訊28at.com

支持度低M9928資訊網——每日最新資訊28at.com

Client級的權限校驗M9928資訊網——每日最新資訊28at.com

不支持M9928資訊網——每日最新資訊28at.com

支持度高M9928資訊網——每日最新資訊28at.com

集成簡易度M9928資訊網——每日最新資訊28at.com

比較簡單M9928資訊網——每日最新資訊28at.com

難度中等M9928資訊網——每日最新資訊28at.com

注:以上僅為在 Sa-Token 中兩種技術的差異度比較,不同框架的實現可能略有差異,但整體思想是一致的。M9928資訊網——每日最新資訊28at.com

SSO單點登錄

什么是單點登錄?解決什么問題?

舉個場景,假設我們的系統被切割為N個部分:商城、論壇、直播、社交…… 如果用戶每訪問一個模塊都要登錄一次,那么用戶將會瘋掉, 為了優化用戶體驗,我們急需一套機制將這N個系統的認證授權互通共享,讓用戶在一個系統登錄之后,便可以暢通無阻的訪問其它所有系統。M9928資訊網——每日最新資訊28at.com

單點登錄——就是為了解決這個問題而生!M9928資訊網——每日最新資訊28at.com

簡而言之,單點登錄可以做到:在多個互相信任的系統中,用戶只需登錄一次,就可以訪問所有系統。M9928資訊網——每日最新資訊28at.com

架構選型

Sa-Token-SSO 由簡入難劃分為三種模式,解決不同架構下的 SSO 接入問題:M9928資訊網——每日最新資訊28at.com

系統架構M9928資訊網——每日最新資訊28at.com

采用模式M9928資訊網——每日最新資訊28at.com

簡介M9928資訊網——每日最新資訊28at.com

文檔鏈接M9928資訊網——每日最新資訊28at.com

前端同域 + 后端同 RedisM9928資訊網——每日最新資訊28at.com

模式一M9928資訊網——每日最新資訊28at.com

共享 Cookie 同步會話M9928資訊網——每日最新資訊28at.com

文檔M9928資訊網——每日最新資訊28at.com

、示例M9928資訊網——每日最新資訊28at.com

前端不同域 + 后端同 RedisM9928資訊網——每日最新資訊28at.com

模式二M9928資訊網——每日最新資訊28at.com

URL重定向傳播會話M9928資訊網——每日最新資訊28at.com

文檔M9928資訊網——每日最新資訊28at.com

、示例M9928資訊網——每日最新資訊28at.com

前端不同域 + 后端不同 RedisM9928資訊網——每日最新資訊28at.com

模式三M9928資訊網——每日最新資訊28at.com

Http請求獲取會話M9928資訊網——每日最新資訊28at.com

文檔M9928資訊網——每日最新資訊28at.com

、示例M9928資訊網——每日最新資訊28at.com

  1. 前端同域:就是指多個系統可以部署在同一個主域名之下,比如:c1.domain.com、c2.domain.com、c3.domain.com。
  2. 后端同Redis:就是指多個系統可以連接同一個Redis。PS:這里并不需要把所有項目的數據都放在同一個Redis中,Sa-Token提供了 [權限緩存與業務緩存分離] 的解決方案,詳情戳:Alone獨立Redis插件。
  3. 如果既無法做到前端同域,也無法做到后端同Redis,那么只能走模式三,Http請求獲取會話(Sa-Token對SSO提供了完整的封裝,你只需要按照示例從文檔上復制幾段代碼便可以輕松集成)。

Sa-Token-SSO 特性

  1. API 簡單易用,文檔介紹詳細,且提供直接可用的集成示例。
  2. 支持三種模式,不論是否跨域、是否共享Redis、是否前后端分離,都可以完美解決。
  3. 安全性高:內置域名校驗、Ticket校驗、秘鑰校驗等,杜絕Ticket劫持、Token竊取等常見攻擊手段(文檔講述攻擊原理和防御手段)。
  4. 不丟參數:筆者曾試驗多個單點登錄框架,均有參數丟失的情況,比如重定向之前是:http://a.com?id=1&name=2,登錄成功之后就變成了:http://a.com?id=1,Sa-Token-SSO內有專門的算法保證了參數不丟失,登錄成功之后原路返回頁面。
  5. 無縫集成:由于Sa-Token本身就是一個權限認證框架,因此你可以只用一個框架同時解決權限認證 + 單點登錄問題,讓你不再到處搜索:xxx單點登錄與xxx權限認證如何整合……
  6. 高可定制:Sa-Token-SSO模塊對代碼架構侵入性極低,結合Sa-Token本身的路由攔截特性,你可以非常輕松的定制化開發。

搭建統一認證中心 SSO-Server

添加maven依賴

<!-- Sa-Token 權限認證,在線文檔:https://sa-token.cc --><dependency>    <groupId>cn.dev33</groupId>    <artifactId>sa-token-spring-boot-starter</artifactId>    <version>1.34.0</version></dependency><!-- Sa-Token 插件:整合SSO --><dependency>    <groupId>cn.dev33</groupId>    <artifactId>sa-token-sso</artifactId>    <version>1.34.0</version></dependency><!-- Sa-Token 整合 Redis (使用 jackson 序列化方式) --><dependency>    <groupId>cn.dev33</groupId>    <artifactId>sa-token-dao-redis-jackson</artifactId>    <version>1.34.0</version></dependency><dependency>    <groupId>org.apache.commons</groupId>    <artifactId>commons-pool2</artifactId></dependency><!-- 視圖引擎(在前后端不分離模式下提供視圖支持) --><dependency>    <groupId>org.springframework.boot</groupId>    <artifactId>spring-boot-starter-thymeleaf</artifactId></dependency><!-- Http請求工具(在模式三的單點注銷功能下用到,如不需要可以注釋掉) --><dependency>    <groupId>com.dtflys.forest</groupId>    <artifactId>forest-spring-boot-starter</artifactId>    <version>1.5.26</version></dependency>

除了 sa-token-spring-boot-starter 和 sa-token-sso 以外,其它包都是可選的:M9928資訊網——每日最新資訊28at.com

  • 在 SSO 模式三時 Redis 相關包是可選的
  • 在前后端分離模式下可以刪除 thymeleaf 相關包
  • 在不需要 SSO 模式三單點注銷的情況下可以刪除 http 工具包

建議先完整測試三種模式之后再對pom依賴進行酌情刪減。M9928資訊網——每日最新資訊28at.com

開放認證接口

/** * Sa-Token-SSO Server端 Controller  */@RestControllerpublic class SsoServerController {    /*     * SSO-Server端:處理所有SSO相關請求 (下面的章節我們會詳細列出開放的接口)      */    @RequestMapping("/sso/*")    public Object ssoRequest() {        return SaSsoProcessor.instance.serverDister();    }    /**     * 配置SSO相關參數      */    @Autowired    private void configSso(SaSsoConfig sso) {        // 配置:未登錄時返回的View         sso.setNotLoginView(() -> {            String msg = "當前會話在SSO-Server端尚未登錄,請先訪問"                    + "<a href='/sso/doLogin?name=sa&pwd=123456' target='_blank'> doLogin登錄 </a>"                    + "進行登錄之后,刷新頁面開始授權";            return msg;        });        // 配置:登錄處理函數         sso.setDoLoginHandle((name, pwd) -> {            // 此處僅做模擬登錄,真實環境應該查詢數據進行登錄             if("sa".equals(name) && "123456".equals(pwd)) {                StpUtil.login(10001);                return SaResult.ok("登錄成功!").setData(StpUtil.getTokenValue());            }            return SaResult.error("登錄失敗!");        });        // 配置 Http 請求處理器 (在模式三的單點注銷功能下用到,如不需要可以注釋掉)         sso.setSendHttp(url -> {            try {                // 發起 http 請求                 System.out.println("------ 發起請求:" + url);                return Forest.get(url).executeAsString();            } catch (Exception e) {                e.printStackTrace();                return null;            }        });    }}

application.yml配置

# 端口server:    port: 9000# Sa-Token 配置sa-token:     # ------- SSO-模式一相關配置  (非模式一不需要配置)     # cookie:         # 配置 Cookie 作用域         # domain: stp.com     # ------- SSO-模式二相關配置     sso:         # Ticket有效期 (單位: 秒),默認五分鐘         ticket-timeout: 300        # 所有允許的授權回調地址        allow-url: "*"        # 是否打開單點注銷功能        is-slo: true        # ------- SSO-模式三相關配置 (下面的配置在SSO模式三并且 is-slo=true 時打開)        # 是否打開模式三         isHttp: true        # 接口調用秘鑰(用于SSO模式三的單點注銷功能)        secretkey: kQwIOrYvnXmSDkwEiFngrKidMcdrgKor        # ---- 除了以上配置項,你還需要為 Sa-Token 配置http請求處理器(文檔有步驟說明) spring:     # Redis配置 (SSO模式一和模式二使用Redis來同步會話)    redis:        # Redis數據庫索引(默認為0)        database: 1        # Redis服務器地址        host: 127.0.0.1        # Redis服務器連接端口        port: 6379        # Redis服務器連接密碼(默認為空)        password: forest:     # 關閉 forest 請求日志打印    log-enabled: false

訪問統一授權地址:M9928資訊網——每日最新資訊28at.com

  • http://localhost:9000/sso/auth

圖片M9928資訊網——每日最新資訊28at.com

可以看到這個頁面目前非常簡陋,這是因為我們以上的代碼示例,主要目標是為了帶大家從零搭建一個可用的SSO認證服務端,所以就對一些不太必要的步驟做了簡化。M9928資訊網——每日最新資訊28at.com

本文鏈接:http://www.tebozhan.com/showinfo-26-35341-0.html再見,Shiro !你好,Sa-Token!

聲明:本網頁內容旨在傳播知識,若有侵權等問題請及時與本網聯系,我們將在第一時間刪除處理。郵件:2376512515@qq.com

上一篇: 再也不怕面試官問watch、computed、watchEffect的區別了

下一篇: 完美世界王雨蘊:文創思維讓科技國潮產業綻放時代生命力

標簽:
  • 熱門焦點
  • 對標蘋果的靈動島 華為帶來實況窗功能

    繼蘋果的靈動島之后,華為也在今天正式推出了“實況窗”功能。據今天鴻蒙OS 4.0的現場演示顯示,華為的實況窗可以更高效的展現出實時通知,比如鎖屏上就能看到外賣、打車、銀行
  • 石頭智能洗地機A10 Plus體驗:雙向自清潔治好了我的懶癌

    一、前言和介紹專為家庭請假懶人而生的石頭科技在近日又帶來了自己的全新旗艦新品,石頭智能洗地機A10 Plus。從這個產品名上就不難看出,這次石頭推出的并不是常見的掃地機器
  • 5月iOS設備性能榜:M1 M2依舊是榜單前五

    和上個月一樣,沒有新品發布的iOS設備性能榜的上榜設備并沒有什么更替,僅僅只有跑分變化而產生的排名變動,剛剛開始的蘋果WWDC2023,推出的產品也依舊是新款Mac Pro、新款Mac Stu
  • 使用LLM插件從命令行訪問Llama 2

    最近的一個大新聞是Meta AI推出了新的開源授權的大型語言模型Llama 2。這是一項非常重要的進展:Llama 2可免費用于研究和商業用途。(幾小時前,swyy發現它已從LLaMA 2更名為Lla
  • 一文掌握 Golang 模糊測試(Fuzz Testing)

    模糊測試(Fuzz Testing)模糊測試(Fuzz Testing)是通過向目標系統提供非預期的輸入并監視異常結果來發現軟件漏洞的方法。可以用來發現應用程序、操作系統和網絡協議等中的漏洞或
  • 微軟邀請 Microsoft 365 商業用戶,測試視頻編輯器 Clipchamp

    8 月 1 日消息,微軟近日宣布即將面向 Microsoft 365 商業用戶,開放 Clipchamp 應用,邀請用戶通過該應用來編輯視頻。微軟于 2021 年收購 Clipchamp,隨后開始逐步整合到 Microsof
  • JVM優化:實戰OutOfMemoryError異常

    一、Java堆溢出堆內存中主要存放對象、數組等,只要不斷地創建這些對象,并且保證 GC Roots 到對象之間有可達路徑來避免垃 圾收集回收機制清除這些對象,當這些對象所占空間超過
  • 破圈是B站頭上的緊箍咒

    來源 | 光子星球撰文 | 吳坤諺編輯 | 吳先之每年的暑期檔都少不了瞄準追劇女孩們的古偶劇集,2021年有優酷的《山河令》,2022年有愛奇藝的《蒼蘭訣》,今年卻輪到小破站抓住了追
  • 利用職權私自解除被封帳號 Meta開除20多名員工

    11月18日消息,據外媒援引知情人士表示,過去一年時間內,Facebook母公司Meta解雇或處罰了20多名員工以及合同工,指控這些人通過內部系統以不當方式重置用戶帳號,其
Top