OAuth 2.0は、ユーザーが自身のデータへのアクセス許可をサードパーティアプリケーションに安全に付与できるプロトコルです。この記事では、クラウドサービスのリーダーであるMicrosoft Azureを用いて、OAuth 2.0の認証フローを初心者でも理解できるように詳しく解説します。なおOAuthを行う部分のコーディング例はJavascriptを使用していきます。
Azureで事前準備
まず、Azureの管理画面でアプリの登録を行います。以下の手順で行うことができます。
リダイレクトURI、アプリケーション (クライアント) ID
- Azure Portalにログインします。
- 「アプリの登録」を選択し、「新しい登録」をクリックします。
- アプリの名前、サポートするアカウントの種類、リダイレクトURIを入力し、「登録」をクリックします。
- 登録が完了すると、アプリケーション (クライアント) IDが生成されます。これは後で使用します。
クライアントシークレット
次に、クライアントシークレットを生成します。
- 「新しいクライアントシークレット」をクリックします。
- 詳細、有効期限を入力し、「追加」をクリックします。
- クライアントシークレットが生成されます。これはすぐにコピーして安全な場所に保存してください。一度ブラウザを離れると、再度表示することはできません。
APIのアクセス許可
次に、APIのアクセス許可を設定します。
- アプリの登録ページで、「APIのアクセス許可」を選択します。
- 「アクセス許可を追加」をクリックします。
- 必要なAPIを選択し、「アクセス許可」を選択します。
- 必要なアクセス許可を選択し、「追加」をクリックします。
- 「変更を保存」をクリックします。
これで、アプリケーションは選択したAPIにアクセスする許可を得ました。
以上で、Azureでの設定は完了です。
ステップ1: 認証リクエストの送信
まず、アプリケーションはユーザーを認証サーバーにリダイレクトします。このリダイレクトURLには、アプリケーションがアクセスを求めているリソースや、アプリケーションを識別するための情報(クライアントIDなど)が含まれています。
認証リクエストを送信するための関数を作成します。この関数は、ユーザーをAzureの認証エンドポイントにリダイレクトします。
function redirectToAuthEndpoint() {
const clientId = 'YOUR_CLIENT_ID'; // Azureで生成したクライアントID
const redirectUri = encodeURIComponent('YOUR_REDIRECT_URI'); // Azureで設定したリダイレクトURI
const authEndpoint = `https://login.microsoftonline.com/common/oauth2/v2.0/authorize?client_id=${clientId}&response_type=code&redirect_uri=${redirectUri}&response_mode=query&scope=openid%20offline_access%20https%3A%2F%2Fgraph.microsoft.com%2F.default`;
// ユーザーを認証エンドポイントにリダイレクト
window.location.href = authEndpoint;
}
ステップ2: ユーザーの認証と承認
次に、ユーザーは認証サーバーで自分自身を認証します。これは通常、ユーザー名とパスワードを入力することで行われます。認証が成功すると、ユーザーはアプリケーションがアクセスを求めているリソースに対するアクセスを承認します。
ステップ3: 認証サーバーからのレスポンス
ユーザーがアクセスを承認すると、認証サーバーはユーザーをアプリケーションにリダイレクトします。このリダイレクトURLには、「認証コード」が含まれています。
async function handleAuthResponse() {
// URLから認証コードを取得
const urlParams = new URLSearchParams(window.location.search);
const authCode = urlParams.get('code');
if (!authCode) {
console.error('認証コードが見つかりません');
return;
}
ステップ4: アクセストークンの取得
アプリケーションはこの認証コードと、アプリケーションの秘密(クライアントシークレット)を使用して、認証サーバーにアクセストークンを要求します。認証サーバーはこれらの情報を検証し、正しい場合はアクセストークンをアプリケーションに返します。
// クライアントIDとクライアントシークレット
const clientId = 'YOUR_CLIENT_ID';
const clientSecret = 'YOUR_CLIENT_SECRET';
// アクセストークンを取得するためのリクエストを作成
const tokenRequest = {
method: 'POST',
headers: {
'Content-Type': 'application/x-www-form-urlencoded'
},
body: `client_id=${clientId}&scope=https%3A%2F%2Fgraph.microsoft.com%2F.default&code=${authCode}&redirect_uri=YOUR_REDIRECT_URI&grant_type=authorization_code&client_secret=${clientSecret}`
};
// アクセストークンを取得
const response = await fetch('https://login.microsoftonline.com/common/oauth2/v2.0/token', tokenRequest);
const data = await response.json();
if (data.error) {
console.error('アクセストークンの取得に失敗しました:', data.error_description);
} else {
console.log('アクセストークン:', data.access_token);
}
}
ステップ5: アクセストークンの使用
最後に、アプリケーションはこのアクセストークンを使用して、ユーザーのデータにアクセスします。アクセストークンは、アプリケーションがユーザーの代わりにリソースサーバー(例えば、MicrosoftAzureのAPI)にアクセスするための「鍵」のようなものです。
ここでは、Microsoft Graph APIを使用してユーザーのプロフィール情報を取得する例を示します。
async function getUserProfile(accessToken) {
// リクエストヘッダーにアクセストークンを設定
const headers = new Headers();
headers.append('Authorization', 'Bearer ' + accessToken);
// Microsoft Graph APIを使用してユーザーのプロフィール情報を取得
const response = await fetch('https://graph.microsoft.com/v1.0/me', { headers });
const data = await response.json();
if (data.error) {
console.error('ユーザーのプロフィール情報の取得に失敗しました:', data.error.message);
} else {
console.log('ユーザーのプロフィール情報:', data);
}
}
この関数は、アクセストークンを使用してMicrosoft Graph APIにリクエストを送り、ユーザーのプロフィール情報を取得します。取得した情報はコンソールに出力されます。
まとめ
以上が、OAuth 2.0の認証フローの基本的なステップです。このフローを通じて、ユーザーは自分のデータに対するアクセスを安全に管理することができ、アプリケーションはユーザーの許可なしにデータにアクセスすることができません。これにより、ユーザーのデータのプライバシーとセキュリティが保護されます。
なお、OAuth 2.0には他にもいくつかのフロー(パスワードフロー、クライアントクレデンシャルフローなど)がありますが、ここでは最も一般的な認証コードフローについて説明しました。これらのフローは、それぞれ異なるシナリオやセキュリティ要件に対応しています。
このように、OAuth 2.0は、ユーザーのデータにアクセスするための安全で効率的な方法を提供します。アプリケーション開発者は、このプロトコルを理解し、適切に実装することで、ユーザーのデータを安全に扱うことができます。
おまけ
通常OAuth2.0のフローを掲載しておきます。
この図は以下のステップを示しています:
- ユーザーがクライアントにリソースを要求します。
- クライアントはユーザーを認証サーバーにリダイレクトします。
- ユーザーは認証サーバーで認証します。
- 認証サーバーはユーザーに認証グラントを提供します。
- ユーザーは認証グラントをクライアントに提供します。
- クライアントは認証グラントを認証サーバーに提供します。
- 認証サーバーはクライアントにアクセストークンを提供します。
- クライアントはアクセストークンをリソースサーバーに提供します。
- リソースサーバーは保護されたリソースをクライアントに提供します。
- クライアントは保護されたリソースをユーザーに提供します。