Redis实现一个账号只能登录一个设备


Posted in Redis onApril 19, 2022

在有些场景下,我们希望用户一个账号只能登录一个设备。

这个时候我们可以用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 相关文章推荐
详解RedisTemplate下Redis分布式锁引发的系列问题
Apr 27 Redis
redis三种高可用方式部署的实现
May 11 Redis
Redis高级数据类型Hyperloglog、Bitmap的使用
May 24 Redis
详解Redis集群搭建的三种方式
May 31 Redis
Redis缓存-序列化对象存储乱码问题的解决
Jun 21 Redis
k8s部署redis cluster集群的实现
Jun 24 Redis
Redis源码阅读:Redis字符串SDS详解
Jul 15 Redis
为什么RedisCluster设计成16384个槽
Sep 25 Redis
Jedis操作Redis实现模拟验证码发送功能
Sep 25 Redis
解决Redis启动警告问题
Feb 24 Redis
Redis实现订单过期删除的方法步骤
Jun 05 Redis
redis protocol通信协议及使用详解
Jul 15 Redis
Redis如何实现验证码发送 以及限制每日发送次数
Apr 18 #Redis
Redis实战高并发之扣减库存项目
Redis中key的过期删除策略和内存淘汰机制
解决 Redis 秒杀超卖场景的高并发
redis 解决库存并发问题实现数量控制
Redis超详细讲解高可用主从复制基础与哨兵模式方案
redis复制有可能碰到的问题汇总
Apr 03 #Redis
You might like
德生S2000电路分析
2021/03/02 无线电
php5.2以下版本无json_decode函数的解决方法
2014/05/25 PHP
JavaScript延迟加载
2021/03/09 Javascript
悄悄用脚本检查你访问过哪些网站的代码
2010/12/04 Javascript
javascript中不提供sleep功能如何实现这个功能
2014/05/27 Javascript
jQuery DOM删除节点操作指南
2015/03/03 Javascript
javascript实现随时变化着的背景颜色
2015/04/02 Javascript
Google 地图获取API Key详细教程
2016/08/06 Javascript
深入理解AngularJS中的ng-bind-html指令和$sce服务
2016/09/08 Javascript
微信小程序 图片等比例缩放(图片自适应屏幕)
2016/11/16 Javascript
JavaScript实现经典排序算法之选择排序
2016/12/28 Javascript
jQuery中绑定事件bind() on() live() one()的异同
2017/02/23 Javascript
使用requirejs模块化开发多页面一个入口js的使用方式
2017/06/14 Javascript
react.js使用webpack搭配环境的入门教程
2017/08/14 Javascript
基于javascript 显式转换与隐式转换(详解)
2017/12/15 Javascript
vue-cli项目配置多环境的详细操作过程
2018/10/30 Javascript
详解JavaScript中的强制类型转换
2019/04/15 Javascript
javascript面向对象三大特征之多态实例详解
2019/07/24 Javascript
[01:10]DOTA2亚洲邀请赛 征战号角响彻全场
2015/01/06 DOTA
[12:29]2018国际邀请赛 开幕秀
2018/08/22 DOTA
Django与遗留的数据库整合的方法指南
2015/07/24 Python
Numpy中矩阵matrix读取一列的方法及数组和矩阵的相互转换实例
2018/07/02 Python
TensorFlow查看输入节点和输出节点名称方式
2020/01/04 Python
Python可变对象与不可变对象原理解析
2020/02/25 Python
html5 canvas-1.canvas介绍(hello canvas)
2013/01/07 HTML / CSS
Smallable英国家庭概念店:设计师童装及家居装饰
2017/07/05 全球购物
银行见习期自我鉴定
2014/01/29 职场文书
导购员的岗位职责
2014/02/08 职场文书
购房意向书范本
2014/04/01 职场文书
最新离婚协议书范本
2014/08/19 职场文书
2014国庆节主题活动方案:快乐的国庆节
2014/09/16 职场文书
2014年学习委员工作总结
2014/11/14 职场文书
换届选举主持词
2015/07/03 职场文书
找规律教学反思
2016/02/23 职场文书
党员公开承诺书(2016最新版)
2016/03/24 职场文书
vue项目配置sass及引入外部scss文件
2022/04/14 Vue.js