详解JWT与Token的应用与原理
什么是JWT
JWT(JSON Web Token)是一种用于网络通信的协议,主要用来在网络应用之间传递认证及授权数据。JWT 将用户信息进行编码,形成一个字符串并将其发送到客户端,在客户端需要访问受保护的资源时,将其发送回服务器进行验证。JWT 是有状态的,因为其中包含了用户的信息,而服务器在解析 Token 时,会将其中的信息还原。
JWT 主要由三部分组成:Header、Payload 和 Signature。其中 Header 和 Payload 都是 JSON 格式的数据。Header 主要用来描述 JWT 的元数据信息,例如使用的加密算法等;Payload 则是我们传递的信息部分,例如用户的ID、角色和访问权限等。Signature 是对 Header 和 Payload 的签名,用来防止信息被篡改。
为什么需要 JWT
在传统的 Web 应用中,服务器在用户登录后,会将用户信息保存在 Session 中,并返回 Session ID 给客户端,在后续的请求中客户端需要将这个 Session ID 放在请求头上,以便服务器识别当前用户的身份。
这种方式会遇到一些问题,例如:
- Session 需要服务器进行存储,增加了服务器的负担;
- Session 是有状态的,需要多台服务器共享存储,增加了集群的复杂度;
- Session 无法跨域,使用 JWT 可以解决跨域的问题。
而使用 JWT 的方式,我们只需要在服务器端进行签名即可,不需要进行存储。同时,JWT 本身包含了用户的信息,因此可以避免对 Session 的依赖。并且由于 JWT 存储于客户端,因此可以跨域使用。
如何使用 JWT
生成 JWT
在生成 JWT 时,需要将 Header 和 Payload 部分进行编码,并进行签名。例如:
// Header
{
"alg": "HS256", // 签名算法
"typ": "JWT" // token类型
}
// Payload
{
"sub": "1234567890", // token的所有用户的唯一标识
"name": "John Doe", // 用户名称
"iat": 1516239022 // token的颁发时间
}
// Signature
HMACSHA256(
base64UrlEncode(header) + "." +
base64UrlEncode(payload),
secret)
其中,Header 和 Payload 都是 JSON 格式的数据,并分别进行了 base64 编码。Signature 由 Header 和 Payload 进行签名得到。
验证 JWT
在服务端验证 JWT 时,主要是对 Signature 进行验证。首先服务器需要获取到 Header 和 Payload 部分,并根据 Header 部分指定的算法进行签名,然后验证得到的 Signature 是否一致。
示例1
假设我们的服务器需要对用户进行认证,用户在登录时需要提供用户名和密码,并返回 JWT。后续用户访问受保护的资源时,需要在请求头上携带 JWT。
curl -X POST http://localhost:3000/login \
-H 'Content-Type:application/json' \
-d '{"username": "admin", "password": "123456"}'
{
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6I..."
}
此时客户端可以将 JWT 存储在 localStorage 或 Cookie 中,并在后续请求中将其添加到请求头中。
curl -X GET http://localhost:3000/protected \
-H 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6I...'
服务端在验证 JWT 时,可以通过解析 Header 和 Payload 进行验证,并根据用户 ID 查找用户信息,如果验证成功则返回数据。
示例2
假设我们需要开发一个 API,其中部分 API 需要进行权限验证。使用 JWT 可以实现类似的功能。
在用户登录时,服务器会返回 JWT,并在其中包含用户的信息和访问权限。
curl -X POST http://localhost:3000/login \
-H 'Content-Type:application/json' \
-d '{"username": "admin", "password": "123456"}'
{
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6I...",
"user_id": 1234567890,
"role": "admin",
"permissions": ["read", "write"]
}
当用户进行受保护的 API 访问时,需要在请求头上添加 JWT,服务器在验证 JWT 后,可以根据其中包含的用户信息和访问权限判断是否有权限进行访问。
curl -X GET http://localhost:3000/api/v1/users \
-H 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6I...'
以上两个示例是 JWT 在实际开发中的两种应用场景,可以根据需要灵活地处理。
本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:详解JWT与Token的应用与原理 - Python技术站