何为单点登录?

今天看到一篇文章,和单点登录有关系,记得有一次课堂答辩,有同学提到了单点登录这个词,我问了一句,老师要求我写一篇关于单点登陆的博客,今天终于有机会了。

什么是单点登录?单点登录全称Single Sign On(以下简称SSO),是指在多系统应用群中登录一个系统,便可在其他所有系统中得到授权而无需再次登录,包括单点登录与单点注销两部分。

相比于单系统登录,sso需要一个独立的认证中心,只有认证中心能接受用户的用户名密码等安全信息,其他系统不提供登录入口,只接受认证中心的间接授权。间接授权通过令牌实现,sso认证中心验证用户的用户名密码没问题,创建授权令牌,在接下来的跳转过程中,授权令牌作为参数发送给各个子系统,子系统拿到令牌,即得到了授权,可以借此创建局部会话,局部会话登录方式与单系统的登录方式相同。这个过程,也就是单点登录的原理。

只是简要介绍下基于java的实现过程,不提供完整源码,明白了原理,我相信你们可以自己实现。sso采用客户端/服务端架构,我们先看sso-client与sso-server要实现的功能(下面:sso认证中心=sso-server)。

sso-client

  1. 拦截子系统未登录用户请求,跳转至sso认证中心;
  2. 接收并存储sso认证中心发送的令牌;
  3. 与sso-server通信,校验令牌的有效性;
  4. 建立局部会话;
  5. 拦截用户注销请求,向sso认证中心发送注销请求;
  6. 接收sso认证中心发出的注销请求,销毁局部会话。

sso-server

  1. 验证用户的登录信息;
  2. 创建全局会话;
  3. 创建授权令牌;
  4. 与sso-client通信发送令牌;
  5. 校验sso-client令牌有效性;
  6. 系统注册;
  7. 接收sso-client注销请求,注销所有会话。

接下来,我们按照原理来一步步实现sso吧!

1、sso-client拦截未登录请求

Java拦截请求的方式有servlet、filter、listener三种方式,我们采用filter。在sso-client中新建LoginFilter.java类并实现Filter接口,在doFilter()方法中加入对未登录用户的拦截

public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {    HttpServletRequest req = (HttpServletRequest) request;    HttpServletResponse res = (HttpServletResponse) response;    HttpSession session = req.getSession();         if (session.getAttribute("isLogin")) {        chain.doFilter(request, response);        return;    }    //跳转至sso认证中心    res.sendRedirect("sso-server-url-with-system-url");}

2、sso-server拦截未登录请求

拦截从sso-client跳转至sso认证中心的未登录请求,跳转至登录页面,这个过程与sso-client完全一样。

3、sso-server验证用户登录信息

用户在登录页面输入用户名密码,请求登录,sso认证中心校验用户信息,校验成功,将会话状态标记为“已登录”。

@RequestMapping("/login")public String login(String username, String password, HttpServletRequest req) {    this.checkLoginInfo(username, password);    req.getSession().setAttribute("isLogin", true);    return "success";}

4、sso-server创建授权令牌

授权令牌是一串随机字符,以什么样的方式生成都没有关系,只要不重复、不易伪造即可,下面是一个例子。

  •  

String token = UUID.randomUUID().toString();

5、sso-client取得令牌并校验

sso认证中心登录后,跳转回子系统并附上令牌,子系统(sso-client)取得令牌,然后去sso认证中心校验,在LoginFilter.java的doFilter()中添加几行。

 

// 请求附带token参数String token = req.getParameter("token");if (token != null) {    // 去sso认证中心校验token    boolean verifyResult = this.verify("sso-server-verify-url", token);    if (!verifyResult) {        res.sendRedirect("sso-server-url");        return;    }    chain.doFilter(request, response);}

verify()方法使用httpClient实现,这里仅简略介绍,httpClient详细使用方法请参考官方文档。

 

HttpPost httpPost = new HttpPost("sso-server-verify-url-with-token");HttpResponse httpResponse = httpClient.execute(httpPost);

原文地址:https://www.cnblogs.com/yyh-678/p/11028025.html