java中如何踢人下線?封禁某個帳號後使其會話當即掉線!

需求場景

封禁帳號是一個比較常見的業務需求,尤爲是在論壇、社區類型的項目中,當出現了違規用戶時咱們須要將其帳號當即封禁。java

常規的設計思路是:在設計用戶表時增長一個狀態字段,例如:status,其值爲1時表明帳號正常,其值爲0時表明帳號已被封禁。git

當咱們須要封禁一個帳號時,只須要將其帳號的status值修改成0便可,對方再次登陸系統時,咱們即可以檢測到status值不爲1禁止登陸。github

這種模式雖然思路簡單,但也有一個不小的問題,那就是: 若是對方一直在線不註銷登陸呢?spring

因爲咱們只在登陸時檢測status值,這也就表明:若是對方不主動註銷帳號,他的會話仍是會一直存在且有效。數據庫

那怎麼才能夠作到在封禁帳號後當即生效?緩存

你可能會想到使用攔截器,攔截用戶的全部請求檢測帳號狀態:status=0時禁止訪問,status=1時再對請求放行app

此方式雖然解決了問題,可是若是每次請求都要進行數據庫查詢的話,數據庫表示你如此掃蕩我你就沒有一點心理壓力嗎?框架

那怎麼辦?上緩存?雖然能夠緩解性能壓力,但彷佛總感受沒有完美解決問題。spring-boot

真正的問題點在於:一個正常的系統只有0.01%的用戶是須要封禁的,咱們對其它99.99%用戶的實時檢測都是沒必要要的性能浪費。性能

在如上場景中,咱們真正須要的是一個踢人下線的操做,即:咱們須要在封禁某個用戶後,使他的會話當即掉線,即時他從新登陸也會被禁止登陸

那麼,怎麼作到實時踢人下線呢?

筆者使用的是sa-token權限認證框架,這個框架封裝了踢人下線操做調用很是方便,不用像其它框架同樣還須要我本身再封裝一層才能作到。

具體代碼

  1. 首先添加pom.xml框架
<!-- sa-token 權限認證, 在線文檔:http://sa-token.dev33.cn/ -->
<dependency>
    <groupId>cn.dev33</groupId>
    <artifactId>sa-token-spring-boot-starter</artifactId>
    <version>1.12.1</version>
</dependency>
  1. 在用戶登陸時將帳號id寫入會話中
@RestController
@RequestMapping("user")
public class UserController {
    @RequestMapping("doLogin")
    public String doLogin(String username, String password) {
        // 此處僅做示例模擬,真實項目須要從數據庫中查詢數據進行比對 
        if("zhang".equals(username) && "123456".equals(password)) {
            StpUtil.setLoginId(10001);
            return "登陸成功";
        }
        return "登陸失敗";
    }
}
  1. 將指定id的帳號
// 使指定id帳號的會話註銷登陸,對方再次訪問系統時會拋出`NotLoginException`異常,場景值爲-5
@RequestMapping("kickout")
public String kickout(long userId) {
    StpUtil.logoutByLoginId(userId);
    return "剔出成功";
}

關鍵代碼就在 StpUtil.logoutByLoginId(userId) 這一句,使指定id的帳號註銷登陸 (踢人下線)

若是以爲文章寫得不錯還請你們不要吝惜爲文章點個贊,您的支持是我更新的最大動力!

最後附上項目連接:

相關文章
相關標籤/搜索