このドキュメントでは、JavaScript ウェブ アプリケーションから Google API にアクセスするための OAuth 2.0 認証を実装する方法について説明します。OAuth 2.0 を使用すると、ユーザー名やパスワードなどの情報を秘密にしたまま、ユーザーが特定のデータをアプリケーションと共有できます。 たとえば、OAuth 2.0 を使用して、ユーザーの Google ドライブにファイルを保存する権限をアプリケーションで取得できます。
この OAuth 2.0 フローは暗黙的な権限付与フローと呼ばれます。これは、ユーザーがアプリを開いている間だけ API にアクセスするアプリ向けに設計されています。このようなアプリケーションでは、機密情報を保存することはできません。
このフローでは、アプリが Google URL を開きます。この URL では、クエリ パラメータを使用して、アプリとアプリが必要とする API アクセスのタイプを識別します。URL は、現在のブラウザ ウィンドウまたはポップアップで開くことができます。ユーザーは Google で認証を行い、リクエストされた権限を付与できます。その後、ユーザーをアプリにリダイレクトします。リダイレクトにはアクセス トークンが含まれます。アプリはこのトークンを確認し、API リクエストに使用します。
Google API クライアント ライブラリと Google Identity Services
JavaScript 用の Google API クライアント ライブラリを使用して Google に対して承認済みの呼び出しを行う場合は、 Google Identity Services JavaScript ライブラリを使用して OAuth 2.0 フローを処理する必要があります。Google ID サービスのトークンモデルをご覧ください。これは、OAuth 2.0 の暗黙的な権限付与フローに基づいています。
前提条件
プロジェクトでAPI を有効にする
Google API を呼び出すすべてのアプリケーションは、 API Consoleでこれらの API を有効にする必要があります。
プロジェクトで API を有効にするには:
- Google API Console内のOpen the API Library 。
- If prompted, select a project, or create a new one.
- API Library には、利用可能なすべての API がプロダクト ファミリーと人気別にグループ化されてリストされます。有効にする API がリストに表示されない場合は、検索を使用して探すか、その API が属するプロダクト ファミリーの [すべて表示] をクリックします。
- 有効にする API を選択し、[有効にする] ボタンをクリックします。
- If prompted, enable billing.
- If prompted, read and accept the API's Terms of Service.
承認認証情報を作成する
OAuth 2.0 を使用して Google API にアクセスするアプリケーションには、Google の OAuth 2.0 サーバーでそのアプリケーションを識別する認証情報が必要です。次の手順では、プロジェクトの認証情報を作成する方法について説明します。これにより、アプリケーションはこの認証情報を使用して、そのプロジェクトで有効にした API にアクセスできるようになります。
- Go to the Credentials page.
- [認証情報を作成] > [OAuth クライアント ID] をクリックします。
- アプリケーションの種類として [ウェブ アプリケーション] を選択します。
- フォームに入力します。JavaScript を使用して承認済みの Google API リクエストを送信するアプリケーションでは、承認済みの JavaScript オリジンを指定する必要があります。オリジンは、アプリケーションが OAuth 2.0 サーバーにリクエストを送信できるドメインを識別します。これらのオリジンは、Google の検証ルールに準拠している必要があります。
アクセス スコープを特定する
スコープを使用すると、アプリケーションに必要なリソースへのアクセスのみをリクエストできます。また、ユーザーはアプリケーションに付与するアクセス権の範囲を制御できます。そのため、リクエストするスコープの数とユーザーの同意を得る可能性には逆相関関係がある場合があります。
OAuth 2.0 認証の実装を開始する前に、アプリがアクセス権限を必要とするスコープを特定することをおすすめします。
OAuth 2.0 API スコープのドキュメントには、Google API へのアクセスに使用できるスコープの一覧が記載されています。
OAuth 2.0 アクセス トークンの取得
以下の手順は、アプリケーションが Google の OAuth 2.0 サーバーとやり取りし、ユーザーの代わりに API リクエストを実行することについてユーザーの同意を取得する方法を示しています。アプリケーションでユーザーの認証を必要とする Google API リクエストを実行するには、まずそのアプリケーションでユーザーの同意を得る必要があります。
ステップ 1: Google の OAuth 2.0 サーバーにリダイレクトする
ユーザーのデータにアクセスする権限をリクエストするには、ユーザーを Google の OAuth 2.0 サーバーにリダイレクトします。
OAuth 2.0 エンドポイント
Google の OAuth 2.0 エンドポイント(https://accounts.google.com/o/oauth2/v2/auth
)からアクセスをリクエストするための URL を生成します。このエンドポイントには HTTPS でアクセスできます。プレーン HTTP 接続は拒否されます。
Google 認可サーバーは、ウェブサーバー アプリケーション用に次のクエリ文字列パラメータをサポートしています。
パラメータ | |||||||
---|---|---|---|---|---|---|---|
client_id |
必須
アプリケーションのクライアント ID。この値は API Console Credentials pageで確認できます。 |
||||||
redirect_uri |
必須
ユーザーが認可フローを完了した後、API サーバーがユーザーをリダイレクトする場所を指定します。この値は、クライアントの API Console
Credentials pageで構成した、OAuth 2.0 クライアント用に承認されたリダイレクト URI のいずれかと完全に一致する必要があります。この値が、指定された
|
||||||
response_type |
必須
JavaScript アプリケーションでは、このパラメータの値を |
||||||
scope |
必須
ユーザーの代わりにアプリケーションがアクセスできるリソースを指定するスコープをスペースで区切ったリスト。これらの値は、Google がユーザーに表示する同意画面に影響します。 スコープを使用すると、アプリケーションに必要なリソースへのアクセスのみをリクエストできます。また、ユーザーはアプリケーションに付与するアクセス権の範囲を制御できます。したがって、リクエストするスコープの数とユーザーの同意を得る可能性には逆相関があります。 可能な限り、コンテキスト内で認可スコープへのアクセスをアプリケーションはリクエストすることをおすすめします。状況に応じてユーザーデータへのアクセスをリクエストする場合は、段階的な認証を介して、アプリケーションがアクセスを必要とする理由をユーザーが簡単に理解できるようにします。 |
||||||
state |
推奨
アプリケーションが認可リクエストと認可サーバーのレスポンスの間で状態を維持するために使用する任意の文字列値を指定します。ユーザーがアプリケーションのアクセス リクエストに同意するか拒否すると、サーバーは、 このパラメータは、ユーザーをアプリ内の適切なリソースに誘導する、ノンスを送信する、クロスサイト リクエスト フォージェリを抑制するなど、さまざまな目的で使用できます。 |
||||||
include_granted_scopes |
省略可
アプリケーションは、増分承認を使用して、状況に応じて追加のスコープへのアクセスをリクエストできます。このパラメータの値を |
||||||
enable_granular_consent |
省略可
デフォルトは |
||||||
login_hint |
省略可
認証しようとしているユーザーをアプリケーションが認識している場合は、このパラメータを使用して、Google 認証サーバーにヒントを提供できます。サーバーはヒントを使用してログインフローを簡素化します。ログイン フォームのメール欄に事前入力するか、適切なマルチログイン セッションを選択します。 パラメータ値をメールアドレスまたは |
||||||
prompt |
省略可
ユーザーに表示するプロンプトをスペースで区切ったリスト(大文字と小文字を区別)。このパラメータを指定しない場合、プロジェクトが初めてアクセスをリクエストしたときにのみ、ユーザーにメッセージが表示されます。詳しくは、 再同意を求めるをご覧ください。 指定できる値は次のとおりです。
|
Google の承認サーバーへのリダイレクトの例
次に、URL の例を示します。読みやすくするために改行とスペースを入れています。
https://accounts.google.com/o/oauth2/v2/auth? scope=https%3A//www.googleapis.com/auth/drive.metadata.readonly& include_granted_scopes=true& response_type=token& state=state_parameter_passthrough_value& redirect_uri=https%3A//oauth2.example.com/code& client_id=client_id
リクエスト URL を作成したら、その URL にユーザーをリダイレクトします。
JavaScript サンプルコード
次の JavaScript スニペットは、JavaScript 用の Google API クライアント ライブラリを使用せずに、JavaScript で認証フローを開始する方法を示しています。この OAuth 2.0 エンドポイントはクロスオリジン リソース シェアリング(CORS)をサポートしていないため、スニペットはそのエンドポイントへのリクエストを開くフォームを作成します。
/* * Create form to request access token from Google's OAuth 2.0 server. */ function oauthSignIn() { // Google's OAuth 2.0 endpoint for requesting an access token var oauth2Endpoint = 'https://accounts.google.com/o/oauth2/v2/auth'; // Create <form> element to submit parameters to OAuth 2.0 endpoint. var form = document.createElement('form'); form.setAttribute('method', 'GET'); // Send as a GET request. form.setAttribute('action', oauth2Endpoint); // Parameters to pass to OAuth 2.0 endpoint. var params = {'client_id': 'YOUR_CLIENT_ID', 'redirect_uri': 'YOUR_REDIRECT_URI', 'response_type': 'token', 'scope': 'https://www.googleapis.com/auth/drive.metadata.readonly', 'include_granted_scopes': 'true', 'state': 'pass-through value'}; // Add form parameters as hidden input values. for (var p in params) { var input = document.createElement('input'); input.setAttribute('type', 'hidden'); input.setAttribute('name', p); input.setAttribute('value', params[p]); form.appendChild(input); } // Add form to page and submit it to open the OAuth 2.0 endpoint. document.body.appendChild(form); form.submit(); }
ステップ 2: Google がユーザーに同意を求める
このステップでは、ユーザーは、リクエストされたアクセス権をアプリケーションに付与するかどうかを決定します。この段階では、同意ウィンドウが表示され、アプリケーションの名前と、ユーザーの認証情報を使用してアクセス権をリクエストしている Google API サービスの名前、付与されるアクセス スコープの概要が表示されます。ユーザーは、アプリケーションによってリクエストされた 1 つ以上のスコープへのアクセスを許可することに同意することも、リクエストを拒否することもできます。
アプリケーションは、アクセスが許可されたかどうかを示す Google の OAuth 2.0 サーバーからのレスポンスを待つため、この段階では何もする必要はありません。このレスポンスについては、次の手順で説明します。
エラー
Google の OAuth 2.0 認可エンドポイントへのリクエストでは、想定される認証と認可フローではなく、ユーザー向けのエラー メッセージが表示されることがあります。一般的なエラーコードと推奨される解決策を以下に示します。
admin_policy_enforced
Google アカウントは、Google Workspace 管理者のポリシーにより、リクエストされた 1 つ以上のスコープを承認できません。OAuth クライアント ID に明示的にアクセス権が付与されるまで、管理者がすべてのスコープ、または機密性の高いスコープと制限付きスコープに対するアクセスを制限する方法については、Google Workspace 管理者のヘルプ記事 Google Workspace のデータにアクセスできるサードパーティ製アプリと内部アプリを制御するをご覧ください。
disallowed_useragent
認可エンドポイントは、Google の OAuth 2.0 ポリシーで許可されていない埋め込みユーザー エージェント内に表示されています。
Android
Android デベロッパーが android.webkit.WebView
で承認リクエストを開始したときに、このエラー メッセージが表示されることがあります。デベロッパーは、代わりに Android 用 Google ログインや OpenID Foundation の Android 用 AppAuth などの Android ライブラリを使用する必要があります。
このエラーは、Android アプリが埋め込みユーザー エージェントで一般的なウェブリンクを開き、ユーザーがサイトから Google の OAuth 2.0 認可エンドポイントに移動したときに、このエラーが発生することがあります。デベロッパーは、オペレーティング システムのデフォルトのリンクハンドラ(Android アプリリンク ハンドラとデフォルトのブラウザアプリの両方を含む)で一般的なリンクを開くことを許可する必要があります。Android カスタムタブ ライブラリもサポートされているオプションです。
iOS
iOS と macOS のデベロッパーは、WKWebView
で承認リクエストを開くときに、このエラーが発生することがあります。デベロッパーは、代わりに iOS 用の Google ログインや OpenID Foundation の iOS 用 AppAuth などの iOS ライブラリを使用する必要があります。
このエラーは、iOS または macOS アプリが埋め込みユーザー エージェントで一般的なウェブリンクを開き、ユーザーがサイトから Google の OAuth 2.0 認可エンドポイントに移動したときに発生することがあります。デベロッパーは、オペレーティング システムのデフォルト リンクハンドラ(ユニバーサル リンク ハンドラとデフォルトのブラウザアプリの両方を含む)で一般的なリンクを開くことを許可する必要があります。SFSafariViewController
ライブラリもサポートされているオプションです。
org_internal
リクエストの OAuth クライアント ID は、特定の Google Cloud 組織内の Google アカウントへのアクセスを制限するプロジェクトの一部です。この構成オプションの詳細については、ヘルプ記事の「OAuth 同意画面を設定する」のユーザータイプのセクションをご覧ください。
invalid_client
リクエストの送信元が、このクライアントに対して承認されていません。origin_mismatch
をご覧ください。
invalid_grant
増分承認を使用しているときに、トークンが期限切れか無効になった可能性があります。 ユーザーを再度認証し、新しいトークンの取得についてユーザーの同意を求めます。このエラーが引き続き表示される場合は、アプリケーションが正しく構成され、リクエストで正しいトークンとパラメータを使用していることを確認してください。それ以外の場合は、ユーザー アカウントが削除されたか無効になっている可能性があります。
origin_mismatch
認証リクエストを発信した JavaScript のスキーム、ドメイン、ポートが、OAuth クライアント ID に登録されている承認済みの JavaScript オリジン URI と一致しない場合があります。 Credentials pageで承認済みの JavaScript 生成元を Google API Console確認します。
redirect_uri_mismatch
認証リクエストで渡された redirect_uri
が、OAuth クライアント ID の承認済みのリダイレクト URI と一致しません。 Google API Console Credentials pageで承認済みのリダイレクト URI を確認します。
認証リクエストを発信した JavaScript のスキーム、ドメイン、ポートが、OAuth クライアント ID に登録されている承認済みの JavaScript オリジン URI と一致しない場合があります。 Google API Console Credentials pageで承認済みの JavaScript 生成元を確認します。
redirect_uri
パラメータは、サポートが終了してサポートが終了した OAuth 帯域外(OOB)フローを参照している可能性があります。統合を更新するには、移行ガイドをご覧ください。
invalid_request
リクエストに何か問題がありました。これにはさまざまな理由が考えられます。
- リクエストの形式が正しくありません
- リクエストに必須パラメータがありません
- リクエストに、Google でサポートされていない認証方法が使用されている。OAuth 統合で推奨される統合方法が使用されていることを確認する
ステップ 3: OAuth 2.0 サーバー レスポンスを処理する
OAuth 2.0 エンドポイント
OAuth 2.0 サーバーは、アクセス トークン リクエストで指定された redirect_uri
にレスポンスを送信します。
ユーザーがリクエストを承認すると、レスポンスにアクセス トークンが含まれます。ユーザーがリクエストを承認しないと、レスポンスにエラー メッセージが格納されます。以下に示すように、アクセス トークンまたはエラー メッセージがリダイレクト URI のハッシュ フラグメントで返されます。
アクセス トークンのレスポンス:
https://oauth2.example.com/callback#access_token=4/P7q7W91&token_type=Bearer&expires_in=3600
access_token
パラメータに加えて、フラグメント文字列には、常にBearer
に設定されるtoken_type
パラメータと、トークンの存続期間を秒単位で指定するexpires_in
パラメータも含まれます。state
パラメータがアクセス トークン リクエストで指定された場合、その値もレスポンスに含まれます。- エラー レスポンス:
https://oauth2.example.com/callback#error=access_denied
OAuth 2.0 サーバー レスポンスの例
このフローをテストするには、次のサンプル URL をクリックします。これは、Google ドライブ内のファイルのメタデータを表示するための読み取り専用アクセスをリクエストします。
https://accounts.google.com/o/oauth2/v2/auth? scope=https%3A//www.googleapis.com/auth/drive.metadata.readonly& include_granted_scopes=true& response_type=token& state=state_parameter_passthrough_value& redirect_uri=https%3A//oauth2.example.com/code& client_id=client_id
OAuth 2.0 のフローが完了すると、http://localhost/oauth2callback
にリダイレクトされます。この URL は、ローカルマシンがそのアドレスでファイルを提供しない限り、404 NOT FOUND
エラーを返します。次のステップでは、ユーザーがアプリケーションにリダイレクトされたときに URI で返される情報の詳細を提供します。
Google API の呼び出し
OAuth 2.0 エンドポイント
アプリケーションがアクセス トークンを取得した後、API で必要なアクセスの範囲が付与されていれば、そのトークンを使用して特定のユーザー アカウントに代わって Google API を呼び出すことができます。これを行うには、access_token
クエリ パラメータまたは Authorization
HTTP ヘッダーの Bearer
値のいずれかを含めることで、API へのリクエストにアクセス トークンを含めます。クエリ文字列はサーバーログで確認されやすいため、可能であれば HTTP ヘッダーを使用することをおすすめします。ほとんどの場合、Drive Files API を呼び出す場合などに、クライアント ライブラリを使用して Google API の呼び出しをセットアップできます。
OAuth 2.0 Playground では、すべての Google API を試し、スコープを確認できます。
HTTP GET の例
Authorization: Bearer
HTTP ヘッダーを使用した
drive.files
エンドポイント(Drive Files API)の呼び出しは次のようになります。独自のアクセス トークンを指定する必要があります。
GET /drive/v2/files HTTP/1.1 Host: www.googleapis.com Authorization: Bearer access_token
次に、認証されたユーザーが access_token
クエリ文字列パラメータを使用して同じ API を呼び出します。
GET https://www.googleapis.com/drive/v2/files?access_token=access_token
curl
の例
これらのコマンドは、curl
コマンドライン アプリケーションを使用してテストできます。HTTP ヘッダー オプションを使用する例を次に示します(推奨)。
curl -H "Authorization: Bearer access_token" https://www.googleapis.com/drive/v2/files
または、クエリ文字列パラメータ オプションを使用します。
curl https://www.googleapis.com/drive/v2/files?access_token=access_token
JavaScript サンプルコード
以下のコード スニペットは、CORS(クロスオリジン リソース シェアリング)を使用して Google API にリクエストを送信する方法を示しています。この例では、JavaScript 用の Google API クライアント ライブラリを使用しません。ただし、クライアント ライブラリを使用していない場合でも、そのライブラリのドキュメントにある CORS サポートのガイドが、これらのリクエストに関する理解を深めるのに役立ちます。
このコード スニペットでは、access_token
変数は、認可されたユーザーに代わって API リクエストを行うために取得したトークンを表します。完全なサンプルは、そのトークンをブラウザのローカル ストレージに格納し、API リクエストを行うときにトークンを取得する方法を示しています。
var xhr = new XMLHttpRequest(); xhr.open('GET', 'https://www.googleapis.com/drive/v3/about?fields=user&' + 'access_token=' + params['access_token']); xhr.onreadystatechange = function (e) { console.log(xhr.response); }; xhr.send(null);
完全なサンプルコード
OAuth 2.0 エンドポイント
このコードサンプルは、JavaScript 用の Google API クライアント ライブラリを使用せずに、JavaScript で OAuth 2.0 フローを完了する方法を示しています。このコードは、API リクエストを試すボタンを表示する HTML ページ用です。このボタンをクリックすると、API アクセス トークンがブラウザのローカル ストレージに保存されているかどうかがコードによってチェックされます。リクエストした場合は API リクエストを実行します。それ以外の場合は、OAuth 2.0 フローが開始されます。
OAuth 2.0 フローの場合、このページは次の手順を実行します。
- これにより、ユーザーは Google の OAuth 2.0 サーバーにリダイレクトされます。このサーバーは
https://www.googleapis.com/auth/drive.metadata.readonly
スコープへのアクセスをリクエストします。 - リクエストされた 1 つ以上のスコープへのアクセスを許可(または拒否)すると、ユーザーは元のページにリダイレクトされます。そのページで、フラグメント識別子文字列のアクセス トークンが解析されます。
アクセス トークンを使用してサンプル API リクエストを作成します。
API リクエストは、Drive API の
about.get
メソッドを呼び出して、承認済みユーザーの Google ドライブ アカウントに関する情報を取得します。- リクエストが正常に実行されると、API レスポンスがブラウザのデバッグ コンソールに記録されます。
Google アカウントの [権限] ページで、アプリへのアクセス権を取り消すことができます。アプリは OAuth 2.0 Demo for Google API Docs として表示されます。
このコードをローカルで実行するには、認可認証情報に対応する YOUR_CLIENT_ID
変数と YOUR_REDIRECT_URI
変数の値を設定する必要があります。YOUR_REDIRECT_URI
変数は、ページが提供されるのと同じ URL に設定する必要があります。この値は、 API Console Credentials pageで構成した OAuth 2.0 クライアント用に承認済みのリダイレクト URI のいずれかと完全に一致している必要があります。この値が承認済みの URI と一致しない場合、redirect_uri_mismatch
エラーが発生します。また、プロジェクトでこのリクエストに対して適切な API を有効にする必要があります。
<html><head></head><body> <script> var YOUR_CLIENT_ID = 'REPLACE_THIS_VALUE'; var YOUR_REDIRECT_URI = 'REPLACE_THIS_VALUE'; var fragmentString = location.hash.substring(1); // Parse query string to see if page request is coming from OAuth 2.0 server. var params = {}; var regex = /([^&=]+)=([^&]*)/g, m; while (m = regex.exec(fragmentString)) { params[decodeURIComponent(m[1])] = decodeURIComponent(m[2]); } if (Object.keys(params).length > 0) { localStorage.setItem('oauth2-test-params', JSON.stringify(params) ); if (params['state'] && params['state'] == 'try_sample_request') { trySampleRequest(); } } // If there's an access token, try an API request. // Otherwise, start OAuth 2.0 flow. function trySampleRequest() { var params = JSON.parse(localStorage.getItem('oauth2-test-params')); if (params && params['access_token']) { var xhr = new XMLHttpRequest(); xhr.open('GET', 'https://www.googleapis.com/drive/v3/about?fields=user&' + 'access_token=' + params['access_token']); xhr.onreadystatechange = function (e) { if (xhr.readyState === 4 && xhr.status === 200) { console.log(xhr.response); } else if (xhr.readyState === 4 && xhr.status === 401) { // Token invalid, so prompt for user permission. oauth2SignIn(); } }; xhr.send(null); } else { oauth2SignIn(); } } /* * Create form to request access token from Google's OAuth 2.0 server. */ function oauth2SignIn() { // Google's OAuth 2.0 endpoint for requesting an access token var oauth2Endpoint = 'https://accounts.google.com/o/oauth2/v2/auth'; // Create element to open OAuth 2.0 endpoint in new window. var form = document.createElement('form'); form.setAttribute('method', 'GET'); // Send as a GET request. form.setAttribute('action', oauth2Endpoint); // Parameters to pass to OAuth 2.0 endpoint. var params = {'client_id': YOUR_CLIENT_ID, 'redirect_uri': YOUR_REDIRECT_URI, 'scope': 'https://www.googleapis.com/auth/drive.metadata.readonly', 'state': 'try_sample_request', 'include_granted_scopes': 'true', 'response_type': 'token'}; // Add form parameters as hidden input values. for (var p in params) { var input = document.createElement('input'); input.setAttribute('type', 'hidden'); input.setAttribute('name', p); input.setAttribute('value', params[p]); form.appendChild(input); } // Add form to page and submit it to open the OAuth 2.0 endpoint. document.body.appendChild(form); form.submit(); } </script> <button onclick="trySampleRequest();">Try sample request</button> </body></html>
JavaScript 送信元の検証ルール
Google では、デベロッパーがアプリケーションの安全性を維持できるように、JavaScript のオリジンに次の検証ルールを適用しています。JavaScript のオリジンは、以下のルールに準拠している必要があります。後述のドメイン、ホスト、スキームの定義については、RFC 3986 のセクション 3 をご覧ください。
検証ルール | |
---|---|
スキーム |
JavaScript 生成元では、プレーンな HTTP ではなく HTTPS スキームを使用する必要があります。ローカルホストの URI(localhost IP アドレスの URI を含む)はこのルールから除外されます。 |
ホスト |
ホストに数値表記の IP アドレスを指定することはできません。ローカルホストの IP アドレスはこのルールから除外されます。 |
ドメイン |
“googleusercontent.com” にすることはできません。goo.gl など)を含めることはできません。 |
ユーザー情報 |
JavaScript オリジンに userinfo サブコンポーネントを含めることはできません。 |
[Path] |
JavaScript オリジンにパス コンポーネントを含めることはできません。 |
クエリ |
JavaScript オリジンにクエリ コンポーネントを含めることはできません。 |
Fragment |
JavaScript オリジンにフラグメント コンポーネントを含めることはできません。 |
文字数 |
JavaScript 生成元には、次のような特定の文字を含めることはできません。
|
増分承認
OAuth 2.0 プロトコルでは、アプリはリソースにアクセスするための承認をリクエストします。リソースはスコープで識別されます。リソースが必要になったときに承認をリクエストするのが、ユーザー エクスペリエンスの最善のプラクティスと考えられています。これを可能にするため、Google の承認サーバーは増分認可をサポートしています。この機能を使用すると、必要に応じてスコープをリクエストできます。また、ユーザーが新しいスコープの権限を付与すると、認証コードが返されます。このコードは、ユーザーがプロジェクトに付与したすべてのスコープを含むトークンと交換できます。
たとえば、ユーザーが音楽トラックをサンプリングし、ミックスを作成できるようにするアプリでは、ログイン時に必要となるリソースはごくわずかであり、ログインする人の名前以外には必要ない可能性があります。ただし、作成したミックスを保存するには、Google ドライブへのアクセスが必要になります。Google ドライブへのアクセスをリクエストするのは、アプリが実際に必要としたときのときだけであれば、ほとんどのユーザーにとって自然なことでしょう。
この場合、アプリはログイン時に openid
スコープと profile
スコープをリクエストして基本的なログインを行い、その後、最初のリクエスト時に https://www.googleapis.com/auth/drive.file
スコープをリクエストして組み合わせを保存します。
増分承認から取得したアクセス トークンには、次のルールが適用されます。
- このトークンを使用して、新しく結合された認可に追加されたスコープのいずれかに対応するリソースにアクセスできます。
- 結合された認可に更新トークンを使用してアクセス トークンを取得する場合、アクセス トークンは結合された認可を表し、レスポンスに含まれる任意の
scope
値に使用できます。 - 異なるクライアントから権限付与がリクエストされた場合でも、ユーザーが API プロジェクトに付与したすべてのスコープが結合された承認に含まれます。たとえば、ユーザーがアプリケーションのデスクトップ クライアントを使用して 1 つのスコープへのアクセスを許可し、その後、モバイル クライアントを介して同じアプリケーションに別のスコープを付与した場合、統合された承認には、両方のスコープが含まれます。
- 統合された承認を表すトークンを取り消すと、関連するユーザーに代わってその承認のすべてのスコープに対するアクセス権が同時に取り消されます。
以下のコードサンプルは、既存のアクセス トークンにスコープを追加する方法を示しています。このアプローチにより、アプリは複数のアクセス トークンを管理する必要がなくなります。
OAuth 2.0 エンドポイント
既存のアクセス トークンにスコープを追加するには、Google の OAuth 2.0 サーバーへのリクエストに include_granted_scopes
パラメータを含めます。
次のコード スニペットは、その方法を示しています。このスニペットでは、アクセス トークンが有効なスコープがブラウザのローカル ストレージに保存されていることを前提としています。(完全なサンプルのコードでは、ブラウザのローカル ストレージに oauth2-test-params.scope
プロパティを設定することで、アクセス トークンが有効になるスコープのリストを保存しています)。
このスニペットは、アクセス トークンが有効なスコープと、特定のクエリに使用するスコープを比較します。アクセス トークンがそのスコープに含まれない場合、OAuth 2.0 フローが開始されます。ここで、oauth2SignIn
関数は、ステップ 2 で提供された関数と同じです(これは後ほど完全な例で説明します)。
var SCOPE = 'https://www.googleapis.com/auth/drive.metadata.readonly'; var params = JSON.parse(localStorage.getItem('oauth2-test-params')); var current_scope_granted = false; if (params.hasOwnProperty('scope')) { var scopes = params['scope'].split(' '); for (var s = 0; s < scopes.length; s++) { if (SCOPE == scopes[s]) { current_scope_granted = true; } } } if (!current_scope_granted) { oauth2SignIn(); // This function is defined elsewhere in this document. } else { // Since you already have access, you can proceed with the API request. }
トークンの取り消し
ユーザーがアプリケーションに付与されたアクセス権の取り消しを希望する場合があります。ユーザーは、 アカウント設定にアクセスしてアクセス権を取り消すことができます。詳しくは、サポート ドキュメントのアカウントにアクセスできるサードパーティのサイトやアプリの、サイトまたはアプリのアクセス権の削除をご覧ください。
また、アプリに付与されているアクセス権をプログラムで取り消すこともできます。ユーザーが登録解除やアプリケーションを削除した場合、またはアプリに必要な API リソースが大幅に変更された場合には、プログラムによる取り消しが重要です。つまり、削除プロセスに、以前にアプリに付与された権限を確実に削除するための API リクエストを含めることができます。
OAuth 2.0 エンドポイント
プログラムでトークンを取り消すには、アプリケーションから https://oauth2.googleapis.com/revoke
にリクエストを行い、トークンをパラメータとして指定します。
curl -d -X -POST --header "Content-type:application/x-www-form-urlencoded" \ https://oauth2.googleapis.com/revoke?token={token}
トークンにはアクセス トークンまたは更新トークンを使用できます。トークンがアクセス トークンで、対応する更新トークンがある場合は、更新トークンも取り消されます。
取り消しが正常に処理された場合、レスポンスの HTTP ステータス コードは 200
です。エラー状態の場合、HTTP ステータス コード 400
がエラーコードとともに返されます。
次の JavaScript スニペットは、JavaScript 用 Google API クライアント ライブラリを使用せずに、JavaScript でトークンを取り消す方法を示しています。トークンを取り消すための Google の OAuth 2.0 エンドポイントはクロスオリジン リソース シェアリング(CORS)をサポートしていないため、コードは XMLHttpRequest()
メソッドを使用してリクエストを送信するのではなく、フォームを作成してエンドポイントに送信します。
function revokeAccess(accessToken) { // Google's OAuth 2.0 endpoint for revoking access tokens. var revokeTokenEndpoint = 'https://oauth2.googleapis.com/revoke'; // Create <form> element to use to POST data to the OAuth 2.0 endpoint. var form = document.createElement('form'); form.setAttribute('method', 'post'); form.setAttribute('action', revokeTokenEndpoint); // Add access token to the form so it is set as value of 'token' parameter. // This corresponds to the sample curl request, where the URL is: // https://oauth2.googleapis.com/revoke?token={token} var tokenField = document.createElement('input'); tokenField.setAttribute('type', 'hidden'); tokenField.setAttribute('name', 'token'); tokenField.setAttribute('value', accessToken); form.appendChild(tokenField); // Add form to page and submit it to actually revoke the token. document.body.appendChild(form); form.submit(); }