持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第1天,点击查看活动详情
前言
在java项目开发中,oauth2框架大家都再熟悉不过了,今天我们就来看一下,在oauth2中,token是如何生成的,以及token过期后,是如何刷新的。
一、oauth2认证方式
oauth2认证方式有四种:密码模式、授权码模式、客户端凭证模式、简单模式。这里就不一一介绍各个模式的认证流程了,总而言之,这四种模式都是通过用户授权认证以后,拿到认证的令牌,也就是token,才可以进行各种操作。
举个简单的例子:
小区中的门禁系统,出于安全考虑,小区门禁不可能让每个人都可以随意进出小区,这样小区的资源会有被盗的风险。那怎么解决呢?物业可以安装一个门禁刷卡系统,只给小区内的业主颁发门禁卡,这样不是小区的人就不能随意进入了,而只要拿到授权令牌(门禁卡),就可以进入小区。
上面的例子中,门禁系统就相当于oauth2认证系统,物业其实就是认证系统,用来认证用户是否有权进入小区。而门禁卡其实就是认证系统办法的认证token。具体认证流程见下图
二、认证结果返回
无论是哪种认证方式,认证成功后,都会将令牌返回,这里有几个参数:
几个重要的参数:
access_token:授权认证后的令牌
refresh_token: access_token失效后,刷新token的令牌
expires_in: token过期时间
三、刷新token
在以上认证完成后,有一个重要的环节,就是刷新token,我们不能每次请求数据都要重新授权获取新的token,这样浪费资源,也不合理。
OAuth 2.0 允许用户自动更新令牌。具体方法是,授权服务器发行令牌的时候,一次性发行两个令牌,一个用于获取数据,另一个用于获取新的令牌(refresh token 字段)。令牌到期前,用户使用 refresh token 发一个请求,去更新令牌。
具体的刷新token的实现流程
一般是用户通过账号和密码登陆系统,用户就可以正常操作了,但是登陆授权生成的token是有时效性的,如果token过期了就不能继续访问了,这时为了避免用户频繁的登陆授权,就采用了定期刷新token来保持用户处于登陆状态,这对于用户来说是无感的。
1、通过账号密码登陆后,会获取到token(授权令牌)、refresh_token(用于刷新token的令牌)、expire_time(令牌token的时效)这三个信息,将这三个连同登陆的时间点(login_time)保存下来以供后续刷新token使用。
2、在以后的操作过程中,每次请求接口时,都检查当前时间current_time与登陆时间login_time的时间差与时效expire_time的大小,如果current_time-login_time大于expire_time亦或者某个阀值,则就使用refresh_token去重新获取token,来更新本地存储的token以达到刷新的目的。
注意一点是,refresh_token的失效性要比token的时效性长很多,这样可以实现token的一直刷新了;但是如果用户长时间为操作,那么refresh_token也过期了,就会强制用户登出。
另外在刷新token时,还有一个方案,一般是使用轮询机制,定期请求刷新token,此方法实现起来稍微简洁些。