SpringBoot整合Redis实现常用功能
- 建议大小伙们,在写业务的时候,提前画好 流程图 ,思路会清晰很多。
- 文末有解决缓存穿透和击穿的通用工具类。
1 登陆功能
我想, 登陆功能
是每个项目必备的功能吧,但是想设计好,却是很难!下面介绍两种登陆功能的解决方式:
- 基于Session实现登录流程
- 基于Redis实现登录流程
1.1 基于Session实现登录流程
功能流程:
发送验证码:
-
用户在提交手机号后,会校验手机号是否合法,如果不合法,则要求用户重新输入手机号
-
如果手机号合法,后台此时生成对应的验证码,同时将验证码进行保存,然后再通过短信的方式将验证码发送给用户
短信验证码登录、注册:
- 用户将验证码和手机号进行输入,后台从session中拿到当前验证码,然后和用户输入的验证码进行校验,如果不一致,则无法通过校验,如果一致,则后台根据手机号查询用户,
- 如果用户不存在,则为用户创建账号信息,保存到数据库,无论是否存在,都会将用户信息保存到session中,方便后续获得当前登录信息
校验登录状态:
- 用户在请求时候,会从cookie中携带者JsessionId到后台,后台通过JsessionId从session中拿到用户信息,如果没有session信息,则进行拦截,如果有session信息,则
- 将用户信息保存到threadLocal中,并且放行
1.1.1 session共享问题
基于 session方式实现登陆功能
,最大的缺点就是在 多台
tomcat下session无法共享,就会下出现下面问题。
核心思路分析:
每个tomcat中都有一份属于自己的session,假设用户第一次访问第一台tomcat,并且把自己的信息存放到第一台服务器的session中,但是第二次这个用户访问到了第二台tomcat,那么在第二台服务器上,肯定没有第一台服务器存放的session,所以此时 整个登录拦截功能就会出现问题,我们能如何解决这个问题呢?早期的方案是 session拷贝
,就是说虽然每个tomcat上都有不同的session,但是每当任意一台服务器的session修改时,都会同步给其他的Tomcat服务器的session,这样的话,就可以实现session的共享了
但是这种方案具有两个大问题
1、每台服务器中都有 完整的一份session数据
,服务器压力过大。
2、session拷贝数据时,可能会 出现延迟
所以咱们后来采用的方案都是基于redis来完成,我们把session换成redis,redis数据本身就是共享的,就可以避免session共享的问题了
1.2 Redis替代Session
1.2.1、设计key的结构
首先我们要思考一下利用redis来存储数据,那么到底使用哪种结构呢?由于存入的数据比较简单,我们可以考虑使用String,或者是使用哈希,如下图,如果使用String,同学们注意他的value,用多占用一点空间,如果使用哈希,则他的value中只会存储他数据本身,如果不是特别在意内存,其实使用String就可以啦。
1.2.2、设计key的具体细节
所以我们可以使用String结构,就是一个简单的key,value键值对的方式,但是关于key的处理,session他是每个用户都有自己的session,但是redis的key是共享的,咱们就不能使用code了