JWT【分布式鉴权方案】

基于Token机制鉴权架构

image.png

一、登录:
服务端校验密码,成功后返回access_token及refresh_token
客户端记录上述token
二、访问api
在访问api之前解析access_token,并查看是否过期,如果不过期则请求api
如果过期,则要先刷新令牌,再请求api
三、刷新token
携带有效期的refresh_token换回有效token
如果refresh_token过期,则需要用户重新登录
四、注销
请求注销api,服务器端和客户端应同时删除token的存储

参数规范

一、token在header中的传输规范

"Authorization":"token值"

二、uuid在header中的传输规范

"uuid":"uuid值"

三、防重放攻击传输规范:

uid={value}×tamp={value}&nonce={nonce}&sign={sign}

四、权限校验失败返回值
http status:401

{"code":"001","message":"无权访问"}"

各流程架构

  • 登录流程

image.png

逻辑说明
一、当用户需要登录时,客户端引导用户进行登录
二、登录发送用户名及密码至认证服务(passport)
三、认证服务验证用户名及密码,如果通过,通过jwt工具生成token

同时生成两种token:access_token和refresh_token
token的格式为:

{ 
uid:1 
username:"kingapex",
role:"seller"
}

access_token有效期为15分钟,refresh_token有效期为30分钟(以上时间应为可配置的常量)

四、将生成的token写入redis

分别 以ACCESSTOKEN*{uid}和REFRESHTOKEN*{uid} 为key存储
有效期为别为各token的有效期+60s

五、返回token

将token:access_token和refresh_token 、userid同时都返回,格式如下:

{
 uid:1,
 access_token:"xxxxx",
 refresh_token:"xxxxx"
}
  • 验权流程

image.png

1、客户端请求api

携带access_token信息
如果是生产环境不会直接携带access_token信息,详见这里

2、获取token

根据环境不同而有不同的获取token方式,参考这里

3、解析token

通过jwt工具将token解析

4、由redis中读取token

根据uid拼接key读取出access_token
如果不存在这个用户的token说明用户已经登出

5、验证token

判断此token是否属于此uid
判断token是否已经过期,如果过期,则进行刷新token流程

6、注入权限

如果token验证成功,根据user信息生成权限注入到spring安全上下文中

用户禁用架构

需求说明

当用户遭禁时,该用户应如果已经登录,也该立刻被禁止访问。
难点在于禁用操作无法操作已经登录的客户端

架构思路

如果将已禁用的用户标识在redis中,每次访问都要读取这个reids,但这个总体来讲是小概率事件,影响性能了。
比较好的办法是:在每个app示例中存储一份被禁用户名单,当禁用操作发生时,通知所有运行的示例。
这个思路采用redis订阅事件:


image.png

刷新token流程

image.png

逻辑说明

1、客户端请求api

携带refresh_token信息
如果是生产环境不会直接携带refresh_token信息,详见这里

2、获取token

根据环境不同而有不同的获取token方式,参考这里

3、解析token

通过jwt工具将token解析

4、由redis中读取token

根据uid拼接key读取出access_token
如果不存在这个用户的token说明用户已经登出

5、验证token

判断此token是否属于此uid
判断token是否已经过期,如果过期,则返回refresh_token过期错误,此时用户需要重新登录

6、刷新token

如果refresh_token 验证成功,则重新生成access_token和refresh_token
上述有效期以当前时间向后计算
替换此用户在redis中的token
并将token返回给客户端

你可能感兴趣的:(JWT【分布式鉴权方案】)