一.SSO单点登陆介绍:
单点登录的英文名叫做:Single Sign On(简称SSO)
在以前的系统架构中,一般单系统的架构,就是所有的功能都在同一个系统上,如下图:
后来,为了合理利用资源以及降低服务的耦合性,把单系统拆解为多个子服务。
比如阿里的淘宝和天猫,很明显地我们可以知道这是两个系统,但是你在使用的时候,登录了天猫,淘宝也会自动登录,再次访问淘宝就不需要登陆了。
简单地来说,就是用户不需要感知内部逻辑的处理,只需要登陆一次,各个服务都可感知用户已经登陆了。
二.回顾单系统登陆
在初学javaWeb时,做得最多的功能就是登陆功能了,这里简单的介绍一下初学的时候,登陆是怎样完成的。
1.输入用户名与密码
2.提交表单,后端代码访问数据库判断用户名与密码是否正确
3.将用户信息存到session中
众所周知,HTTP协议是无状态的,这意味着服务端无法确认用户的信息。于是乎,W3C就提出了:给每一个用户都发一个通行证,无论谁访问的时候都需要携带通行证,这样服务器就可以从通行证上确认用户的信息。通行证就是Cookie。
这里区分一下cookie与session的区别,cookie是存放在客户端的,session是存放在服务端的。也就是说,以往的做法是把用户信息存放在session中会造成服务巨大的压力。所以后来我们使用了cookie。
三、多系统登录的问题与解决
1.问题
在nginx中,我们使用得最多的就是负载均衡与反向代理,nginx可以有效的将流量以配置权重分发到各个服务中。尤其是分布式用得比较多,这里我对分布式不是太懂,没有进一步补充。如下图:
下图可以理解为淘宝双十一下单,我们在双十一通常并发量会非常大,就会造成我们出现下单页面在轮询。
这就是我们通过nginx监听80端口,然后通过分布式,将流量有效的分发到各个服务中,减轻服务的压力
但归根揭底的是,3个订单服务,不知道我们登陆的是哪一个订单服务,也就是说,如果session共享的问题没解决的话,那么你登陆了一次去下单一个商品,然后继续下单第二个商品,有可能会要你重新登陆,所以这个是很蛋疼的问题。
2.解决方案
我们通过开发一个通用的SSO服务去解决session共享的问题,具体思路如下:
1.用户登陆成功后,将用户信息与token进行绑定,统一上传到redis中,与保存到本地cookie
2.每个服务都有一个拦截机制,就是说,私人页面,需要你判断cookie是否存在token跟redis的token是否过期两个条件
3.SSO单点登陆服务总体就是对token的管理也就是CRUD
4.注意,像爱奇艺这种,你很久不上去更新cookie过期时间,过了一段时间会直接过期,但是你每天登陆一次,cookie的过期时间是会重新刷新的。
3.具体代码与时序图如下:
拦截器配置类:
自定义拦截器:
登陆实现: