「[[マイクロソフト系技術情報 Wiki>http://techinfoofmicrosofttech.osscons.jp/]]」は、「[[Open棟梁Project>https://github.com/OpenTouryoProject/]]」,「[[OSSコンソーシアム .NET開発基盤部会>https://www.osscons.jp/dotNetDevelopmentInfrastructure/]]」によって運営されています。

-戻る
--[[JSON]]
--[[クレームベース認証]]

* 目次 [#ld8342fd]
#contents

*概要 [#yfb13271]
-http://openid-foundation-japan.github.io/draft-ietf-oauth-json-web-token-11.ja.html

JWTとはJSON Web Tokenの略でjot(ジョット)と発音する。

**仕様 [#u3914621]
-JSONのアサーションを生成するための仕様

-Base64 URL Encodeした[[ヘッダ>#m9c6f99a]]、[[ペイロード(クレームセット)>#m5b94cda]]等を「.」で連結
--このため、url-safeであり、Webでの取り扱いが楽。
--言語毎のライブラリも整っており、相互運用が容易。
--言語毎のライブラリも整っており、自作も相互運用も容易。

**用途 [#s26d45ab]
-暗号化により、鍵で[[ペイロード(クレームセット)>#m5b94cda]]の改ざんチェック可能(=信頼関係のセマンティクス)。

-この特徴のため、仲介者を伴う(改竄・盗聴の危険性がある)情報のやり取りに利用される。
--主に、認証サーバから返されるトークンに使われる。
--実際、[[OAuth]] 2.0 拡張や[[OpenID Connect]]などで使われている。

*構造 [#ad27d98c]

**構成要素 [#q01f4062]
以下の要素から構成される。

ここの詳細は、[[RFC>#t002076b]]を参照。

個別に、
-[[OpenID Connect]]の[[IDトークン(クレーム)>OpenID Connect#ofb73c59]]
-[[JWT生成プログラムの作成方法の参考サイト>JWT#e11d0494]]

などを参照のこと。

***ヘッダ [#m9c6f99a]
-JSONオブジェクト(JOSE)ヘッダ
--署名・検証のために利用するもの。
--電子署名、MAC に関する情報を保持する。
--このヘッダは、[[JWS>#md583102]]でも[[JWE>#y75c2692]]でも共通

-ヘッダの内容は、3 種に分けられている。

--Registered Header
---RFC 上で仕様化されているヘッダ内容。
---署名に使うアルゴリズムを示す alg 
---公開鍵の在処を示す jku (JWK Set URL)

--Public Header~
定義していいけど名前の衝突を避けるために IANA に登録したヘッダ内容。

--Private Header~
衝突するかもしれないから注意が必要なヘッダ内容。

***ペイロード(クレームセット) [#m5b94cda]

-[[予約済みクレーム>https://openid-foundation-japan.github.io/draft-ietf-oauth-json-web-token-11.ja.html#ReservedClaimName]]~
以下すべて、使用は任意 (OPTIONAL)。
--"iss" : Issuer クレーム
--"sub" : (Subject) クレーム
--"aud" : (Audience) クレーム
--"exp" : (Expiration Time) クレーム
--"nbf" : (Not Before) クレーム
--"iat" : (Issued At) クレーム
--"jti" : (JWT ID) クレーム
--"typ" : (Type) クレーム
|#|キー|説明|h
|1|"iss"|Issuer クレーム|
|2|"sub"|Subject クレーム|
|3|"aud"|Audience クレーム|
|4|"exp"|Expiration Time クレーム|
|5|"nbf"|Not Before クレーム|
|6|"iat"|Issued At クレーム|
|7|"jti"|JWT ID クレーム|
|8|"typ"|Type クレーム|

-パブリック・クレーム
--JWTの利用者によって自由に定義できる。
--衝突を避けるために、
---IANA JSON Web Token Claim Registry に登録するか、
---耐衝突性を持つ名前空間を含むパブリック名にすべき。

-プライベート・クレーム
--JWTの作成者と利用者の合意のものとで、~
予約済みでもパブリック・クレーム名でもないプライベート・クレーム名を利用可能。
--ただし、衝突の可能性があるため、慎重に使用する必要がある。

-サンプル
 {
   "sub": "1234567890",
   "name": "John Doe",
   "admin": true
 }

***その他 [#h6c0fec8]
JWTの種類によって様々。


**JWTの種類 [#j5dabc60]
http://openid-foundation-japan.github.io/draft-ietf-jose-json-web-signature-14.ja.html

***[[JWS]] [#md583102]

***[[JWE]] [#y75c2692]

***プレーンJWT [#d5575bd7]
-[[JWS>#md583102]]でも[[JWE>#y75c2692]]でもない、プレーンなJWT。
-[[ヘッダ>#m9c6f99a]]内のalgはnone = {“alg”: “none”} 。

-フォーマット([[JWS Compact Serialization>JWS#xe1c18e7]])
--[[ヘッダ>#m9c6f99a]].[[ペイロード(クレームセット)>#m5b94cda]].
--
 BASE64URL (UTF-8 (Header))
 .
 BASE64URL (UTF-8 (Claim Set))
 .

***[[JWK]] [#t3bd8497]

***JWA [#y4a514dc]
[[JWS>#md583102]]や[[JWE>#y75c2692]]で利用される各アルゴリズムおよびそれらの識別子を定義している仕様

*JWTの作成と検証手順 [#dd514c38]
-JWT を扱えるライブラリは沢山ある。

-署名・暗号化は特定用途であれば、1パターン実装すればイイので自作も可能。

-検証・復号化は網羅性を高めることが難しいので、ライブラリを使用する。
--OpenID Connect の JWT の署名を自力で検証してみると見えてきた公開鍵暗号の実装の話 - Qiita~
http://qiita.com/bobunderson/items/d48f89e2b3e6ad9f9c4c

**ライブラリ [#n981cbc3]
-JSON Web Token の効用 - Qiita~
http://qiita.com/kaiinui/items/21ec7cc8a1130a1a103a

-WebCrypto APIでJSON Web Tokenの検証を試してみる - Qiita~
http://qiita.com/tomoyukilabs/items/faa66805a440f4b30cfb

|項番|言語|ライブラリのURL|h
|0|JavaScript|https://www.w3.org/TR/WebCryptoAPI/|
|1|Ruby|https://github.com/nov/json-jwt|
|2|Python|https://github.com/rohe/pyjwkest|
|3|Java|https://bitbucket.org/nimbusds/nimbus-jose-jwt/wiki/Home|
|4|PHP|https://github.com/ritou/php-Akita_JOSE|
|5|Perl|https://github.com/xaicron/p5-JSON-WebToken|
|6|Objective-C|https://github.com/yourkarma/JWT|
|7|.NETなら|Nugetからメジャーな奴を入れる。|

**JWTの作成手順 [#pfa9f0dd]
-JWSやJWEの手順に従って作成
-入れ子になったJWTの場合には[[ヘッダ>#m9c6f99a]]の”cty”の値に”JWT”を指定

***[[JWS]] [#n6dca050]

***[[JWE]] [#e5ba4555]

**JWTの検証手順 [#r8923712]
-JWSやJWEの手順に従って作成

***[[JWS]] [#ldcecbc0]

***[[JWE]] [#tc2030de]

*ユースケース [#neb31e45]
-http://openid-foundation-japan.github.io/draft-ietf-jose-use-cases-03.ja.html

-JSON Web Token の効用 - Qiita~
http://qiita.com/kaiinui/items/21ec7cc8a1130a1a103a

-JWTによるJSONに対する電子署名と、そのユースケース | Developers.IO~
http://dev.classmethod.jp/server-side/json-signing-jws-jwt-usecase/

**認証用途 [#yd304024]
-JWT(JSON Web Token)を使った認証を試みる | 69log~
https://blog.kazu69.net/2016/07/30/authenticate_with_json_web_token/
-JWTを認証用トークンに使う時に調べたこと - Carpe Diem~
http://christina04.hatenablog.com/entry/2016/06/07/123000
-JWT(Json Web Token)を利用したWebAPIでのCredentialの受け渡しについて | I am mitsuruog~
http://blog.mitsuruog.info/2014/08/jwtjson-web-tokenwebapicredential.html
-カスタム・アプリケーションによる認証フローとプログラミング - Build Insider~
http://www.buildinsider.net/web/msidentitydev/03

***[[OpenID Connect]]のIDトークン [#o5f70766]
[[コチラ>OpenID Connect#ofb73c59]]を参照。

***[[OAuth]] 2.0のアクセストークン [#f9d1b3ca]
[[コチラ>OAuthによる外部ログイン(認証)の研究#yf9cec19]]を参照。

***シングルサインオン(SSO) [#qc19ebd8]
-シングルサインオン - Wikipedia~
https://ja.wikipedia.org/wiki/%E3%82%B7%E3%83%B3%E3%82%B0%E3%83%AB%E3%82%B5%E3%82%A4%E3%83%B3%E3%82%AA%E3%83%B3

--近年は、SAMLアサーションやJWTアサーション([[OpenID Connect]]の[[IDトークン>OpenID Connect#ofb73c59]])~
によって、クレデンシャル伝えてSSOを実現する方式が一般的になってきている。

-JWTを使った簡易SSOで徐々にシステムをリニューアルしている話~
http://www.slideshare.net/TsuchiKazu/jwt-ssopepabotech

--ショップ(Webアプリ)とカート(WebAPI+SPA)を分離し、~
tempストアをサイト間で共有しないで、認証情報を共有するSSOを実現したい。

--JWTにより、以下を跨いだ認証が可能に。
---サーバー(Webアプリ・WebAPI)間
---クライアント(ブラウザ)・サーバー(Webアプリ・WebAPI)間

--また、その後の、

---マイクロサービス化にも対応可能になる。~
サービスの多様化、フロントエンドの多極化

---認証情報以外の共有したい情報にも利用することができる。~
この場合、[[JWE>#y75c2692]]を使用する可能性がある(HTTPSなら不要だが)。

-JWT(JSON Webトークン)を使用したシングルサインオンの設定 – Zendesk Support~
https://support.zendesk.com/hc/ja/articles/203663816-JWT-JSON-Web%E3%83%88%E3%83%BC%E3%82%AF%E3%83%B3-%E3%82%92%E4%BD%BF%E7%94%A8%E3%81%97%E3%81%9F%E3%82%B7%E3%83%B3%E3%82%B0%E3%83%AB%E3%82%B5%E3%82%A4%E3%83%B3%E3%82%AA%E3%83%B3%E3%81%AE%E8%A8%AD%E5%AE%9A

**メール着信確認トークン [#uc4b4ccb]
以下でメール着信確認トークンを使用するようなケースで利用する事で、~
トークンをtempストアに格納して、後に比較するような実装が不要になる。

-アカウント確認(E-mail confirmation)
-パスワード・リセット

**共有用URL [#w567a950]
-OneDriveのファイル・フォルダ共有にも利用されている。
-URLにオブジェクトに対する[[ACL・ACE]]的なモノをJWTアサーションに同梱。
-サービスが認証したユーザがオブジェクトに対するアクセス許可を持っているか、[[ACL・ACE]]から確認する。

*.NETのJWTライブラリ [#c4fe6111]
-JWT を扱える[[ライブラリ>#n981cbc3]]は沢山ある。

-署名・暗号化は特定用途であれば、1パターン実装すればイイので自作も可能。

-検証・復号化は網羅性を高めることが難しいので、[[ライブラリ>#n981cbc3]]を使用する。
--OpenID Connect の JWT の署名を自力で検証してみると見えてきた公開鍵暗号の実装の話 - Qiita~
http://qiita.com/bobunderson/items/d48f89e2b3e6ad9f9c4c

*ライブラリ [#n981cbc3]
**様々なライブラリ(相互運用) [#j1232beb]
-JSON Web Token の効用 - Qiita~
http://qiita.com/kaiinui/items/21ec7cc8a1130a1a103a

-WebCrypto APIでJSON Web Tokenの検証を試してみる - Qiita~
http://qiita.com/tomoyukilabs/items/faa66805a440f4b30cfb

|項番|言語|ライブラリのURL|h
|0|JavaScript|https://www.w3.org/TR/WebCryptoAPI/|
|1|Ruby|https://github.com/nov/json-jwt|
|2|Python|https://github.com/rohe/pyjwkest|
|3|Java|https://bitbucket.org/nimbusds/nimbus-jose-jwt/wiki/Home|
|4|PHP|https://github.com/ritou/php-Akita_JOSE|
|5|Perl|https://github.com/xaicron/p5-JSON-WebToken|
|6|Objective-C|https://github.com/yourkarma/JWT|
|7|.NETなら|NuGetからメジャーな奴を入れる。|

**相性がある模様 [#l9bea68e]
***[[System.IdentityModel.Tokens.JwtSecurityTokenHandler>https://msdn.microsoft.com/ja-jp/library/system.identitymodel.tokens.jwtsecuritytokenhandler.aspx]] [#y171da32]

Microsoft Open Technologiesによって開発された、~
JSON Web Token Handler For the Microsoft .Netというライブラリ。

下記が参考になる。

-IdM実験室~
http://idmlab.eidentity.jp
-- [JWT/OAuth]Service Accountを使ってGoogle APIを利用する①, ②~
---http://idmlab.eidentity.jp/2015/01/jwtoauthservice-accountgoogle-api.html
---http://idmlab.eidentity.jp/2015/01/jwtoauthservice-accountgoogle-api_5.html

上記は、Resource Ownerであるユーザが介在することなく~
ClientがResource ServerのAPIを利用するようなユースケースらしく、~
以下の様な、grant_typeで、Access Tokenを取得して、WebAPIにアクセスする。

-grant_type:~
http://oauth.net/grant_type/jwt/1.0/bearer
--TenantContextID、AppPrincipalId、SymmetricKey を使用して、
--JWTを投げると、Access Tokenが返ってくるflowのgrant_typeらしい。

この時、Googleの秘密鍵のキー長は1024bitだが、~
このライブラリは最低でも2048bitを要求しているため、

>相互運用が不可だったらしい。

恐らく、色々なライブラリ間の実装差異で~
相互運用が難しくなるようなケースがあると思う。

***[[Microsoft.Owin.Security.Jwt.JwtFormat>https://msdn.microsoft.com/ja-jp/library/microsoft.owin.security.jwt.jwtformat.aspx]] [#ib881924]

以下の2メソッドのインターフェイスを確認すると、~
引数・戻り値に、Microsoft.Owin.Security.AuthenticationTicketが在ったり、~
.NET技術と結合度が高く、相互運用には向かないように見える。

-[[JwtFormat.Protect メソッド>https://msdn.microsoft.com/ja-jp/library/dn450167.aspx]]
-[[JwtFormat.Unprotect メソッド>https://msdn.microsoft.com/ja-jp/library/dn450160.aspx]]

**検索結果 [#r4ac23c8]
-NugetやWebを検索した所、以下の2ライブラリの利用者が多い。
-NuGetやWebを検索した所、以下の2ライブラリの利用者が多い。
-ダウンロード数を確認した所、System.IdentityModel.Tokens.Jwtが優勢。

***JSON Web Token (JWT) implementation for .NET [#o8ee7ae2]

-NuGet Gallery | JWT 1.3.4~
https://www.nuget.org/packages/JWT/

Version Historyを参照。

***System.IdentityModel.Tokens.Jwt [#f8161509]
以前は、JSON Web Token Handler For the Microsoft .Netという表示名だったようだが、~
version 05-00からは、パッケージ名(=名前空間)と同じ表示名になっている。~
ライセンスはMITだが、ソースコードをGithubやCodePlex上に確認できない・・・。

上記の、BCL入りしているJwtSecurityTokenHandlerが含まれる名前空間より~
一つ下の階層のJWT系の追加ライブラリを格納する名前空間であるもよう。

必要に応じて、追加でNugetから取得する必要がある。
必要に応じて、追加でNuGetから取得する必要がある。

-NuGet Gallery | System.IdentityModel.Tokens.Jwt~
https://www.nuget.org/packages/System.IdentityModel.Tokens.Jwt/

詳しくは、Version Historyを参照。

*自作のJWTライブラリ [#v028206c]
**自作のJWTライブラリ [#v028206c]
以下を考慮して開発可能。

**用途 [#b90af93a]
***用途 [#b90af93a]
-認証など、特定用途の署名・暗号化、検証・復号化レベルであればであれば自作ライブラリで良い。
-正しく署名・暗号化できていれば、他のライブラリでも検証・復号化が可能。

**相互運用(検証・復号化) [#dfbab710]
***相互運用(検証・復号化) [#dfbab710]
他のライブラリでも検証・復号化が可能かどうかは、~
[[JSON Web Tokens - jwt.io>https://jwt.io/]]などの検証サイトを使用して確認すると良い。

**Base64url Enc/Dec [#n0909b67]
***Base64url Enc/Dec [#n0909b67]
このライブラリも必要になる。

-【C#】Base64urlエンコード・デコード - Qiita~
http://qiita.com/hukatama024e/items/b1352cabcd85948511c3
>RFC4648に条件付きでパディング外すなどの難しい処理が~
あるようなので、ライブラリを使用するほうが良いかもしれない~
(Microsoft.Owin.Securityのicrosoft.Owin.Security.DataHandler.Encoderにライブラリがある)。

**脆弱性 [#j8e0d191]
***脆弱性 [#j8e0d191]
実装に脆弱性を作らないように注意する。

-JWS 実装時に作りがちな脆弱性パターン - OAuth.jp~
http://oauth.jp/blog/2015/03/16/common-jws-implementation-vulnerability/

ざっくり、
-alg を "none"に改竄された場合、検証でtrueにするな。
-alg を "HMAC-SHA*"に改竄された場合、検証でtrueにするな。

ということらしい。

後者は、
-公開鍵暗号方式 (RSA / ECDSA) から共通鍵暗号方式 (HMAC) に差し替え、
-「公開鍵文字列を共通鍵として利用して」署名を生成することで、

検証でtrueになるJWTを生成できてしまう模様。

特定用途の自作ライブラリであれば、~
署名と検証のalgは固定にしておくのも良いと考える。

**参考 [#v386926d]
***[[JWS]] [#qe759f54]
***[[JWE]] [#p8193a1f]
***参考 [#v386926d]
-[[JWS]]の自作ライブラリ
-[[JWE]]の自作ライブラリ

*参考 [#p90217f2]
-JWT Translation #technight~
http://www.slideshare.net/matake/jwt-trans

-JWTについて簡単にまとめてみた - hiyosi's blog~
https://hiyosi.tumblr.com/post/70073770678/jwt%E3%81%AB%E3%81%A4%E3%81%84%E3%81%A6%E7%B0%A1%E5%8D%98%E3%81%AB%E3%81%BE%E3%81%A8%E3%82%81%E3%81%A6%E3%81%BF%E3%81%9F

**[[JWS]] [#u904c09f]

**[[JWE]] [#sf477302]

**[[JWK]] [#wd42f78a]

**RFC [#t002076b]
-IETF JOSE WG と OAuth WG から一気に9本の RFC が! - OAuth.jp~
http://oauth.jp/blog/2015/05/20/jose-and-oauth-assertion-rfcs/

***OAuth WG [#vdd1ecf0]
-RFC 7519 - JSON Web Token (JWT)~
https://tools.ietf.org/html/rfc7519

-[[RFC 7521, 7522, 7523>JWT bearer token authorizationグラント種別#c65d5829]]

***JOSE WG [#z5dc6cf2]
jose : Javascript Object Signing and Encryption

-RFC 7515 - JSON Web Signature (JWS)~
https://tools.ietf.org/html/rfc7515
-RFC 7516 - JSON Web Encryption (JWE)~
https://tools.ietf.org/html/rfc7516
-RFC 7517 - JSON Web Key (JWK)~
https://tools.ietf.org/html/rfc7517
-RFC 7518 - JSON Web Algorithms (JWA)~
https://tools.ietf.org/html/rfc7518
-RFC 7520 - Examples of Protecting Content~
Using JSON Object Signing and Encryption (JOSE)~
https://tools.ietf.org/html/rfc7520

***公開資料 | OpenID ファウンデーション・ジャパン [#n96a7959]
-JSON Web Token (JWT)~
https://openid-foundation-japan.github.io/draft-ietf-oauth-json-web-token-11.ja.html

**内部 [#ua5e41e6]

***[[JWS]] [#u904c09f]

***[[JWE]] [#sf477302]

***[[JWK]] [#wd42f78a]

----
Tags: [[:認証基盤]], [[:クレームベース認証]], [[:暗号化]]


トップ   新規 一覧 単語検索 最終更新   ヘルプ   最終更新のRSS