ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

JWT伪造详解

2022-07-01 00:35:22  阅读:151  来源: 互联网

标签:加密 jwt base64 JWT 用户 信息 详解 伪造


一、JWT简介

1、简介

JSON Web Token(JSON Web令牌)是一个开放标准(rfc7519),它定义了一种紧凑的、自包含的方式,用于在各方之间以JSON对象安全地传输信息。通过JSON形式作为Web应用中的令牌,用于在各方之间安全地将信息作为JSON对象传输。在数据传输过程中还可以完成数据加密、签名等相关处理。

2、作用

1)授权:一旦用户登录,每个后续请求将包括JWT,从而允许用户访问该令牌允许的路由、服务和资源。它的开销很小并且可以在不同的域中使用。如:单点登录。

2)信息交换:在各方之间安全地传输信息。JWT可进行签名(如使用公钥/私钥对),因此可确保发件人。由于签名是使用标头和有效负载计算的,因此还可验证内容是否被篡改。

二、传统session

1、认证方式

http协议本身是一种无状态的协议,即使用户向服务器提供了用户名和密码来进行用户认证,在下次请求时用户也得再一次进行用户认证。因为根据http协议,服务器并不能知道接收到的请求来自哪个用户,所以为了让应用能识别是哪个用户发出的请求,只能在服务器存储─份用户登录的信息,这份登录信息会在响应时传递给浏览器,告诉其保存为cookie以便下次请求时发送给应用。这样应用就能识别请求来自哪个用户。

2、存在的问题

1)用户经改应用认证后,应用都要在服务端存储一份session。而session一般都是保存在内存中,随着认证用户的增多,服务端的开销会明显增大。而且用户下次的请求还必须发送到这台服务器上,这样才能拿到授权的资源。在分布式应用上会限制负载均衡器的能力

2)session是基于cookie来进行用户识别,cookie如果被截获,用户很容易受到CSRF(跨站伪造请求攻击)攻击

三、JWT认证

1、认证流程

1)前端通过Web表单将自己的用户名和密码发送到后端的接口。该过程一般是HTTP的POST请求。建议的方式是通过SSL加密的传输(https协议),从而避免敏感信息被嗅探。
2)后端核对用户名和密码成功后,将用户的id等其他信息作为JWT Payload(负载),将其与头部分别进行Base64编码拼接后签名,形成一个JWT(Token)。
3)后端将JWT字符串作为登录成功的返回结果返回给前端。前端可以将返回的结果保存在localStorage(浏览器本地缓存)或sessionStorage(session缓存)上,退出登录时前端删除保存的JWT即可。
4)前端在每次请求时将JWT放入HTTP的Header中的Authorization位。(解决XSS和XSRF问题)
后端检查是否存在,如存在验证JWT的有效性。例如,检查签名是否正确﹔检查Token是否过期;检查Token的接收方是否是自己(可选)
5)验证通过后后端使用JWT中包含的用户信息进行其他逻辑操作,返回相应结果

四、JWT结构

JWT是一个stringt字符串,由三部分组成,中间用 .  隔开。举个栗子:

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9.TJVA95OrM7E2cBab30RMHrHDcEfxjoYZgeFONFh7HgQ

第一部分是头部(Header),第二部分是有效载荷(Payload),第三部分是签名(Signature)。

1、头部(Header)

头部包含两部分信息:

  • 声明类型
  • 声明加密的算法。通常直接使用HMAC、SHA256、RSA。
{
  'typ': 'JWT',
  'alg': 'HS256'
}

然后将头部进行base64加密,构成第一部分。

eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9

 注意

可以将JWT中的alg算法修改为none:

JWT支持将算法设定为“None”。如果“alg”字段设为“ None”,那么JWT的第三部分会被置空,这样任何token都是有效的。这样就可以伪造token进行随意访问。

2、有效载荷(Payload)

包含3部分信息:

1)标准中注册的声明(建议但不强制使用)

  • iss: jwt签发者
  • sub: jwt所面向的用户
  • aud: 接收jwt的一方
  • exp: jwt的过期时间,这个过期时间必须要大于签发时间
  • nbf: 定义在什么时间之前,该jwt都是不可用的.
  • iat: jwt的签发时间
  • jti: jwt的唯一身份标识,主要用来作为一次性token,从而回避重放攻击。

2、公共的声明

公共的声明可以添加任何的信息,一般添加用户的相关信息其他业务需要的必要信息。但不建议添加敏感信息,因为该部分在客户端可解密。

3、私有的声明

私有声明是提供者和消费者所共同定义的声明,一般不建议存放敏感信息,因为base64是对称解密的,意味着该部分信息可以归类为明文信息。

定义一个payload:

{
  "sub": "1234567890",
  "iss": "http://localhost:8000/auth/login",
  "iat": 1451888119,
  "exp": 1454516119,
  "nbf": 1451888119,
  "name": "John Doe",
  "admin": true
}

然后将其进行base64加密,得到Jwt的第二部分。

eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9

3、签证(Signature)

包含以下三个部分:

  • base64加密后的header
  • base64加密后payload
  • 密钥secret

这个部分需要base64加密后的header和base64加密后的payload使用.连接组成的字符串,然后通过header中声明的加密方式进行加盐secret组合加密,然后就构成了jwt的第三部分。

// javascript
var encodedString = base64UrlEncode(header) + '.' + base64UrlEncode(payload);

var signature = HMACSHA256(encodedString, 'secret'); // TJVA95OrM7E2cBab30RMHrHDcEfxjoYZgeFONFh7HgQ

注意:

secret是保存在服务器端的,jwt的签发生成也是在服务器端的,secret就是用来进行jwt的签发和jwt的验证,所以,它就是你服务端的私钥,在任何场景都不应该流露出去。一旦客户端得知这个secret,那就意味着客户端是可以自我签发jwt了。

 

Reference

https://blog.csdn.net/qq_45521281/article/details/106073624

https://blog.csdn.net/Top_L398/article/details/109361680

                                   

标签:加密,jwt,base64,JWT,用户,信息,详解,伪造
来源: https://www.cnblogs.com/kinyoobi/p/16379076.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有