本文用于个人学习笔记,个人简书地址
Token 什么是token为什么要用token与传统的SESSION有什么区别token身份验证流程服务端中跟Token有关的问题 JWTJson Web Token 官网地址httpsjwtiojwt githubhttpsgithubcomjwtkjjwt什么是JWTJson Web TokenJWT长什么样子JWT的结构JWT签发与验证流程注意Token是服务端生成的一串字符串,以作客户端进行请求的一个令牌,服务端根据令牌获取客户端的身份信息。 举个栗子:
http://www.example.com/demo?token=15qwc87wq336scwWFSC2sc1w
互联网时代信息安全验证放在首要的地位,对于敏感的信息(如账号密码等等)明文的出现次数越少越好。
我们都知道,HTTP协议是一种无状态的协议,这就意味着当我们向应用服务端提供了用户名和密码进行用户认真后,下次请求还是要再进行用户认证,而且服务端又不知道发起请求是谁。按照这个思维,假如每个请求都带有敏感信息,即使进行加密,但是这就增加暴露频率,并且服务端频繁对每个请求的身份信息进行数据查询验证,这是个很大的开销,显然不是我们想要的结果。
为了我们登录后让服务端“记住”我,下次发出请求服务端识别哪个用户发送的,token令牌能解决http无状态的问题,这时候你会觉得SESSION不也一样吗?别急,下面会说到。token就像我们的身份证,客户端一旦得到服务端响应的token后本地缓存,之后每次请求带上token就行了,重要的是开发者可以在token上自定义信息(如UUID),并且是加密的,服务端就减少数据查询验证身份的开销了。
如果您还不了解session,请先自行百度学习,这里我简单介绍下:
session 是一种HTTP存储机制,目的是为无状态的HTTP提供的持久机制。
Session一般只提供一种简单的认证ID,即JSESSIONID,用户数据只保存在服务端上,因此JSESSIONID尤为重要需要严格保密,这导致了session的弊端:如果web服务器做了负载均衡,那么下一个操作请求到了另一台服务器的时候session会丢失。Session:用户数据保存在服务端;Token:客户端的 cookie 或本地介质存储。Session 更加适合在浏览器上应用,对于开发API接口 Token 是不错的选择。一旦服务器挂了 sessionid 在服务端内存中映射信息丢失了, token 具有自带性,状态还存在。Token 安全性好,有签名能防止信息篡改、监听、重放攻击。Token 能进行授权操作,Session 不可以。Token 不再依赖于 Cookie,所以你就不需要考虑对 CSRF(跨站请求伪造)的防范。HMACSHA256 计算的 Token 验证和解析的费时比数据库查询 Session 多。Json web token (JWT), 是为了在网络应用环境间传递声明而执行的一种基于JSON的开放标准。该token被设计为紧凑且安全的,特别适用于分布式站点的单点登录(SSO)场景。JWT的声明一般被用来在身份提供者和服务提供者间传递被认证的用户身份信息,以便于从资源服务器获取资源,也可以增加一些额外的其它业务逻辑所必须的声明信息,该token也可直接被用于认证,也可被加密。也就是说JWT是Token的一种表述性声明规范。
如果你不清楚JSON请自行学习
eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiI3OHNhd2RmZjUiLCJzdWIiOiJ4aWFvdGlhbnRpYW4iLCJpYXQiOjE0OTgwMzE0NDIsImlzcyI6IjEyMi4xMTQuMjE0LjE0NyIsImV4cCI6MTQ5ODAzMjY0Mn0.0h_kDhyZLhnt8TRgbLsOnVT8eOUAqgFTEZP-XgIGuA
上面字符串都是用Base64编码后,发现结构类似:xxx.yyy.zzz
JWT包含了三个部分,分别用.分割开来,分别是:
Header 头部Payload 负载Signature 签名 // 1.Header,包含JWT基础声明,加密算法与类别 { "alg": "HS256", // 加密算法 "typ": "JWT" // 类别 } // 2.Payload,存放有效信息的地方 // 包含 Claim ,它可以一些实体(通常指的用户)的状态和额外的元数据,有三种类型 // 2.1.Reserved claims JWT标准里面定好的claim,内容如下: // 2.2.Public claims // 2.3.Private claims // 建议的 Claims 不是强制使用的,完全可以按照自己的需求自定义playload,如果是自定义的claims名,您使用的实现库是不会主动去验证它们的 { "aud": "uuu", // 接受者 "iss": "xxx", // 签发者 "exp": "1498499261660", // 过期时间 "sub": "yyy", // 主题 "iat": "1498459261660", // 签发时间 "jti": "", // JWT的唯一身份标示 "nbf": "1498459261660", // 定义在什么时间之前,该jwt都是不可用的 ... } // 3.Signature,签名,根据Header定义的算法和私钥组合加密 HMACSHA256( base64UrlEncode(header) + "." + base64UrlEncode(payload), secret)PS: * 推荐个 在线签名工具 用于调试 * 超赞强大的API调试工具 Postman,在谷歌浏览器插件就搜索得到,不过需要翻墙,这个百度好多种方法