写在前面
本文看下JWT相关内容。
1:为什么需要JWT
OAuth2.0规范中并没有规定access_token使用什么样的格式,只要求满足,不连续性,不可猜测性,不可重复性就可以了,所以我们在生成accest_token的时候就比较灵活了,比如使用uuid的方式来生成,当三方应用拿着令牌访问受保护资源服务器时,过程是这样子的:
此时受保护资源服务器本身无法判断令牌是否有效,所以需要通过灰色框中的令牌内检
过程来验证令牌,有没有一种方式能够避免令牌内检呢?如果我们能够在保证数据安全的同时,将需要校验的信息直接封装到令牌中,似乎就可以了。而JWT就提供了这种能力,其是一种数据格式的标准,设计的核心目的就是将数据通过结构化的方式进行存储,其包括如下的几个部分:
三部分通过.
进行分割,如下就是一个可能的jwt数据:
eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJYSUFPTUlOR1RFU1QiLCJhdWQiOiJBUFBJRF9SQUJCSVQiLCJpc3MiOiJodHRwOi8vbG9jYWxob3N0OjgwODEvIiwiZXhwIjoxNTg0MTA1NzkwNzAzLCJpYXQiOjE1ODQxMDU5NDgzNzJ9.SoJT62wYOMihpaH3Ttxf3WYwnC6qEyKbJ-bF7jMqxL8
可以通过在线网站https://jwt.io/
来看下其结构:
因为前2部分只是简单的base64编码,所以我们自然也能通过一般的base64工具 来查看:
使用了包含具体数据信息的jwt作为访问令牌之后,三方应用拿着令牌访问受保护资源服务器时,过程就变成这样子的:
可以看到令牌内检就不需要了。看到这里不知道你是否有这样的疑惑,如果是数据泄露了怎么办?如果是数据被篡改了怎么办?我们通过加密就可以解决泄露的风险(需要自己实现,非jwt职责范围)
,就算泄露了,因为解不了密所以也不用不了,通过signature就可以处理数据篡改的问题,一旦篡改,签名验证将会失败。
2:JWT的生命周期
一般jwt有如下几种生命周期:
1:从颁发到达到失效时间,自动过期失效
2:手动失效处理
3:使用刷新令牌生成新的令牌,老的令牌自动失效
3:程序测试
源码 。
生成令牌的过程参考授权协议OAuth 2.0之授权码和访问令牌 。
生成令牌之后我们通过链接http://localhost:8899/protectedresource/giveMeFengJieYanZhao?access_token=xxxx
就可以来模拟访问受保护资源服务器来获取受保护资源了:
写在后面
参考文章列表
授权协议OAuth 2.0之授权码和访问令牌 。
多知道一点
jwt结构还挺复杂的,难道我们要自己开发程序解析?
不用,jjwt 已经帮我们干了这个事了,我们一般使用它。
三方软件需要关心令牌是普通的无结构的随机字符串或者是jwt吗?
不用,只管用就行。
header,payload只是做了base64,如何避免数据泄露呢?
需要对jwt结果整体做加密,当然这已经超出了jwt的范畴了,jwt只是解决通过结构化的方式来表示数据的问题。但额外进行加密和解密也并不是特备麻烦的事情。
jwt,jws,jwe?
jwt是一种规范,jws,jwe都是jwt的实现,我们前面分析的其实就是jws,如下图:
jwt:json web token,一种规范
jws:json web signature,jwt的一种实现,目前使用最多的是这一种
jwe:json web encryption,jwt的一种实现,算法比较复杂,比较难,使用的不多