次の方法で共有


API保護

開発者が API を保護する場合は、承認に重点を置く必要があります。 リソースの API を呼び出すには、アプリケーションが アプリケーションの承認を取得する必要があります。 リソースによって承認が強制されます。 この記事では、 ゼロ トラスト の目標を達成するためのベスト プラクティスについて説明します。 登録、アクセス許可と同意の定義、アクセスの強制によって API を保護する方法について説明します。

保護された API を登録する

Microsoft Entra ID (Microsoft Entra ID) で API を保護するには、API を登録します。 その後、 登録済みの API を管理できます。 Microsoft Entra ID では、API は、別のアプリケーションがアクセスできるリソースまたは API として定義される特定のアプリ登録設定を持つアプリです。 Microsoft Entra 管理センターMicrosoft Identity Developerでは、アプリの登録は、Microsoft Entra ID が保護する API を持つ SaaS (Software-as-a-Servcie) プロバイダーの基幹業務 API またはサービスとしてテナント内にある API です。

登録時に、呼び出し元アプリケーションが API とその委任されたアクセス許可とアプリケーションのアクセス許可を参照する方法を定義します。 アプリの登録は、クライアント アプリケーションと API の両方を持つソリューションを表すことができます。 ただし、この記事では、スタンドアロン リソースが API を公開するシナリオについて説明します。

通常、API は認証を実行したり、承認を直接要求したりしません。 API は、呼び出し元アプリが提示するトークンを検証します。 API には対話型サインインがないため、リダイレクト URI やアプリケーションの種類などの設定を登録する必要はありません。 API は、Microsoft Entra ID を操作することによってではなく、それらの API を呼び出しているアプリケーションからトークンを取得します。 Web API の場合は、承認に OAuth2 アクセス トークンを使用します 。 Web API は、ベアラー トークンを検証して呼び出し元を承認します。 ID トークンをアクセス許可の証明として受け入れないでください。

既定では、Microsoft Entra ID は、新しいアプリ登録の API アクセス許可に User.Read を追加します。 ほとんどの Web API では、このアクセス許可を削除します。 Microsoft Entra ID には、API が別の API を呼び出す場合にのみ API アクセス許可が必要です。 API が別の API を呼び出さない場合は、API を登録するときに User.Read アクセス許可を削除します。

あなたの API にアクセスする必要があるクライアント アプリが API を呼び出す許可を求めるときに使用する、一意の識別子である アプリケーション ID URIが必要です。 アプリケーション ID URI は、すべての Microsoft Entra テナントで一意である必要があります。 api://<clientId> (ポータルの既定の提案) を使用できます。ここで、<clientId>は登録済みの API のアプリケーション ID です。

API を呼び出す開発者にわかりやすい名前を付けるために、API のアドレスをアプリケーション ID URI として使用できます。 たとえば、yourdomain.comが Microsoft Entra テナントで構成された発行元ドメインである場合にhttps://API.yourdomain.comを使用できます。 Microsoft は、ドメインを API の一意識別子として使用できるように、そのドメインの所有権を確認します。 このアドレスにコードを記述する必要はありません。 API は、必要な場所であればどこでもかまいませんが、API の https アドレスをアプリケーション ID URI として使用することをお勧めします。

最小限の特権で委任されたアクセス許可を定義する

ユーザーが含まれるアプリケーションで API を呼び出す場合は、少なくとも 1 つの委任されたアクセス許可を定義します (「アプリ登録に スコープを追加 する API を公開する」を参照してください)。

組織のデータ ストアへのアクセスを提供する API は、そのデータにアクセスする不適切なアクターの注目を集めることができます。 委任されたアクセス許可を 1 つだけ持つ代わりに、 最小限の特権アクセス を念頭に置いて、ゼロ トラスト原則を使用してアクセス許可を設計します。 すべてのクライアント アプリが完全な特権アクセスで始まる場合、後で最小特権モデルに入るのは困難な場合があります。

多くの場合、開発者は、ユーザーとしてのアクセスユーザーのなりすまし(技術的には不正確な一般的な語句)など、単一のアクセス許可を使用するパターンに陥ります。 このような単一のアクセス許可では、API への完全な特権アクセスのみが許可されます。

アプリケーションがセキュリティ侵害に対して脆弱にならないように、または意図しないタスクの実行に使用されるように、最小限の特権スコープを宣言します。 API のアクセス許可で複数のスコープを定義します。 たとえば、スコープをデータの読み取りと更新から分離し、読み取り専用のアクセス許可を提供することを検討します。 書き込みアクセス には、作成、更新、および削除操作の権限が含まれます。 クライアントは、データの読み取り専用に書き込みアクセス権を必要としてはなりません。

API が機密データで動作する場合は、 標準 アクセス許可と フル アクセス許可を検討してください。 標準のアクセス許可でアクセスが許可されないように機密性の高いプロパティを制限します (たとえば、 Resource.Read)。 次に、プロパティと機密情報を返す フル アクセス許可 ( Resource.ReadFull など) を実装します。

要求するアクセス許可を常に評価し、作業を完了するために求める絶対最小特権を目指してください。 高い特権のアクセス許可を要求しないでください。 代わりに、コア シナリオごとに個別のアクセス許可を作成します。 このアプローチの良い例については、 Microsoft Graph のアクセス許可リファレンスを参照 してください。 必要に応じ、適切な数のアクセス許可を見つけて使用します。

スコープ定義の一部として、特定のスコープで実行できる操作の範囲に 管理者の同意が必要かどうかを決定します。

API デザイナーとして、ユーザーの同意のみを安全に要求できるスコープに関するガイダンスを提供できます。 ただし、テナント管理者は、すべてのアクセス許可に管理者の同意が必要になるようにテナントを構成できます。 スコープを管理者の同意を必要とするように定義した場合、アクセス許可には常に管理者の同意が必要です。

ユーザーまたは管理者の同意を決定するときは、次の主な考慮事項があります。

  • アクセス許可の背後にある操作の範囲が複数のユーザーに影響を与えるかどうか。 アクセス許可によって、ユーザーが自分の情報にのみアクセスできるアプリケーションを選択できる場合は、ユーザーの同意が適切である可能性があります。 たとえば、ユーザーは、電子メール用の優先アプリケーションを選択することに同意できます。 ただし、アクセス許可の背後にある操作に複数のユーザー (他のユーザーの完全なユーザー プロファイルの表示など) が含まれている場合は、そのアクセス許可を管理者の同意を必要とするように定義します。

  • アクセス許可の背後にある操作の範囲に広範なスコープがあるかどうか。 たとえば、広範なスコープは、アクセス許可によって、アプリがテナント内のすべてを変更したり、元に戻せない可能性のある操作を行ったりできる場合です。 広い範囲は、ユーザーの同意ではなく管理者の同意が必要であることを示します。

疑わしい場合は、保守的な側に立ち、管理者の同意を要求してください。 同意の結果を明確かつ簡潔に、アクセス許可文字列に記述します。 説明文字列を読み取る個人には、API や製品に関する知識がないとします。

アクセス許可のセマンティクスを変更する方法で、既存のアクセス許可に API を追加しないでください。 既存のアクセス許可をオーバーロードすると、クライアントが以前に同意を与えた理由が薄められます。

アプリケーションのアクセス許可を定義する

ユーザー以外のアプリケーションをビルドする場合、ユーザー名とパスワードまたは多要素認証 (MFA) の入力を求めることができるユーザーはいません。 ユーザーがいないアプリケーション (ワークロード、サービス、デーモンなど) が API を呼び出す場合は、API の アプリケーションアクセス許可 を定義します。 アプリケーションのアクセス許可を定義するときは、スコープを使用する代わりに アプリケーション ロール を使用します。

委任されたアクセス許可と同様に、API を呼び出すワークロードが最小限の特権アクセスに従い、ゼロ トラストの原則に準拠できるように、詳細なアプリケーションアクセス許可を提供します。 1 つのアプリ ロール (アプリのアクセス許可) と 1 つのスコープ (委任されたアクセス許可) のみを発行したり、すべての操作を各クライアントに公開したりしないでください。

次のコード例に示すように、ワークロードは クライアント資格情報 を使用して認証し、 .default スコープ でトークンを要求します。

// With client credentials flows the scopes is ALWAYS of the shape "resource/.default", as the 
// application permissions need to be set statically (in the portal or by PowerShell), 
// and then granted by a tenant administrator
string[] scopes = new string[] { "https://kkaad.onmicrosoft.com/webapi/.default" };
 
AuthenticationResult result = null;
try
{
  result = await app.AcquireTokenForClient(scopes)
    .ExecuteAsync();
  Console.WriteLine("Token acquired \n");
}
catch (MsalServiceException ex) when (ex.Message.Contains("AADSTS70011"))
{
  // Invalid scope. The scope has to be of the form "https://resourceurl/.default"
  // Mitigation: change the scope to be as expected
  Console.WriteLine("Scope provided is not supported");
}

アクセス許可は、アプリの前にユーザーがいない場合や、アプリケーションのアクセス許可によって広範な操作が可能になったときに、管理者の同意が必要です。

アクセスを強制する

呼び出し元のアプリケーションが https 要求の承認ヘッダーでベアラー トークンとして提供するアクセス トークンを検証して解釈することで、API がアクセスを強制していることを確認します。 次のセクションで説明するように、トークンの検証、メタデータの更新の管理、スコープとロールの適用によってアクセスを強制します。

トークンを検証する

API がトークンを受け取ったら、トークンが 検証されていることを確認します。 検証により、トークンが適切な発行者からアンサンプリングされ、変更されていないことが保証されます。 ID トークンの場合と同様に、Microsoft Entra ID からトークンを直接取得しないため、署名を確認します。 API がネットワーク上の信頼されていないソースからトークンを受け取った後に署名を検証します。

JSON Web トークン署名の検証に関する既知の脆弱性があるため、適切に保守および確立された標準トークン検証ライブラリを使用します。 認証ライブラリ ( Microsoft.Identity.Web など) は、適切な手順を使用し、既知の脆弱性を軽減します。

必要に応じて、 トークンの検証を拡張します。 テナント ID (tid) 要求を使用して、API がトークンを取得できるテナントを制限します。 azp要求とappid要求を使用して、API を呼び出すことができるアプリをフィルター処理します。 オブジェクト ID (oid) 要求を使用して、個々のユーザーへのアクセスをさらに絞り込みます。

メタデータの更新を管理する

トークン検証ライブラリが必要なメタデータを効果的に管理することを常に確認してください。 この場合、メタデータは、Microsoft が Microsoft Entra トークンの署名に使用する公開キー (秘密キーのペア) です。 ライブラリがこれらのトークンを検証すると、既知のインターネット アドレスから公開されている公開署名キーの一覧が取得されます。 これらのキーを取得するための適切なタイミングがホスティング環境にあることを確認します。

たとえば、古いライブラリは、24 時間ごとにこれらの公開署名キーを更新するようにハードコーディングされる場合がありました。 Microsoft Entra ID でこれらのキーをすばやくローテーションする必要があり、ダウンロードしたキーに新しいローテーションされたキーが含まれていない場合を検討してください。 API は、メタデータの更新サイクルを待機している間、1 日オフラインになる可能性があります。 メタデータを適切に取得できるように、 特定のメタデータ更新ガイダンス を参照してください。 ライブラリを使用している場合は、適切なタイミングでそのメタデータが処理されていることを確認します。

スコープとロールを適用する

トークンを検証した後、API はトークン内の要求を調べて、その動作を決定します。

委任されたアクセス許可トークンの場合、API でスコープ (scp) クレームを確認し、アプリケーションに許可された操作を把握します。 オブジェクト ID (oid) またはサブジェクト キー (sub) 要求を調べて、アプリケーションが動作しているユーザーを確認します。

次に、API チェックを行って、ユーザーが要求された操作にもアクセスできることを確認します。 API で ユーザーとグループに割り当てるためのロールが定義されている場合は、API でトークン内のロール要求を確認し、それに応じて動作するようにします。 アプリケーションアクセス許可トークンには、スコープ (scp) 要求がありません。 代わりに、API でロール要求を調べて、ワークロードが受け取ったアプリケーションのアクセス許可を決定します。

API がトークンとスコープを検証し、オブジェクト ID (oid)、サブジェクト キー (sub)、ロール要求を処理すると、API は結果を返すことができます。

次のステップ