Skip to content

Commit 16b555d

Browse files
committed
feat:jwt介绍,python使用代码示例
1 parent 03f7fcb commit 16b555d

File tree

1 file changed

+215
-0
lines changed

1 file changed

+215
-0
lines changed

docs/python/web/jwt.md

Lines changed: 215 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,215 @@
1+
### **JWT(JSON Web Token)详解**
2+
3+
#### **1. 什么是 JWT?**
4+
5+
JWT(JSON Web Token)是一种用于 **身份验证(Authentication)****信息安全传输** 的开放标准(RFC 7519)。它通过 JSON 形式存储声明信息(claims),并使用 **数字签名** 保证数据完整性。
6+
7+
JWT 主要用于:
8+
9+
+ **用户身份验证**(如 OAuth 授权)
10+
+ **API 认证**(如 RESTful API 访问)
11+
+ **信息安全传输**(如在微服务间传递认证信息)
12+
13+
---
14+
15+
#### **2. JWT 的结构**
16+
17+
JWT 由 **三部分** 组成,每部分之间用 `.` 分隔:
18+
19+
```plain
20+
Header.Payload.Signature
21+
```
22+
23+
这三部分分别是:
24+
25+
+ **Header(头部)**:说明使用的算法和 token 类型
26+
+ **Payload(载荷)**:存储用户信息和声明(Claims)
27+
+ **Signature(签名)**:用于验证 JWT 的真实性
28+
29+
##### **示例 JWT**
30+
31+
```plain
32+
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1c2VyX2lkIjoxMjMsInJvbGUiOiJhZG1pbiIsImlhdCI6MTY5MTMwNjgwMCwiZXhwIjoxNjkxMzEwNDAwfQ.OjR1mI5fBItMdXsH2fF2p5Aj54PkbOSmCFEwC_Qw1tE
33+
```
34+
35+
**分解后:**
36+
37+
1. **Header(Base64编码)**
38+
39+
```json
40+
{
41+
"alg": "HS256",
42+
"typ": "JWT"
43+
}
44+
```
45+
46+
2. **Payload(Base64编码)**
47+
48+
```json
49+
{
50+
"user_id": 123,
51+
"role": "admin",
52+
"iat": 1691306800,
53+
"exp": 1691310400
54+
}
55+
```
56+
57+
3. **Signature(HMAC SHA256 计算)**
58+
59+
```python
60+
HMACSHA256(
61+
base64UrlEncode(header) + "." +
62+
base64UrlEncode(payload),
63+
secret
64+
)
65+
```
66+
67+
---
68+
69+
#### **3. JWT 如何工作?**
70+
71+
1. **用户登录**
72+
- 用户使用账号密码登录,服务器验证成功后生成 JWT 并返回给用户。
73+
2. **用户请求 API**
74+
- 之后,用户每次请求 API 时,都在 `Authorization` 头中携带 `Bearer <JWT>` 访问受保护资源。
75+
3. **服务器验证 JWT**
76+
- 服务器端使用 **签名密钥** 解析 JWT,验证合法性,并检查 `exp` 是否过期。
77+
78+
---
79+
80+
### **4. Python 实现 JWT**
81+
82+
Python 中可以使用 `PyJWT` 进行 JWT 生成和解析。
83+
84+
#### **4.1 安装 **`PyJWT`
85+
86+
```bash
87+
pip install PyJWT
88+
```
89+
90+
#### **4.2 生成 JWT**
91+
92+
```python
93+
import jwt
94+
import datetime
95+
96+
# 定义密钥(务必妥善保存)
97+
SECRET_KEY = "mysecretkey"
98+
99+
# 生成 Token
100+
def create_jwt(user_id: int, role: str):
101+
payload = {
102+
"user_id": user_id,
103+
"role": role,
104+
"iat": datetime.datetime.utcnow(),
105+
"exp": datetime.datetime.utcnow() + datetime.timedelta(hours=1) # 1小时后过期
106+
}
107+
108+
token = jwt.encode(payload, SECRET_KEY, algorithm="HS256")
109+
return token
110+
111+
# 示例
112+
token = create_jwt(123, "admin")
113+
print("JWT Token:", token)
114+
```
115+
116+
---
117+
118+
#### **4.3 解析 JWT**
119+
120+
```python
121+
def decode_jwt(token: str):
122+
try:
123+
decoded_payload = jwt.decode(token, SECRET_KEY, algorithms=["HS256"])
124+
return decoded_payload
125+
except jwt.ExpiredSignatureError:
126+
return "Token 已过期"
127+
except jwt.InvalidTokenError:
128+
return "无效 Token"
129+
130+
# 示例
131+
decoded_data = decode_jwt(token)
132+
print("解析后的数据:", decoded_data)
133+
```
134+
135+
---
136+
137+
### **5. JWT 进阶**
138+
139+
#### **5.1 使用 RSA 非对称加密**
140+
141+
在上面的示例中,我们使用了 `HS256`(对称加密),这意味着服务器端需要同一个密钥来生成和验证 JWT。
142+
143+
如果需要**更高的安全性**,可以使用 **RSA(非对称加密)**,客户端用公钥加密,服务器用私钥解密:
144+
145+
```python
146+
# 生成 RSA 私钥和公钥(仅需一次)
147+
from cryptography.hazmat.primitives.asymmetric import rsa
148+
from cryptography.hazmat.primitives import serialization
149+
150+
private_key = rsa.generate_private_key(
151+
public_exponent=65537,
152+
key_size=2048
153+
)
154+
public_key = private_key.public_key()
155+
156+
# 转换为可存储格式
157+
private_pem = private_key.private_bytes(
158+
encoding=serialization.Encoding.PEM,
159+
format=serialization.PrivateFormat.PKCS8,
160+
encryption_algorithm=serialization.NoEncryption()
161+
)
162+
163+
public_pem = public_key.public_bytes(
164+
encoding=serialization.Encoding.PEM,
165+
format=serialization.PublicFormat.SubjectPublicKeyInfo
166+
)
167+
168+
# 生成 RSA JWT
169+
def create_rsa_jwt(user_id: int):
170+
payload = {
171+
"user_id": user_id,
172+
"exp": datetime.datetime.utcnow() + datetime.timedelta(hours=1)
173+
}
174+
token = jwt.encode(payload, private_pem, algorithm="RS256")
175+
return token
176+
177+
# 解析 RSA JWT
178+
def decode_rsa_jwt(token: str):
179+
try:
180+
decoded = jwt.decode(token, public_pem, algorithms=["RS256"])
181+
return decoded
182+
except jwt.ExpiredSignatureError:
183+
return "Token 已过期"
184+
except jwt.InvalidTokenError:
185+
return "无效 Token"
186+
187+
# 测试
188+
rsa_token = create_rsa_jwt(123)
189+
print("RSA JWT Token:", rsa_token)
190+
print("解析 RSA JWT:", decode_rsa_jwt(rsa_token))
191+
```
192+
193+
---
194+
195+
### **6. JWT 安全性注意事项**
196+
197+
1. **不要存储敏感信息**
198+
JWT 可以被解码,因此不要在 `payload` 里存储密码或重要机密数据。
199+
2. **使用短生命周期**
200+
令牌应有一个较短的 `exp` 过期时间,并结合 **刷新 Token 机制** 避免滥用。
201+
3. **采用 HTTPS 传输**
202+
JWT 包含身份信息,必须使用 HTTPS 进行安全传输,防止中间人攻击。
203+
4. **尽量使用 **`RS256`** 非对称加密**
204+
使用 `RS256` 避免密钥泄露风险,公钥可安全公开,私钥则妥善存储。
205+
206+
---
207+
208+
### **7. 总结**
209+
210+
+ JWT 是一种安全、无状态的身份认证机制。
211+
+**Header、Payload、Signature** 三部分组成。
212+
+ **HS256** 适合对称加密,**RS256** 适合非对称加密。
213+
+ Python 可使用 `jwt` 库进行生成和解析。
214+
+ 需要注意 **安全性**,避免敏感数据泄露。
215+

0 commit comments

Comments
 (0)