JWT原理和簡單應用

JWT認證登陸

最近在作一個審覈系統,後臺登陸用到JWT登陸認證,在此主要作個總結git

JWT是什麼

Json web token (JWT), 根據官網的定義,是爲了在網絡應用環境間傳遞聲明而執行的一種基於JSON的開放標準.該token被設計爲緊湊且安全的,特別適用於分佈式站點的單點登陸場景。JWT的聲明通常被用來在身份提供者和服務提供者間傳遞被認證的用戶身份信息,以便於從資源服務器獲取資源,也能夠增長一些額外的其它業務邏輯所必須的聲明信息,該token也可直接被用於認證,也可被加密。github

爲何使用JWT

此處主要和傳統的session做對比,傳統的session在服務器端須要保存一些登陸信息,一般是在內存中,在後端服務器是集羣等分佈式的狀況下,其餘主機沒有保存這些信息,因此都須要經過一個固定的主機進行驗證,若是用戶量大,在認證這個點上容易造成瓶頸,是應用不易拓展。web

JWT原理

JWT由三個部分組成,用點號分割,看起來像是這樣,JWT token自己沒有空格換行等,下面是爲了美觀處理了下算法

eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.
eyJpc3MiOiJsYWJzX3B1cmlmaWVyLWFwaS1wYW5lbCIsImlhdCI6MTU1Mjk3NTg3OCwiZXhwIjoxNTU1NTY3ODc4LCJhdWQiOiJodHRwOi8vZmYtbGFic19wdXJpZmllci1hcGktdGVzdC5mZW5kYS5pby9wcm9kL3YxL2F1dGgvand0Iiwic3ViIjoiMTUwMTM4NTYxMTg4NDcwNCIsInNjb3BlcyI6WyJyZWdpc3RlciIsIm9wZW4iLCJsb2dpbiIsInBhbmVsIl19.
m0HD1SUd30TWKuDQImwjIl9a-oWJreG7tKVzuGVh7e4
1.頭部(Header)

Header部分是一個json,描述JWT的元數據,一般是下面這樣json

{
  "alg": "HS256",
  "typ": "JWT"
}

alg表示簽名使用的的算法,默認是HMAC SHA256,寫成HS256, tye表示這個token的類型,JWT token統一使用JWT,上面這段Header生成的token是後端

eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9
2.負載(Payload)

官方規定了7個字段,解釋以下api

  • iss: 簽發人,能夠填寫生成這個token的ID等等,可選參數
  • sub: 該JWT所面向的客戶,能夠存儲用戶的account_id等等,可選
  • aud:該JWTtoken的接收方,能夠填寫生成這個token的接口URL,可是不強制,可選
  • exp: 過時時間,時間戳,整數,可選參數
  • iat:生成token的時間,unix時間,時間戳,可選參數
  • nbf(Not Before): 表示該token在此時間前不可用,驗證不經過的意思,可選
  • jti: JWT ID,主要用來生成一次性token,可選的參數

除了官方以外,咱們還能夠定義一部分自定義字段,可是考慮到BASE64是可逆的,因此不要放入敏感信息
下面是一個例子;跨域

{
  "iss": "labs_purifier-api-panel",
  "iat": 1552975878,
  "exp": 1555567878,
  "aud": "http://ff-labs_purifier-api-test.fenda.io/prod/v1/auth/jwt",
  "sub": "1501385611884704",
  "scopes": [
    "register",
    "open",
    "login",
    "panel"
  ]
}

上面這個Payload,通過BASE64加密後,生成的token是安全

eyJpc3MiOiJsYWJzX3B1cmlmaWVyLWFwaS1wYW5lbCIsImlhdCI6MTU1Mjk3NTg3OCwiZXhwIjoxNTU1NTY3ODc4LCJhdWQiOiJodHRwOi8vZmYtbGFic19wdXJpZmllci1hcGktdGVzdC5mZW5kYS5pby9wcm9kL3YxL2F1dGgvand0Iiwic3ViIjoiMTUwMTM4NTYxMTg4NDcwNCIsInNjb3BlcyI6WyJyZWdpc3RlciIsIm9wZW4iLCJsb2dpbiIsInBhbmVsIl19
3.簽名(Signature)

Signature是對前面兩部分生成的兩段token的加密,使用的加密方式是Header裏面指定的,此處是HS256,此時,須要一個祕鑰,不能夠泄露,大體過程以下:服務器

HMACSHA256(
  base64UrlEncode(header) + "." +
  base64UrlEncode(payload),
  secret)

JWT的使用

JWT token 通常放在請求頭裏面,固然也能夠放在cookie裏面,可是放在cookie裏面不能夠跨域,例如:

Authorization: Bearer <token>

JWT在Python中的簡單生成和驗證

jwt庫

生成token

def create_token():
    payload={
              "iss": "labs_purifier-api-panel",
              "iat": 1552975878,
              "exp": 1555567878,
              "aud": Config.AUDIENCE,
              "sub": "1501385611884704",
              "scopes": [
                "register",
                "open",
                "login",
                "panel"
              ]
            }
    token = jwt.encode(payload, Config.SECRET_KEY, algorithm='HS256')
    return True, {'access_token': token}

驗證token

def verify_jwt_token(token):
    try:
        payload = jwt.decode(token, Config.SECRET_KEY,
                             audience=Config.AUDIENCE,
                             algorithms=['HS256'])
    except (ExpiredSignatureError, DecodeError):
        return False, token
    if payload:
        return True, jwt_model

須要注意的是,若是在生成的時候,加上了aud參數,驗證的時候也要用上audience參數,而且值必須同樣

相關文章
相關標籤/搜索