zoukankan      html  css  js  c++  java
  • JWT简介

    代码里面, 客户端和服务端之间的交互, 用了jwt,  从代码里面看到, 服务端对客户端之间的各种 加密验证签名等(不一一介绍了) , 最后还生成了jwt , 关于jwt, 在网上找到了一篇很好的博客, 基本概念写的很详细, 大家可以点击链接进去看

    https://blog.csdn.net/weixin_42139757/article/details/80689234     作者:GhostSugar 

    以下内容是我从这篇博客里面复制过来的.


    1.背景介绍

    什么是JWT

    JWT(JSON WEB TOKEN):JSON网络令牌,JWT是一个轻便的安全跨平台传输格式,定义了一个紧凑的自包含的方式在不同实体之间安全传输信息(JSON格式)。它是在Web环境下两个实体之间传输数据的一项标准。实际上传输的就是一个字符串。广义上讲JWT是一个标准的名称;狭义上JWT指的就是用来传递的那个token字符串

    JWT用来做什么?怎么来的?

    由于http协议是无状态的,所以客户端每次访问都是新的请求。这样每次请求都需要验证身份,传统方式是用session+cookie来记录/传输用户信息,而JWT就是更安全方便的方式。它的特点就是简洁,紧凑和自包含,而且不占空间,传输速度快,而且有利于多端分离,接口的交互等等
    JWT是一种Token规范,主要面向的还是登录、验证和授权方向,当然也可以用只来传递信息。一般都是存在header里,也可以存在cookie里。
    • 紧凑: 意味着这个字符串很小,甚至可以通过URL参数,POSTparameter中以Http Header的方式传输。

    • 自包含:传输的字符串包含很多信息,别人拿到以后就不需要再多次访问数据库获取信息,而且通过其中的信息就可以知道加密类型和方式,当然解密需要公钥和密钥。

    应用场景:认证和授权,认证解决[你是谁]的问题,授权解决了[你能做什么]的问题 一次性验证,邮件验证
    注册激活
    登录验证,长期未登录激活
    应用授权
    单点登录

    什么是TOKEN
    Token是服务器签发的一串加密字符串,是为了给客户端重复访问的一个令牌,作用是为了证明请求者(客户端)的身份,保持用户长期保持登录状态。

    JWT和TOKEN的关系
    JWT就是TOKEN的一种载体,或者说JWT是一种标准,而Token是一个概念,而JWT就是这个概念执行的一种规范,通俗点说token就是一串字符串,jwt就是加上类型,信息等数据再加密包装一下成为一个新的token。
    最直观的区别就是不使用JWT的token需要查询数据库来验证,而使用JWT可以不用对数据库进行操作,因为它本身包含了可自定义的信息

    JWT是所有语言通用的
    其实sessionID储存也算是一种token

    • JWT是所有语言通用的
    • 其实sessionID储存也算是一种token

    2.知识剖析

    JWT的数据结构以及签发的过程
    JWT由三部分构成:header(头部)、payload(载荷)和signature(签名)。

    Header 头部信息:指定类型和算法
    Payload 荷载信息:存放Claims声明信息
    Signature 签名:把前两者对应的Json结构进行base64url编码之后的字符串拼接起来和密钥放一起加密后的签名
    组成方式为 header.payload.signature
    eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.
    eyJpc3MiOiLlvKDlvLoiLCJuYW1lIjoiNzg5IiwiZXhwIjoxNTI4MzY0MjU5LCJpYXQiOjE1MjgzNjMwNTl9.574koY-c9SqMNNzfvAWQuKEnimWeZAcoFQ5XudNWF3o

    Header的结构
    * type 声明类型
    * algorithm 声明加密算法
    格式: {“typ”: “JWT”,“alg”: “HS256”}

    payload的结构
    * 声明信息
    payload用来承载要传递的数据,它的json结构实际上是对JWT要传递的数据的声明,这些声明被JWT标准称为claims(声明),它的每个属性键值对其实就是一个claim,JWT常用的有两种声明,一种是Reserved claims(保留声明),也就是JWT规定的标准声明。
    一种是Private claims(自定义声明),我们在这里定义要传递的信息
    还有一种是public claims(公共声明),这个目前没用到。

    格式: {"name": "value","id": "value2"}
    1
    标准声明(JWT保留声明)
    •iss(Issuser):代表这个JWT的签发主体;
    •sub(Subject):代表这个JWT的主体,即它的所有人;
    •aud(Audience):代表这个JWT的接收对象;
    •exp(Expiration time):是一个时间戳,代表这个JWT的过期时间;
    •nbf(Not Before):是一个时间戳,代表这个JWT生效的开始时间,意味着在这个时间之前验证JWT是会失败的;
    •iat(Issued at):是一个时间戳,代表这个JWT的签发时间;
    •jti(JWT ID):是JWT的唯一标识。

    signature
    * 签名
    把header和payload对应的json结构进行base64url编码之后得到的字符串用点号拼接起来,然后根据header里面alg指定的签名算法生成出来的,然后添加自己设定的key进行加密签名
    添加:
    .sign(Algorithm.HMAC256(Key))
    在线加密解密:http://tool.oschina.net/encrypt?type=3

    工具
    auth0     OAuth2.0     JWTUtil     jsonwebtoken

    3.常见问题

    如何验证

    当接收方接收到一个JWT的时候,首先要对这个JWT的完整性进行验证,这个就是签名认证。它验证的方法其实很简单,只要把header使用base64url解码以后就知道签发者用什么算法做的签名,然后用这个算法对header和payload加密一下,再比较这个签名是否和JWT本身包含的signature是否完全相同,只要不同就可以认为这个JWT是被篡改过的。所以接收方生成签名的时候必须使用跟JWT发送方相同的密钥。
    再次就是验证payload里的部分,比如是否过期,还有自定义的信息是否相同,加上已经前面验证的signature,这样就保证了这个签名的有效性

    互斥登录/修改密码后登录的问题
    场景:用户在多个设备或者其它浏览器/IP登录以后或者修改密码以后,那其它的设备就需要自动退出登录

    用户修改密码之后签发一个新的token来覆盖之前的。但是之前的token只要在失效之前仍然是可以验证并且登录的
    用户手动退出的时候也是需要token失效的,这就需要退出的时候直接清除或者覆盖客户端保存的token。同上,之前的token仍然有效,所以token的时间不能太长
    设置黑名单,在签发新token的时候把之前未过期的token加入黑名单使之失效。但是这样就需要储存token,而jwt的优点就是不需要储存空间。

    续签
    场景:需要用户长期登录的应用,比如用你开发需要用户保持登录的应用,在使用token的时候保证用户体验不需要频繁登录操作,又要保证用户在一段时间之后登录过期重新登录,主要是一个用户体验和用户信息安全的问题。这个时候又要求token不能过长,只能通过续签来保持登录状态
    又或者说用户登录的时候你需要获取用户在社交网站的信息,就需要获取社交网站授权的token,这也需要续签,不过这是向社交网站续签。这里后面说。

    何时续签:
    1.每次请求刷新 每次请求直接覆盖签发新的token
    2.记录时间定时刷新 设置一个定时器,记录签发时间,然后到过期的时候签发新的
    3.临期时刷新 访问的时候对比时间,如果即将过期就立即刷新。
    4.过期后续签,这样设置过期时间的意义就在于如果token被盗取后黑客登录也需要续签,这样用户再次登录客户端就会发现用户登录异常。而且每次获取的token都是新的,旧的只能获取一次续签的机会,也就说如果用户续签以后之前的token就不能再续签了。
    5.jwt-autorefresh(JWT自动刷新)(有限制条件,在客户端定时刷新)

    4.~~~~~~

    5~~~~~~~

    6.参考文献
    JWT实现token-based会话管理 : https://www.cnblogs.com/lyzg/p/6028341.html
    RFC 7519 : https://tools.ietf.org/html/rfc7519
    RFC : https://baike.baidu.com/item/RFC/1840?fr=aladdin
    auth0:https://auth0.com/docs/tokens/refresh-token/current
    oauth2 : https://oauth.net/2/

    7.更多讨论

    A:JWT有什么不好的地方?
    Q:不好的地方就是JWT等于说是泼出去的水,发出去的令牌,不可更改,只要有效期内就可以永使用
    A: JWT安全性如何?
    Q: 这也是JWT最重要的一点,它的出现就是为了免登陆或者权限控制,所以它的安全性至关重要。所以它虽然是一直加密的,但是安全性总是建立在相对性之上的。所以只能说一定程度上是安全的。
    A: JWT如何存放?
    Q: JWT不需要存放,或者说存放在客户端那里。服务端只需要有解密算法就可以判断当前的JWT是不是有效的。

  • 相关阅读:
    PHP获取一周的日期
    关系型数据库和非关系型数据库的区别和特点
    关系型数据库和非关系型数据库的特性以及各自的优缺点
    什么是数据库?什么是关系数据库?什么是非关系型数据库?
    PHP中把对象转数组的几个方法
    验证银行卡号
    xss过滤方法
    PHP 随机字符
    计算两个日期相差年月日
    判断一个时间段是否包含周末
  • 原文地址:https://www.cnblogs.com/PinkPink/p/9962650.html
Copyright © 2011-2022 走看看