token就是一种身份验证方法,和cookie有相似作用;它被很多人翻译过来后生动的称为“令牌”,它的扩展性,安全性更高,非常适合用在Web应用和移动开发应用上。
token验证流程
使用token身份验证,服务器端就不会存储用户的登录记录。
客户端使用用户名跟密码请求登录;
服务端收到请求,去验证用户名与密码;验证成功后,服务端会签发一个 Token,
再把这个 Token 发送给客户端;
客户端收到 Token 以后可以把它存储起来,比如放在 Cookie 里或者 Local Storage 里;
客户端每次向服务端请求资源的时候需要带着服务端签发的 Token;
服务端收到请求,然后去验证客户端请求里面带着的 Token,如果验证成功,就向客户端返回请求的数据。
token 生成的方法有很多 我们一般常用Jwt来生成这个token
jwt的组成部分
标准的jwt令牌分为三部分,分别是Header、payload、signature;
第一部分:header
#一般固定如下 { 'typ': 'JWT', 'alg': 'HS256' } base64编码 ,并替换=号---> "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9"
第二部分: payload
{ 'id': user.id, 'username': user.username, ‘exp’: time.time() + 300, #过期时间 } base64编码-> "eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZvaG4gRGdWV9"
第一部分和第二部分, 可以被其他人使用base64解密,不建议存储敏感信息
第三部分: 前两部分的编码串通过 ‘.’ 连接,得到如下:
temp = "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZvaG4gRGdWV9"
然后使用第一部分 声明的算法HS256进行加密,得到如下:
import hmac h = hmac.new(b'key', temp.encode(), digestmod='SHA256') sign = base64.urlsafe_b64encode(h.digest())
最后三者拼接:1.2.3
代码演示
import base64
import hmac
import json
import time
import hmac
header = {"typ": 'JWT', 'alg': "HS256"}
# 将header字典 转为 json字符串
header_str = json.dumps(header)
# print("header_str:", header_str, type(header_str))
# 对header进行base64编码
header_encode = base64.urlsafe_b64encode(header_str.encode())
print("编码的结果:", header_encode)
# 替换= 为 空字符
header_p1 = header_encode.replace(b"=", b"")
payload = {"username": 'laufing', 'uid': 3, 'exp': time.time() + 300}
# 对payload进行base64编码
payload_p2 = base64.urlsafe_b64encode(json.dumps(payload).encode()).replace(b"=", b"")
# 获取第三部分
# 先拼接前两部分
temp = header_p1 + b"." + payload_p2
# hash 加密
temp_hash = hmac.new(b"123", temp, digestmod="SHA256")
print("加密的二进制结果:", temp_hash.digest())
print("加密的十六进制结果:", temp_hash.hexdigest())
# base64 编码
signature = base64.urlsafe_b64encode(temp_hash.digest()).replace(b"=", b"")
# 最后三者拼接
jwt_token = (header_p1 + b"." + payload_p2 + b"." + signature).decode()
print("jwt token:", jwt_token)