首頁 > 軟體

Redis實現單裝置登入的場景分析

2022-04-19 13:01:36

在有些場景下,我們希望使用者一個賬號只能登入一個裝置。

這個時候我們可以用Redis來實現。

原理: 使用者首次登入時,將使用者資訊存入Redis,key是使用者id,value是token。當用戶在其他裝置登入時,會重新生成token,這個時候原先的token已經被覆蓋了。所以使用者在存取需要登入賬號的操作時,系統會攔截請求判斷token是否存在。當然是不存在的,所以我們就實現了單個裝置登入的需求。

這裡只提供大概的樣例。

使用者登入

@PostMapping("login")
@ApiOperation(value = "使用者登入",notes = "使用者登入")
public GraceJSONResult login(@RequestParam String userId,HttpServletRequest request) throws Exception {
    String uToken = UUID.randomUUID().toString();
    //把token存入redis
    redis.set("redis_user_token"+":"+userId,uToken);
    //返回使用者資訊,包含token
    return GraceJSONResult.ok(usersVO);
}

攔截器

攔截哪些操作需要使用者登入,在攔截器中實現單裝置登入。

說明:BaseInfoProperties是共有的程式碼,整合這個類就可以直接使用reidis。

public class BaseInfoProperties {
    @Autowired
    public RedisOperator redis;
}

說明:GraceException是自定義的丟擲異常的類,這裡不做展示。

public class UserTokenInterceptor extends BaseInfoProperties implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        String userId = request.getHeader("headerUserId");
        String userToken = request.getHeader("headerUserToken");
        // 判斷使用者id和token是否為空
        if(StringUtils.isNotBlank(userId) && StringUtils.isNotBlank(userToken)){
            String redisToken=redis.get(REDIS_USER_TOKEN+":"+userId);
            //判斷token是否失效
            if(StringUtils.isBlank(redisToken)){
                GraceException.display(ResponseStatusEnum.UN_LOGIN);
                return false;
            }else {
                //判斷token是否一致,如果不一致,表示使用者在別的手機端登入,token被覆蓋了
                if(!redisToken.equalsIgnoreCase(redisToken)){
                    GraceException.display(ResponseStatusEnum.TICKET_INVALID);
                    return false;
                }
            }
        }else {
            // 使用者id和token為空
            GraceException.display(ResponseStatusEnum.UN_LOGIN);
            return false;
        }

        return true;
    }
}

註冊攔截器

@Configuration
public class InterceptorConfig implements WebMvcConfigurer{
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        //要攔截的請求,哪些需要登入
        registry.addInterceptor(userTokenInterceptor())
                .addPathPatterns("/userInfo/modifyUserInfo")
                .addPathPatterns("/userInfo/modifyImage");
    }
    //使用者未登入攔截器
    @Bean
    public UserTokenInterceptor userTokenInterceptor() {
       return  new UserTokenInterceptor();
    }
}

到此這篇關於Redis實現單裝置登入的文章就介紹到這了,更多相關redis單裝置登入內容請搜尋it145.com以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援it145.com!


IT145.com E-mail:sddin#qq.com