jwt --- JSON Web Tokens

การนำ JSON Web Token (JWT) มาตรฐานขนาดเล็กสำหรับ MicroPython JWT คือคอนเทนเนอร์ JSON ที่กะทัดรัด ปลอดภัยสำหรับ URL ซึ่งผู้ออกลงนามเพื่อให้ผู้ตรวจสอบสามารถตรวจจับการแก้ไขและการหมดอายุได้

พอร์ต MicroPython นี้มีขนาดเล็กโดยตั้งใจ:

  • รองรับเฉพาะ HS256 (HMAC กับ SHA-256) อัลกอริทึม RSA / ECDSA / EdDSA ไม่ได้นำมาใช้งาน ผู้ออกและผู้ตรวจสอบต้องใช้คีย์ลับแบบสมมาตรร่วมกัน

  • claim exp (การหมดอายุ) ที่เป็นตัวเลือกจะได้รับการยอมรับ claim ที่ลงทะเบียนอื่นๆ (nbf, iat, iss, aud, sub, jti) จะถูกส่งผ่านโดยไม่เปลี่ยนแปลงใน payload แต่ ไม่ได้รับการตรวจสอบ แอปพลิเคชันจะตรวจสอบหากต้องการ

  • ไม่มีการจัดการ key-rotation, JWKS หรือ audience-list

ฟังก์ชัน

jwt.encode(payload: dict, key: bytes | str, algorithm: str = 'HS256') str

เข้ารหัส payload เป็น JWT ที่ลงนามแล้วและส่งคืน compact serialization ผลลัพธ์ (str ในรูปแบบ "header.payload.signature" โดยแต่ละส่วนเข้ารหัส Base64-URL)

payload

dict ของ claims ที่ serialize ได้เป็น JSON claim มาตรฐาน (exp, iat, sub, ...) จะถูกส่งผ่านตามที่เป็น คีย์แอปพลิเคชันที่กำหนดเองได้รับอนุญาต

key

HMAC secret ที่ใช้ร่วมกัน bytes เป็นที่ต้องการ str จะถูกเข้ารหัส UTF-8 โดยอัตโนมัติ

algorithm

ต้องเป็น "HS256" (ค่าเริ่มต้น) สิ่งอื่นใดจะยกข้อยกเว้น exceptions.InvalidAlgorithmError

jwt.decode(token: str, key: bytes | str, algorithms: list = ['HS256']) dict

ตรวจสอบลายเซ็นของ token และ (หากมี) claim exp แล้วส่งคืน payload dict ที่ถอดรหัสแล้ว ยกคลาสย่อยของ exceptions.PyJWTError เมื่อเกิดความล้มเหลวใดๆ ผู้เรียกมักจะดักจับคลาสฐาน

token

สตริง JWT แบบ compact ที่สร้างโดย encode() (หรือผู้ออกที่เข้ากันได้)

key

HMAC secret ที่ใช้ร่วมกัน ต้องตรงกับคีย์ที่ใช้ตอนเข้ารหัส

algorithms

รายการอัลกอริทึมที่ผู้เรียกยินดีรับ HS256 ต้องมีอยู่ และ alg ในส่วนหัวของ token ต้องอยู่ในรายการ ค่าเริ่มต้นคือ ["HS256"]

ยกข้อยกเว้น:

  • exceptions.InvalidAlgorithmError -- HS256 ไม่อยู่ใน algorithms หรือ alg ในส่วนหัวของ token เป็นอะไรอื่นที่ไม่ใช่ HS256

  • exceptions.InvalidTokenError -- token มีรูปแบบไม่ถูกต้อง (ไม่แบ่งออกเป็นสาม Base64-URL segment หรือ segment ไม่สามารถถอดรหัส / แยกวิเคราะห์เป็น JSON ได้)

  • exceptions.InvalidSignatureError -- ลายเซ็นไม่ตรงกับ HMAC ที่คำนวณใหม่จากส่วนหัวและ payload

  • exceptions.ExpiredSignatureError -- payload มี claim exp ที่มีค่าน้อยกว่าเวลา Unix ปัจจุบัน นาฬิกาของกล้องต้องตั้งค่าให้ถูกต้องสำหรับการตรวจสอบนี้จึงจะมีความหมาย ดู ntptime.settime()

ข้อยกเว้น

ข้อยกเว้นทั้งหมดอยู่ภายใต้แอตทริบิวต์โมดูล jwt.exceptions

exception exceptions.PyJWTError

คลาสฐานสำหรับความล้มเหลว JWT ทุกประเภท ดักจับคลาสนี้หากไม่จำเป็นต้องแยกแยะระหว่างกรณีด้านล่าง

exception exceptions.InvalidTokenError

token มีโครงสร้างไม่ถูกต้อง จำนวน segment ผิด segment ที่ถอดรหัส Base64 ไม่ได้ หรือ JSON ที่แยกวิเคราะห์ไม่ได้ เป็นคลาสย่อยของ exceptions.PyJWTError

exception exceptions.InvalidAlgorithmError

อัลกอริทึมของ token ไม่อยู่ในรายการที่ผู้เรียกยอมรับ หรือผู้เรียกขออัลกอริทึมอื่นที่ไม่ใช่ HS256 เป็นคลาสย่อยของ exceptions.PyJWTError

exception exceptions.InvalidSignatureError

ลายเซ็นของ token ไม่ตรงกับ HMAC ที่คำนวณจากส่วนหัวและ payload โดยใช้คีย์ที่ให้มา เป็นคลาสย่อยของ exceptions.PyJWTError

exception exceptions.ExpiredSignatureError

claim exp ของ token อยู่ในอดีต เป็นคลาสย่อยของ exceptions.PyJWTError เวลานาฬิกาของกล้องต้องตั้งค่า (ผ่าน ntptime.settime()) สำหรับการตรวจสอบนี้จึงจะมีความหมาย

ตัวอย่าง

วงจรออก/ตรวจสอบด้วย symmetric secret:

import jwt
import time

SECRET = b"keep-this-out-of-source-control"

payload = {
    "sub": "kitchen-cam",
    "role": "admin",
    "exp": time.time() + 3600,                 # 1 hour from now
}

token = jwt.encode(payload, SECRET)
print("token:", token)

try:
    claims = jwt.decode(token, SECRET)
except jwt.exceptions.PyJWTError as e:
    print("rejected:", type(e).__name__)
else:
    print("subject:", claims["sub"])

ใช้ secret เดียวกันในการลงนามและตรวจสอบ ดังนั้นผู้ตรวจสอบต้องถือคีย์ที่ผู้ออกใช้ สำหรับบริการที่กล้องเป็นผู้ออก (แจก token ให้โทรศัพท์ที่จับคู่) ให้เก็บ secret ไว้ในระบบไฟล์ของกล้องและปฏิบัติเหมือนข้อมูลรับรองระยะยาวอื่นๆ ดู การดำเนินการ: คีย์ การหมดอายุ และการแก้ปัญหา

Note

โมดูลนี้ต้องอาศัย hmac และ hashlib ซึ่งทั้งคู่ถูกสร้างไว้ในกล้อง ไม่จำเป็นต้องกำหนดค่าภายนอก คีย์อาจมีความยาวเท่าใดก็ได้ แต่การสร้าง HMAC มีประโยชน์มากที่สุดเมื่อคีย์มีความยาวอย่างน้อยเท่ากับขนาดบล็อก SHA-256 (32 ไบต์)