0%

单点登录

SSO, Single Sign On, 单点登录

1. 应用场景

大型Web项目一般都有这样的开发场景:

  • 项目子系统众多, 需要一个统一的登录系统, 用户只需要登录一次就可以访问其他信任的子系统应用.
  • 子系统间依赖复杂, 前端页面间有相互跳转需求.
  • 前后端分离, 各个系统间需要跨域访问.

2. 单点登录序列图

  • ticket
    SSO系统发放给前端页面的登录凭证, 之后交给子系统判断其有效性.
    为了防止被拦截, ticket的存活时间极短, 一般设置为5秒左右.
  • sid
    即Session ID, 用户登录成功后的会话ID.
    同一用户在各个系统间获得的sid应该不同, 以防止某个子系统泄露sid而影响其他子系统.
    用户与sid之间是一对多的关系.
  1. 用户在浏览器触发任意请求访问子系统.
  2. 子系统验证请求的Cookie中是否有sid.
    假设目前为首次登录, Cookie为空, 则返回未登录状态.
  3. 子系统页面跳转到SSO系统的登录页面.
  4. 用户输入相关登录信息(用户名, 密码, 验证码等), 请求登录验证.
  5. SSO系统验证用户信息, 生成ticket及用户信息;返回结果中将sid写入Cookie, 用于免登, 防止用户重复登录.
  6. 浏览器跳转到回调页面, 该页面用于统一验证ticket, 可设计成空白页面.
    若不用回调页面, 则需要每个页面都有处理ticket的能力.
  7. 浏览器向子系统请求验证ticket.
  8. 子系统向SSO系统请求验证ticket.
  9. SSO系统验证完成后销毁ticket, 并为子系统生成sid.
    该sid与之前步骤5的sid不同, 原因之前已说明.
  10. 子系统缓存用户相关信息, 返回登录状态.
  11. 浏览器重新跳转到原url, 触发任意请求.
  12. 子系统验证Cookie中是否sid.
    若之前步骤都成功, 则此时Cookie一定带有sid.
  13. 子系统从本地缓存中获取用户信息.
    用户信息缓存时间不宜过长, 避免用户长时间不操作或不友好退出后, 占用缓存空间资源.
    若无缓存信息, 则向SSO系统获取.
  14. 子系统向SSO系统获取用户权限列表.
    此步骤也可做缓存处理, 同样缓存时间也不宜过长.
  15. SSO系统查询并返回用户权限列表.
  16. 子系统正常处理请求并返回处理结果.

3. 缓存内容

sid --n–1--> userid, loginTime, SubModuleID
userid --1–1--> userInfo, permissionList

4. 安全问题

  1. ticket与sid应使用uuid类型的字符串, 防止暴力破解
  2. 为了防止被拦截, ticket的存活时间极短, 一般设置为5秒左右.
  3. 同一用户在各个系统间获得的sid应该不同, 以防止某个子系统泄露sid而影响其他子系统.
  4. 缓存设置时间不宜过长, 一方面避免占用空间资源, 另一方面防止回话被劫持.可以用户触发接口后延期, 但到一定时间后必须销毁.
  5. 在修改用户重要信息或权限后, 自动登出.
  6. CSRF攻击
  7. XSS攻击
  8. 日志记录用户操作, 无论成功还是失败, 防御各种攻击.

5. 性能问题

  1. 缓存时间过不宜过短, 防止接口频繁调用, 缓存频繁写入.

6. 迭代开发

迭代开发BOSS系统, 在统一的系统页面可以管理所有子系统, 不用在不同的系统中跳转, 方便运维.

7. Resource