flask項目--認證方案Json Web Token(JWT)


網上大多數介紹JWT的文章實際介紹的都是JWS(JSON Web Signature),也往往導致了人們對於JWT的誤解,但是JWT並不等於JWS,JWS只是JWT的一種實現,除了JWS外,JWE(JSON Web Encryption)也是JWT的一種實現。

JWS

  • 頭部(Header)
    頭部用於描述關於該JWT的最基本的信息
    例如:其類型、以及簽名所用的算法等。
    JSON內容要經Base64 編碼生成字符串成為Header。

  • 載荷(PayLoad)
    payload的五個字段都是由JWT的標准所定義的。
    iss: 該JWT的簽發者
    sub: 該JWT所面向的用戶
    aud: 接收該JWT的一方
    exp(expires): 什么時候過期,這里是一個Unix時間戳
    iat(issued at): 在什么時候簽發的
    后面的信息可以按需補充。 JSON內容要經Base64 編碼生成字符串成為PayLoad。

  • 簽名(signature)
    這個部分header與payload通過header中聲明的加密方式,使用密鑰secret進行加密,生成簽名。
    JWS的主要目的是保證了數據在傳輸過程中不被修改,驗證數據的完整性。
    但由於僅采用Base64對消息內容編碼,因此不保證數據的不可泄露性。所以不適合用於傳輸敏感數據。

JWE

相對於JWS,JWE則同時保證了安全性與數據完整性。 JWE由五部分組成:

JWE的計算過程相對繁瑣,不夠輕量級,因此適合與數據傳輸而非token認證,但該協議也足夠安全可靠,用簡短字符串描述了傳輸內容,兼顧數據的安全性與完整性

  • JWE組成
    具體生成步驟為:
    JOSE含義與JWS頭部相同。
    生成一個隨機的Content Encryption Key (CEK)。
    使用RSAES-OAEP 加密算法,用公鑰加密CEK,生成JWE Encrypted Key。
    生成JWE初始化向量。
    使用AES GCM加密算法對明文部分進行加密生成密文Ciphertext,算法會隨之生成一個128位的認證標記Authentication Tag。 6.對五個部分分別進行base64編碼。

1. jwt

  • VS狀態保持機制
    1.APP不支持狀態保持
    2.狀態保持有同源策略, 默認無法跨服務器傳遞(nginx可以處理)

  • JWT不會對數據進行加密, 所以數據中不要存放有閱讀價值的數據

  • 不可逆加密

    • md5 sha1 sha256
    • 主要用於數據認證, 防止數據被修改

消息摘要 MD

  • 哈希算法:
    將任意長度內容轉為定長內容, 且相同內容的哈希值始終相同, 不同內容的哈希值不同(極小概率出現碰撞)
    由於其唯一性, 一般將數據的哈希值稱為數據的摘要信息, 稱為數據的"指紋", 用於檢測數據是否被修改
  • 代表算法 sha1 sha256 md5
  • 缺點:哈希算法是公開的, 如果可以獲取到明文, 就可以窮舉出使用的算法

消息認證 MA ( JWT一般會采用消息認證機制)

哈希算法基礎上混入秘鑰, 防止哈希算法被破解, 避免簽名被偽造

  • 代表算法 hmacsha256

2. PyJWT (重點)

  • 安裝 pip install PyJWT
import jwt
from jwt import PyJWTError
from datetime import datetime, timedelta


payload = {  # jwt設置過期時間的本質 就是在payload中 設置exp字段, 值要求為格林尼治時間
    "user_id": 1,
    'exp': datetime.utcnow() + timedelta(seconds=30)
}

screct_key = "test"
# 生成token
token = jwt.encode(payload, key=screct_key, algorithm='HS256')
print(token)
# 驗簽token  返回payload    pyjwt會自動校驗過期時間
try:
    data = jwt.decode(token, key=screct_key, algorithms='HS256')
    print(data)
except PyJWTError as e:
    print("jwt驗證失敗: %s" % e)

3. 數字簽名 (拓展)

  • 消息認證存在缺點
    • 之前沒有對服務器返回的數據進行驗簽, 無法確認數據是否被修改(服務器身份是否合法)
    • 將秘鑰交給客戶端, 客戶端才可以驗簽服務器返回的數據是否被修改
    • 但是客戶端安全性較差, 一旦秘鑰泄露, 仍然可以偽造簽名
  • 利用非對稱加密對摘要信息進行加密, 避免摘要信息被偽造
  • 非對稱加密采用秘鑰對
    • 公鑰和私鑰
    • 公鑰加密, 私鑰解密
    • 私鑰加密, 公鑰解密
    • 私鑰可以推出公鑰, 公鑰無法推出私鑰
  • 發送者使用私鑰對數據摘要加密(簽名), 接收者使用對應的公鑰解密, 然后對數據進行哈希處理, 比對摘要信息是否一致(驗簽)
  • 代表算法 RSA
  • 使用場景
    • 安全級別要求比較高的系統, 如銀行等
  • 優點
    • 客戶端不會像消息認證一樣保存秘鑰, 而是保存了非對稱加密的公鑰, 即使客戶端被破解, 公鑰被獲取, 也無法通過公鑰生成合法的簽名
  • 缺點
    • 效率低

  • 使用openssl 生成RSA秘鑰對
# 生成私鑰,指定私鑰的長度為2048bit   1024基本安全, 2048非常安全
openssl genrsa -out rsa_private_key.pem 2048
# 根據私鑰生成對應的公鑰
openssl rsa -in rsa_private_key.pem -pubout -out rsa_public_key_2048.pub
# 私鑰轉化成pkcs8格式, 非必須,pkcs8格式解析起來更方便
openssl pkcs8 -topk8 -inform PEM -in rsa_private_key.pem -outform PEM -nocrypt > rsa_private_key_pkcs8.pem
  • 安裝RSA類庫pip install cryptography


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM