单点登录SSO的实现流程

文章类别 in java, 分布式系统

传统的登录方式

kiri开发了一个项目,这个项目只有一个web工程,所以他在做系统登录的时候呢?是这样做的:

UML sequence diagram

“当用户进行登录的时候,他把登录请求交给LoginController,这时候就会去数据库中根据用户 传来的用户名查询查询密码,判断密码是否正确,如果密码正确的话就会把用户信息放到session里, 如果不正确就提示用户密码不正确。

当用户在该系统中需要访问用户相关信息的时候,那么这个时候就可以直接到session中判断用户 是否登录,如果从session获取到有该用户的信息,那么就直接展示就可以了,不需要再次登录了。”

kiri突然觉得自己很是牛逼,就开始吭哧吭哧的写代码了… 不到半个小时kiri就写完了,然后部署好了系统就出去happy了!

后来,系统并发量大了起来,在一个Tomcat中已经无法支撑了,这时候kiri开始做起集群来, 把web工程部署多了一台Tomcat,然后用nginx做负载均衡。

不到半小时kiri就部署完了,然后又出去happy去了…

但是正当kirihappy的时候,许多用户反映在这个系统里需要多次登录,有时候登录了还需要再次登录! kiri有点纳闷,怎么会这样,于是只能扫兴的回去打开电脑看看怎么回事!

kiri看了5分钟后发现了问题:

原来,把web部署在不同的Tomcat上,他们的session是不同的,也就是每个tomcat都有她自己独立的session。 当用户登录系统的时候,nginx将用户请求代理到第一个tomcat进行登录,将用户信息存放到session中,当用户再次请求系统的时候,nginx可能会 将用户的请求代理转发给第二个tomcat进行处理,这个时候第二个tomcat的session并没有该用户的信息,所以就需要用户去登录!

于是kiri就开始配置tomcat,让它们之间的session进行共享,也就是当tomcat的session发生改变的时候,就会广播给配置好的另一个tomcat,让它们的 session保持同步!

这样子用户就不需要再进行多次登录了,kiri搞完之后又出去happy了…

SSO单点登录

kiri团队后来做了个比之前大一点的系统,这个系统是采用分布式系统架构的,kiri这次负责的用户相关的功能模块。 kiri发现系统被分成了多个子系统,这些子系统将来可能会被部署到多个不同的服务器上,如果采用之前的session 共享进行用户登录的话,会非常占用系统资源,而且非常影响性能!

于是kiri就发现了原来有个叫做单点登录的玩意,上Google搜了一下

单点登录

发现维基百科对它的定义是这样的:

单点登录(英语:Single sign-on,缩写为 SSO),又译为单一签入,一种对于许多相互关连,但是又是各自独立的软件系统, 提供访问控制的属性。当拥有这项属性时,当用户登录时,就可以获取所有系统的访问权限,不用对每个单一系统都逐一登录。

发现这正是他想要的!

于是kiri就创建了一个子模块,叫做SSO,这个模块就是专门来管理用户的登录的,它将用户的session数据用Redis存放,因为 Redis可以全局管理数据,可以设置key值的生存有效期,而且访问效率很快!

单点登录实现流程

kiri展开了思路:

  1. 用户在每个系统中对用户的登录请求会发送给SSO系统,SSO系统显示登录页面,在SSO系统中接收用户名和密码;

  2. 根据用户名密码去查询数据库是否存在,如果存在就会生成Token,这个Token对应的便是存放到Redis中的key, 用户信息就是对应的Value,然后存放到Redis中,接着设置登录有效期;

  3. 接着返回登录成功,并将token写入cookie中,这个时候再判断是否有回调的URL,如果有就重定向到用户需要的页面, 没有就跳转到门户首页;

  4. 当用户在另一个系统中需要请求到用户信息的时候,就会通过拦截器判断用户中的请求的cookie中的token是否在redis中有数据, 如果不存在就会返回登录url,如果存在说明已经登录,那么就可以刷新登录有效期,并将用户信息进行返回!

kiri搞完之后发现不错,Redis存取速度快,不会出现多个session共享影响性能问题。更加高效,所以认为 创建一个SSO系统来做单点登录是很有必要的!

我的相关文章

相关资料