[Web] JWT


マークhttpの代表的な特徴statelessは、接続が中断され、サーバおよびクライアントは、クライアントが以前に要求した結果を忘れてしまう.すなわち,それぞれの通信記録が保存されていないため,以前にログインしてもユーザがサーバに要求するたびに인증を行い,認証を行うための토큰(Token)である.これらのトークンはメタデータとして、サーバとクライアントがrequestおよびresponseを交換すると、headerにロードされて交換される.
ユーザーが正常にログインした場合  サーバはクライアントにaccess tokenを送信し、ログインに成功すると、 クライアントはaccess tokenを追加し、requestをサーバに送信し、ログインのたびに送信しないようにします.
ここでaccess tokenを生成する方法は様々であり、その中で最も広く用いられている技術の一つがJWT(JSON Web Tokens)である.
JWT(JSON Web Tokens)
名前の通り、JWTとは、ユーザ情報を含むJSONデータを暗号化してクライアントとサーバとの間で交換することを意味する.
JWT構造
JWTは、タイトル、コンテンツ、署名の3つの構造から構成されています.
タイトル(Header)
ヘッダにはトークンタイプとハッシュアルゴリズムの情報があります.ヘッダの内容はBASE 64で符号化され、JWTの第1の部分に記録される.以下の例に示すように、アルゴリズム方式はHS 256であり、タイプはJWTとしてマークされた情報を含む.
  • {"alg":"HS256", "typ":"JWT"}
    コンテンツ(Payload)
    内容には、トークンに含める情報が含まれています.次に、情報の一部をクレーム(claim)と呼び、{「key」:「value」}に示す.クレームは、公開クレーム(public claim)と非公開クレーム(private claim)に分けられます.公開クレームには、コインの有効期限を表すexp、コインの発行時間を示すiatなどが含まれ、非公開クレームは、クライアントとサーバの間でプロトコルを行う際に使用されるクレームです.この開示と非開示クレームを組み合わせた後、BASE 64方式で符号化記録を行う.
  • {"user-id":1, "exp":"1539517391"}
    に署名
    署名は契約書に署名して契約書の偽造を防止するように、JWTがそのままであることを確認する際に使用される.前に見たタイトルと内容の値は、単純に符号化された値です.ただし,署名ではヘッダとコンテンツの値に加えてヘッダに指定された暗号アルゴリズムを用いて,別途生成された秘密鍵(Secret Key)を暗号化して伝送する.もちろん、この値は復号可能であるので、クライアントがJWTをAPIサーバに送信すると、サーバは、サーバによって生成されたJWTが正しいかどうかを判断するために、送信されたJWTの署名部分を復号する.
    つまり,このトークンが我々のサイトで発行されたトークンであるかどうかの鍵が秘密鍵(Secret Key)となることを確認することができる.
    JWTの使用例
    インストール
  • pyjwt
  • pip install pyjwt
    作成
  • JWT
  • >>> import jwt
    >>> encoded_jwt = jwt.encode({"user-id": 5}, "secret", algorithm="HS256")
    >>> encoded_jwt
    'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyLWlkIjo1fQ.tBQu0HfnOYK7lL3tH5ImgsI-y4Jz1RKscJWbV3U2QMI'
    *パッケージ名はpyjwtですが、インポート時の名前はjwtです.
    JWTの最初のパラメータはJWTに書き込まれる内容(ペイロード)であり、2番目のパラメータは秘密鍵を書くが、秘密鍵の露出を避ける.また、復号可能であるため、コンテンツ(ペイロード)にユーザのアイデンティティやパスワードなどのユーザ情報を含まないようにし、例で用いたidは、DBのアクセス権限がなければ、知っていても意味のない情報であるため、開示することができる.
  • JWT復号
  • >>> jwt.decode(encoded_jwt, "secret", algorithm="HS256")
    {'user-id': 5}
    リファレンス
    🔗 PyJWT | Welcome to PyJWT
    🔗 DevTaekの開発備考|HTTPは無状態で、どのようにログインを実現しますか?
    🔗 VELOPERT.LOG|JSON Web Tokenの概要と構造