$30 off During Our Annual Pro Sale. View Details »

仕様が読めるようになるOAuth2.0、OpenID Connect 入門

Auth屋
October 05, 2023

仕様が読めるようになるOAuth2.0、OpenID Connect 入門

2023/10/05 Offersさんのイベントでの資料です。
https://offers.connpass.com/event/295782/

イベント後の満足度アンケート(5点満点)の結果は以下になります。
5点: 49%
4点: 39%
3点: 8%
2点: 4%

こちらのスライドの内容は以下の本の抜粋になります。デモの内容、このスライドでは触れていないことについてご興味ある場合は以下の本をご参照ください。
https://authya.booth.pm/items/1296585
https://authya.booth.pm/items/1550861

本発表で扱っていないセキュリティに関しては以下の本がおすすめです。
https://authya.booth.pm/items/1877818

本の評判
https://togetter.com/li/1477483

Auth屋

October 05, 2023
Tweet

More Decks by Auth屋

Other Decks in Technology

Transcript

  1. 仕様が読めるようになる
    OAuth2.0、OpenID Connect入門
    2023 年 10 月 5 日
    Auth屋
    1

    View Slide

  2. Auth屋 is 誰 ?
    OAuth2.0、OpenID Connectの本を書いてます
    商業誌 同人誌
    Boothで販売中 https://authya.booth.pm/
    Amazon、その他書店で発売中
    2

    View Slide

  3. 監修者 いとう りょうさん(@ritou)
    ● OpenID Connect Core1.0の
    コントリビュータ
    ● OpenIDファウンデーション・ジャパン
    のエバンジェリスト
    ● Identity Dance School #iddance
    3

    View Slide

  4. アンケート
    4

    View Slide

  5. RFC6749 (OAuth2.0の基本仕様)
    OAuthでは, クライアントは, リソースオーナーのコントロー
    ル下にありリソースサーバーによってホストされているリ
    ソースへのアクセス権を要求する. そしてリソースオーナー
    のクレデンシャルそのものとは別のクレデンシャルを取得す
    る.
    5
    引用元: OpenID ファウンデーション・ジャパン による日本語訳
    http://openid-foundation-japan.github.io/rfc6749.ja.html

    View Slide

  6. RFC6749 (OAuth2.0の基本仕様)
    OAuthでは, クライアントは, リソースオーナーのコントロー
    ル下にありリソースサーバーによってホストされているリ
    ソースへのアクセス権を要求する. そしてリソースオーナー
    のクレデンシャルそのものとは別のクレデンシャルを取得す
    る.
    6
    引用元: OpenID ファウンデーション・ジャパン による日本語訳
    http://openid-foundation-japan.github.io/rfc6749.ja.html
    最後に見返します

    View Slide

  7. 基本的な用語と概念を理解すれば読める
    7

    View Slide

  8. 目次
    OAuth
    ● 登場人物
    ● OAuthとは何か
    ● OAuthのメリット
    ● OAuthのフロー
    ● OAuthでログイン?
    OpenID Connect
    ● OpenID Connectとは
    ● IDトークンとは
    8

    View Slide

  9. OAuthの登場人物
    9

    View Slide

  10. OAuthの登場人物
    10
    ユーザー 画像編集アプリ
    Google OAuth
    Google Photo API

    View Slide

  11. OAuthの登場人物
    11
    ユーザー 画像編集アプリ
    Google OAuth
    Google Photo API
    Google Photo から
    画像をダウンロード

    View Slide

  12. OAuthの登場人物
    12
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)

    View Slide

  13. OAuthの登場人物
    13
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    写真・動画などの
    リソースを保持

    View Slide

  14. OAuthの登場人物
    14
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    アクセストークンを発

    View Slide

  15. OAuthの登場人物
    15
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    アプリのユーザー
    Google Photo のユーザー
    (リソースの所有者)

    View Slide

  16. OAuthの登場人物
    16
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    リソース
    を利用するアプリ

    View Slide

  17. OAuthの登場人物 | 2つのクライアント
    17
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    クライアントシークレットを安
    全に保持できない
    パブリッククライアント

    View Slide

  18. OAuthの登場人物 | 2つのクライアント
    18
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    クライアントシークレットを
    安全に保持できる
    コンフィデンシャルクライアント

    View Slide

  19. OAuthとは何か
    19

    View Slide

  20. OAuthとは何か
    ● RFC6749「OAuth2.0 はサードパーティアプリケーションによる HTTP
    サービスへの限定的なアクセスを可能にする認可フレームワークである」
    ● 例「OAuth2.0は画像編集アプリによるGoogle Photo への限定的なアクセ
    ス(Aさんの画像のダウンロード)を可能にするアクセストークンの発行
    ルールである」 20
    RFC6749の用語 画像編集アプリの例
    サードパーティアプリ 画像編集アプリ
    HTTPサービス Google Photo
    限定的なアクセス Aさんの画像のダウンロードのみ
    認可フレームワーク アクセストークンの発行ルール

    View Slide

  21. OAuth の流れ
    21
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    Google Photoから写真を
    ダウンロード

    View Slide

  22. OAuth の流れ
    22
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    Google Photo APIに
    アクセスしたい

    View Slide

  23. OAuth の流れ
    23
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    Google Photoのリソース
    オーナーとしての認証

    View Slide

  24. OAuth の流れ
    24
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    画像編集アプリにGoogle Photoの
    画像のダウンロードを許可します
    か?

    View Slide

  25. OAuth の流れ
    25
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    許可します

    View Slide

  26. OAuth の流れ
    26
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    アクセストークン発行

    View Slide

  27. OAuth の流れ
    27
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    画像ダウンロードします

    View Slide

  28. OAuth の流れ
    28
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    アクセストークンのチェック

    View Slide

  29. OAuth の流れ
    29
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    画像どうぞ

    View Slide

  30. OAuthを使うメリット
    30

    View Slide

  31. OAuthは何が嬉しいのか
    ● 画像編集アプリにGoogleの認証情報(ID、パスワードなど)を渡す必要がない
    31
    ユーザー
    (リソースオーナー) 画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    認証

    View Slide

  32. OAuthがない場合
    32
    32
    Aさん 画像編集アプリ
    Google Photo API

    View Slide

  33. OAuthがない場合
    33
    33
    Aさん 画像編集アプリ
    Google Photo API
    Googleの
    ID/パスワード

    View Slide

  34. OAuthがない場合 | ケース1
    34
    34
    Aさん 悪意ある
    画像編集アプリ
    Google Photo API
    Googleの
    ID/パスワード

    View Slide

  35. OAuthがない場合 | ケース2
    35
    35
    Aさん 画像編集アプリ
    Google Photo API
    Googleの
    ID/パスワード

    View Slide

  36. OAuthがない場合 | ケース2
    36
    36
    ユーザー 画像編集アプリ
    Google Photo API
    Googleの
    ID/パスワード

    View Slide

  37. OAuthがない場合 | ケース2
    37
    37
    ユーザー 画像編集アプリ
    Google Photo API
    Aさんの
    Google Photoで
    なんでもできる

    View Slide

  38. OAuthがある場合
    38
    38
    ユーザー 画像編集アプリ
    Google OAuth
    Google Photo API
    アクセストークン

    View Slide

  39. OAuthがある場合
    39
    39
    ユーザー 画像編集アプリ
    Google OAuth
    Google Photo API
    Aさんの画像の
    ダウンロードだけを
    一定期間できる

    View Slide

  40. OAuthのフロー
    40

    View Slide

  41. OAuthのフロー(グラント)
    ● 認可コードフロー
    ● インプリシットフロー
    ● リソースオーナーパスワードクレデンシャルフロー
    ● クライアントクレデンシャルフロー
    41

    View Slide

  42. OAuthのフロー(グラント)
    ● 認可コードフロー
    ● インプリシットフロー ← 非推奨
    ● リソースオーナーパスワードクレデンシャルフロー ← 特殊ケース
    ● クライアントクレデンシャルフロー ← ユーザー関係しない
    42

    View Slide

  43. クライアントの登録
    43
    ユーザー
    (リソースオーナー)ç
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    APIを利用するアプリと
    して事前に登録

    View Slide

  44. クライアントの登録
    44
    ● 一般的には開発者向けサイトでアプリの情報を登録
    ● クライアントID・クライアントシークレットの発行を受ける

    View Slide

  45. クライアントの登録
    45

    View Slide

  46. クライアントの登録
    46
    {
    "web": {
    "client_id": "7429476-bb2mshkghp5bje196p9pvugi1av19.apps.googleusercontent.com",
    "project_id": "storied-box-250407",
    "auth_uri": "https://accounts.google.com/o/oauth2/auth",
    "token_uri": "https://oauth2.googleapis.com/token",
    "auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
    "client_secret": "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uww",
    "redirect_uris": [
    "https://offers.example.com/callback"
    ]
    }
    }

    View Slide

  47. クライアントの登録
    47
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    クライアントID
    クライアントシークレット

    View Slide

  48. クライアントの登録
    48
    ユーザー
    (リソースオーナー)
    画像編集アプリ
    (クライアント)
    Google OAuth
    (認可サーバー)
    Google Photo API
    (リソースサーバー)
    アプリの
    リダイレクトURI

    View Slide

  49. 認可コードフロー
    49

    View Slide

  50. 認可コードフロー
    50
    Step1
    ROの認証
    権限委譲の同意

    認可コードの発行

    View Slide

  51. 認可コードフロー
    51
    Step2
    クライアント認証

    アクセストークンの発行

    View Slide

  52. 認可コードフロー
    52
    Step1
    ROの認証
    権限委譲の同意

    認可コードの発行

    View Slide

  53. 認可コードフロー
    53
    Google Photoから
    ダウンロード

    View Slide

  54. 認可コードフロー
    54
    Google Photoの画像の
    ダウンロード権限の
    リクエスト

    View Slide

  55. 認可コードフロー
    55
    認可リクエスト

    View Slide

  56. 認可コードフロー
    56
    認可エンドポイント

    View Slide

  57. 認可リクエスト
    GET /authorize
    ?response_type=code
    &client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &state=s6Bh…Rkqt3
    &redirect_uri=htts://offers.example.com/callback
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    57

    View Slide

  58. 認可リクエスト
    GET /authorize
    ?response_type=code
    &client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &state=s6Bh…Rkqt3
    &redirect_uri=htts://offers.example.com/callback
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    58
    レスポンスタイプ= 認可コード

    View Slide

  59. 認可リクエスト
    GET /authorize
    ?response_type=code
    &client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &state=s6Bh…Rkqt3
    &redirect_uri=htts://offers.example.com/callback
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    59
    クライアントID

    View Slide

  60. 認可リクエスト
    GET /authorize
    ?response_type=code
    &client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &state=s6Bh…Rkqt3
    &redirect_uri=htts://offers.example.com/callback
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    60
    セッションと紐づけたランダムな文字列
    クロスサイトリクエストフォージェリー対策

    View Slide

  61. 認可リクエスト
    GET /authorize
    ?response_type=code
    &client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &state=s6Bh…Rkqt3
    &redirect_uri=htts://offers.example.com/callback
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    61
    Redirect URI

    View Slide

  62. 認可リクエスト
    GET /authorize
    ?response_type=code
    &client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &state=s6Bh…Rkqt3
    &redirect_uri=htts://offers.example.com/callback
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    62
    スコープ

    View Slide

  63. スコープ
    ● アクセストークンに紐付ける権限
    ● 権限の内容、表現方法は仕様では規定されていない(サービスごとに違う)
    ● Googleの例
    https://www.googleapis.com/auth/photoslibrary.readonly
    Google Photoのリソースに対する読み込み権限
    https://www.googleapis.com/auth/photoslibrary.appendonly
    Google Photoのリソースに対する書き込み権限
    https://www.googleapis.com/auth/photoslibrary.sharing
    Google Photoのリソースに対するアルバムの作成、共有などの権限
    63

    View Slide

  64. 認可リクエスト
    GET /authorize
    ?response_type=code
    &client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &state=s6Bh…Rkqt3
    &redirect_uri=htts://offers.example.com/callback
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    64

    View Slide

  65. 認可コードフロー
    65
    リソースオーナーの認証
    権限委譲の同意

    View Slide

  66. 認証画面と同意画面
    66

    View Slide

  67. 認可コードフロー
    67
    リソースオーナーの認証
    権限委譲の同意

    View Slide

  68. 認可コードフロー
    68
    認可コード
    発行します

    View Slide

  69. 認可コードフロー
    69
    リダイレクトURLに
    認可コードを渡す
    リダイレクトURI

    View Slide

  70. 認可コードフロー
    70
    認可レスポンス

    View Slide

  71. 認可レスポンス
    302 Found
    Location: https://offers.example.com/callback
    ?state=s6Bh…Rkqt3
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    71

    View Slide

  72. 認可レスポンス
    302 Found
    Location: https://offers.example.com/callback
    ?state=s6Bh…Rkqt3
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    72
    リダイレクトURI

    View Slide

  73. 認可レスポンス
    302 Found
    Location: https://offers.example.com/callback
    ?state=s6Bh…Rkqt3
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    73
    認可リクエストで送ったstate

    View Slide

  74. 認可レスポンス
    302 Found
    Location: https://offers.example.com/callback
    ?state=s6Bh…Rkqt3
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    74
    認可コード

    View Slide

  75. 認可レスポンス
    302 Found
    Location: https://offers.example.com/callback
    ?state=s6Bh…Rkqt3
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    75
    スコープ

    View Slide

  76. 認可コードフロー
    76
    認可コードが
    クライアントに渡る

    View Slide

  77. 認可コードフロー
    77
    Step1
    ROの認証
    権限委譲の同意

    認可コードの発行

    View Slide

  78. 認可コードフロー
    78
    Step2
    クライアント認証

    アクセストークンの発行

    View Slide

  79. 認可コードフロー
    79
    アクセストークンの
    発行リクエスト

    View Slide

  80. 認可コードフロー
    80
    トークンリクエスト

    View Slide

  81. 認可コードフロー
    81
    トークンエンドポイント

    View Slide

  82. トークンリクエスト
    POST /token
    Host: www.googleapis.com
    Content-Type: application/x-www-form-urlencoded
    client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &client_secret=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uww
    &grant_type=authorization_code
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &redirect_uri=https://offers.example.com/callback
    82

    View Slide

  83. トークンリクエスト
    POST /token
    Host: www.googleapis.com
    Content-Type: application/x-www-form-urlencoded
    client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &client_secret=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uww
    &grant_type=authorization_code
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &redirect_uri=https://offers.example.com/callback
    83
    クライアントID

    View Slide

  84. トークンリクエスト
    POST /token
    Host: www.googleapis.com
    Content-Type: application/x-www-form-urlencoded
    client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &client_secret=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uww
    &grant_type=authorization_code
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &redirect_uri=https://offers.example.com/callback
    84
    クライアントシークレット

    View Slide

  85. トークンリクエスト
    POST /token
    Host: www.googleapis.com
    Content-Type: application/x-www-form-urlencoded
    client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &client_secret=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uww
    &grant_type=authorization_code
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &redirect_uri=https://offers.example.com/callback
    85
    認可コードグラント(フロー)

    View Slide

  86. トークンリクエスト
    POST /token
    Host: www.googleapis.com
    Content-Type: application/x-www-form-urlencoded
    client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &client_secret=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uww
    &grant_type=authorization_code
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &redirect_uri=https://offers.example.com/callback
    86
    認可コード

    View Slide

  87. トークンリクエスト
    POST /token
    Host: www.googleapis.com
    Content-Type: application/x-www-form-urlencoded
    client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &client_secret=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uww
    &grant_type=authorization_code
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &redirect_uri=https://offers.example.com/callback
    87
    リダイレクトURI

    View Slide

  88. 認可コードフロー
    88
    トークンリクエスト

    View Slide

  89. 認可コードフロー
    89
    アクセストークンの
    発行

    View Slide

  90. 認可コードフロー
    90
    トークンレスポンス

    View Slide

  91. トークンレスポンス
    {
    "access_token": "ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv",
    "expires_in": 3600,
    "scope": "https://www.googleapis.com/auth/photoslibrary.readonly",
    "token_type": "Bearer"
    }
    91

    View Slide

  92. トークンレスポンス
    {
    "access_token": "ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv",
    "expires_in": 3600,
    "scope": "https://www.googleapis.com/auth/photoslibrary.readonly",
    "token_type": "Bearer"
    }
    92
    アクセストークン

    View Slide

  93. トークンレスポンス
    {
    "access_token": "ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv",
    "expires_in": 3600,
    "scope": "https://www.googleapis.com/auth/photoslibrary.readonly",
    "token_type": "Bearer"
    }
    93
    有効期限[秒]

    View Slide

  94. トークンレスポンス
    {
    "access_token": "ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv",
    "expires_in": 3600,
    "scope": "https://www.googleapis.com/auth/photoslibrary.readonly",
    "token_type": "Bearer"
    }
    94
    スコープ

    View Slide

  95. トークンレスポンス
    {
    "access_token": "ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv",
    "expires_in": 3600,
    "scope": "https://www.googleapis.com/auth/photoslibrary.readonly",
    "token_type": "Bearer"
    }
    95
    ベアラートークンであ
    ることを示す

    View Slide

  96. 認可コードフロー
    96
    アクセストークン
    ゲット

    View Slide

  97. 認可コードフロー
    97
    Step1
    ROの認証
    権限委譲の同意
    認可コードの発行
    Step2
    クライアント認証
    アクセストークンの発行

    View Slide

  98. リソースサーバーへのアクセス
    98

    View Slide

  99. リソースサーバーへのアクセス
    99
    ヘッダーにアクセストーク
    ンをセットして
    APIにアクセス

    View Slide

  100. リソースサーバーへのアクセス
    GET /v1/albums
    Host: photoslibrary.googleapis.com
    Authorization: Bearer ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv
    100

    View Slide

  101. リソースサーバーへのアクセス
    GET /v1/albums
    Host: photoslibrary.googleapis.com
    Authorization: Bearer ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv
    101
    Authorizationヘッダー

    View Slide

  102. リソースサーバーへのアクセス
    GET /v1/albums
    Host: photoslibrary.googleapis.com
    Authorization: Bearer ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv
    102
    文字列「Bearer」

    View Slide

  103. リソースサーバーへのアクセス
    GET /v1/albums
    Host: photoslibrary.googleapis.com
    Authorization: Bearer ya29.GlscB0j4x.....DsR9iOiU-BfZjTXWUJ7olv
    103
    アクセストークン

    View Slide

  104. リソースサーバーへのアクセス
    104
    画像のダウンロード

    View Slide

  105. OAuthでログイン?
    105

    View Slide

  106. ところで
    OAuthって「ソーシャルログイン」でつかわれてるんじゃないの?
    106

    View Slide

  107. OAuth 認可コードフロー ふりかえり
    107

    View Slide

  108. 認可コードフロー
    108
    ここでGoogle アカウントで認
    証してるよね?

    View Slide

  109. OAuth 認可コードフロー ふりかえり
    109
    アクセスするリソース(画像)のオー
    ナーは誰かを確認

    View Slide

  110. OAuth 認可コードフロー ふりかえり
    110
    アクセスするリソース(画像)のオー
    ナーは誰かを確認
    アプリにログインさせるための
    認証をおこなっているわけではない

    View Slide

  111. OAuth 認可コードフロー ふりかえり
    111
    そもそもここで
    アプリにはログイン状態

    View Slide

  112. OAuthとアプリへのログインの関係
    ● OAuthと「アプリへのログイン」は関係ない
    ● が、SNSのリソース(SNSユーザーのプロフィール情報)を利用して、次の
    ようなことが行われていた時代がある(今もある?)
    112

    View Slide

  113. SNSの例 | 登場人物
    113
    ほげアプリ
    (クライアント)
    認可サーバー
    プロフィール API
    (リソースサーバー)
    Aさん
    (リソースオーナー)

    View Slide

  114. SNSの例 | 登場人物
    114
    ほげアプリ
    (クライアント)
    認可サーバー
    プロフィール API
    (リソースサーバー)
    SNSのユーザー
    ほげアプリのユーザー
    Aさん
    (リソースオーナー)
    「SNS アカウントでログ
    イン」機能
    SNS ユーザーの
    プロフィール情報を
    提供するAPI

    View Slide

  115. SNSの例
    115

    View Slide

  116. SNSの例
    116
    SNS アカウントで
    ログイン

    View Slide

  117. SNSの例
    117
    OAuth

    View Slide

  118. SNSの例
    118
    OAuth
    Aさんのプロフィール情報にア
    クセスするための
    アクセストークン

    View Slide

  119. SNSの例
    119
    OAuth
    プロフィール情報の
    リクエスト

    View Slide

  120. SNSの例
    120
    OAuth
    Aさんの
    プロフィール情報の

    View Slide

  121. SNSの例
    121
    OAuth
    Aさんのプロフィール情報
    からユーザー識別子を確認してロ
    グイン完了

    View Slide

  122. この実装には脆弱性がある
    ● アクセストークンを差し替えられると、ほげアプリも
    SNSサービスもそれに気づけない
    ● アクセストークンには差し替えに気づく仕組みがない
    122

    View Slide

  123. SNSの例
    123
    OAuth
    Bさんのアクセストークン
    に差し替えられた
    Bさんとしてログイン
    Aさん

    View Slide

  124. この実装には脆弱性がある
    ● アクセストークンを差し替えられると、ほげアプリも
    SNSサービスもそれに気づけない
    ● アクセストークンには差し替えに気づく仕組みがない
    124
    OpenID Connectを使いましょう

    View Slide

  125. OpenID Connectとは
    125

    View Slide

  126. 登場人物
    ● OAuthとOpenID Connectでは登場人物の呼び名が異なります
    126
    OAuth リソースオーナー
    OIDC エンドユーザー
    OAuth クライアント
    OIDC リライング・パーティ
    OAuth 認可サーバー
    OIDC IDプロバイダ
    OAuth リソースサーバー
    OIDC (User Info API)

    View Slide

  127. OpenID Connectとは
    何をやっている?
    ● ユーザー認証を外部サービス(IDプロバイダ)におまかせし、アプリはID
    トークンを受け取って、IDプロバイダによる認証内容を確認する
    何に使う?
    ● ソーシャルログイン
    仕組みは?
    ● OAuthを拡張したプロトコル
    127
    OpenID Connect = OAuth + ID トークン + UserInfo API

    View Slide

  128. OpenID Connectとは
    何をやっている?
    ● ユーザー認証を外部サービス(IDプロバイダ)におまかせし、アプリはID
    トークンを受け取って、IDプロバイダによる認証内容を確認する
    何に使う?
    ● ソーシャルログイン
    仕組みは?
    ● OAuthを拡張したプロトコル
    128
    OpenID Connect = OAuth + ID トークン + UserInfo API
    プロフィールAPIの
    形式を規定

    View Slide

  129. OpenID Connectとは
    何をやっている?
    ● ユーザー認証を外部サービス(IDプロバイダ)におまかせし、アプリはID
    トークンを受け取って、IDプロバイダによる認証内容を確認する
    何に使う?
    ● ソーシャルログイン
    仕組みは?
    ● OAuthを拡張したプロトコル
    129
    OpenID Connect = OAuth + ID トークン + UserInfo API
    IDトークンを理解
    =
    OIDCを理解

    View Slide

  130. IDトークンとは
    誰が発行する?
    ● IDプロバイダ
    誰が何のために使うのか?
    ● リライング・パーティがエンドユーザーを認証するため
    どんな情報が含まれているか
    ● ユーザーID
    ● トークンの有効性(有効期限、発行日時)
    ● トークン発行者ID、トークン受領者ID
    ● 改ざんを防ぐための署名
    ● トークンのフォーマットに関する情報
    130

    View Slide

  131. IDトークンとは
    形式は?
    ● Json Web Token(JWT)
    ● .(ドット)で区切られる3つのパートからなる
    ● ヘッダーとペイロードはBase64エンコードされたJSON
    eyJhbGci…QifQ. eyJpc3M…I6MTU2MzH0.Bx9Eds2f…CeekBuYokY
    Bx9Edsrn2f3・・・・・・CeekBuYokYnxt4A3XRSSfcpvg
    131
    ヘッダー ペイロード 署名

    View Slide

  132. IDトークン | ヘッダー
    {
    "typ": "JWT",
    "alg": "RS256",
    }
    132

    View Slide

  133. IDトークン | ヘッダー
    {
    "typ": "JWT",
    "alg": "RS256",
    }
    133
    署名アルゴリズム

    View Slide

  134. IDトークン | ペイロード
    {
    "iss": "https://accounts.google.com",
    "aud": "6727653....ibqog5.apps.googleusercontent.com",
    "sub": "103567684956724214211",
    "iat": 1563792930,
    "exp": 1563796530,
    }
    134

    View Slide

  135. IDトークン | ペイロード
    {
    "iss": "https://accounts.google.com",
    "aud": "6727653....ibqog5.apps.googleusercontent.com",
    "sub": "103567684956724214211",
    "iat": 1563792930,
    "exp": 1563796530,
    }
    135
    Issuer: 発行者

    View Slide

  136. IDトークン | ペイロード
    {
    "iss": "https://accounts.google.com",
    "aud": "6727653....ibqog5.apps.googleusercontent.com",
    "sub": "103567684956724214211",
    "iat": 1563792930,
    "exp": 1563796530,
    }
    136
    Audience:
    IDトークンを受け取るリライング・パー
    ティのクライアントID

    View Slide

  137. IDトークン | ペイロード
    {
    "iss": "https://accounts.google.com",
    "aud": "6727653....ibqog5.apps.googleusercontent.com",
    "sub": "103567684956724214211",
    "iat": 1563792930,
    "exp": 1563796530,
    }
    137
    Subject:
    エンドユーザーの識別子

    View Slide

  138. IDトークン | ペイロード
    {
    "iss": "https://accounts.google.com",
    "aud": "6727653....ibqog5.apps.googleusercontent.com",
    "sub": "103567684956724214211",
    "iat": 1563792930,
    "exp": 1563796530,
    }
    138
    Issue at :
    JWTの発行時間(UNIX time)

    View Slide

  139. IDトークン | ペイロード
    {
    "iss": "https://accounts.google.com",
    "aud": "6727653....ibqog5.apps.googleusercontent.com",
    "sub": "103567684956724214211",
    "iat": 1563792930,
    "exp": 1563796530,
    }
    139
    Expiration time :
    有効期限(UNIX time)

    View Slide

  140. IDトークン | ペイロード
    {
    "iss": "https://accounts.google.com",
    "aud": "6727653....ibqog5.apps.googleusercontent.com",
    "sub": "103567684956724214211",
    "iat": 1563792930,
    "exp": 1563796530,
    "email": "[email protected]"
    "name": "Auth屋",
    "given_name": "屋",
    "family_name": "Auth"
    }
    140
    scope(email profile)を
    追加すると、対応して情報が増える

    View Slide

  141. IDトークン | 署名
    なぜ署名が必要?
    ● sub(ユーザー識別子)、iss(発行者)、aud(発行先)などが改ざんされ
    ていないことを保証
    署名アルゴリズムは?
    ● ヘッダーに記載(RS256)
    署名検証用の公開鍵は?
    ● IDプロバイダが公開
    ● https://www.googleapis.com/oauth2/v3/certs
    Bx9Edsrn2f3・・・・・・CeekBuYokYnxt4A3XRSSfcpvg
    141

    View Slide

  142. OIDC 認可コードフロー
    142

    View Slide

  143. OIDC 認可コードフロー
    143
    SNSアカウントで
    ログイン

    View Slide

  144. OIDC 認可コードフロー
    144
    認証リクエスト

    View Slide

  145. OIDC 認可コードフロー
    145
    scope = openid

    View Slide

  146. OIDC 認可コードフロー
    146
    scope = openid email profile

    View Slide

  147. OIDC 認可コードフロー
    147
    アクセストークン
    IDトークン

    View Slide

  148. OIDC 認可コードフロー
    148
    IDトークンのsub
    を確認して
    ログイン完了

    View Slide

  149. ログイン時以外のタイミングで取得する場合
    149
    プロフィール情報の
    リクエスト
    UserInfo API

    View Slide

  150. ログイン時以外のタイミングで取得する場合
    150
    プロフィール情報
    UserInfo API

    View Slide

  151. OIDC 認可コードフロー
    151
    IDトークンのsub
    を確認して
    ログイン完了

    View Slide

  152. IDトークン | ペイロード
    {
    "iss": "https://accounts.google.com", ← 発行者
    "aud": "6727653....ibqog5.apps.googleusercontent.com", ← 受領者
    "sub": "103567684956724214211", ← ユーザーID
    "iat": 1563792930, ← 発行日時
    "exp": 1563796530, ← 有効期限
    }
    入れ替えられても、気付ける仕組みがある
    署名により改ざんも気付ける
    152

    View Slide

  153. 説明していないこと
    ● パブリッククライアントのフロー
    ● PKCE
    ● リフレッシュトークン
    ● 攻撃と対策(state、nonce、etc.)
    ● 他のフロー
    ● etc.
    153

    View Slide

  154. 宣伝 | 同人誌
    Boothで販売中
    https://authya.booth.pm /
    雰囲気OAuth本 OIDC本 攻撃本
    154

    View Slide

  155. RFC6749 (OAuth2.0の基本仕様)
    OAuthでは, クライアントは, リソースオーナーのコント
    ロール下にありリソースサーバーによってホストされている
    リソースへのアクセス権を要求する. そしてリソースオー
    ナーのクレデンシャルそのものとは別のクレデンシャルを取
    得する.
    155
    引用元: OpenID ファウンデーション・ジャパン による日本語訳
    http://openid-foundation-japan.github.io/rfc6749.ja.html

    View Slide

  156. RFC6749 (OAuth2.0の基本仕様)
    保護されたリソースにアクセスする為にリソースオーナーの
    クレデンシャルを使う代わりに, クライアントはアクセス
    トークンを取得する. アクセストークンとは, ある特定のス
    コープ, 期間およびその他のアクセス権に関する情報を示す
    文字列である. アクセストークンはリソースオーナーの同意
    をもって認可サーバーからサードパーティークライアントへ
    発行される. クライアントはアクセストークンを用いてリ
    ソースサーバーがホストしている保護されたリソースにアク
    セスする.
    156

    View Slide

  157. デモ
    157

    View Slide

  158. Google の トークンを取得
    ● Google からアクセストークンとIDトークンを取得します
    ● 雰囲気OAuth本に乗せている方法
    ○ 認可・認証リクエストをブラウザで実施
    ○ トークンリクエストをcurlコマンドで実施
    158

    View Slide

  159. 認可コードフロー(OIDC)
    159
    認証リクエスト(OIDC)

    View Slide

  160. 認可コードフロー
    160
    認可エンドポイント
    https://accounts.google.com/o/oauth2/v2/auth

    View Slide

  161. 認証リクエスト
    GET /o/oauth2/v2/auth
    ?client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &response_type=code
    &scope=openid
    &redirect_uri=http://localhost/callback
    &state=xyz
    161

    View Slide

  162. 認可コードフロー
    162
    リソースオーナーの認証
    権限委譲の同意

    View Slide

  163. 認可コードフロー
    163
    リダイレクトURLに
    認可コードを渡す
    http://localhost/callback

    View Slide

  164. 認可コードフロー
    164
    トークンリクエスト

    View Slide

  165. 認可コードフロー
    165
    トークンエンドポイント
    https://www.googleapis.com/oauth2/v4/token

    View Slide

  166. トークンリクエスト
    POST /oauth2/v4/token
    Host: www.googleapis.com
    Content-Type: application/x-www-form-urlencoded
    client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &client_secret=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uww
    &grant_type=authorization_code
    &code=4%2FZQHK-DEk0Jfp4drQ-3iZ4fwFYf48vyaOf.....
    &redirect_uri=http://localhost/callback
    166

    View Slide

  167. 認可リクエスト(Google Photo)
    GET /authorize
    ?response_type=code
    &client_id=7429476…bje196p9pvugi1av19.apps.googleusercontent.com
    &state=s6Bh…Rkqt3
    &redirect_uri=http://localhost/callback
    &scope=https://www.googleapis.com/auth/photoslibrary.readonly
    167

    View Slide