웹 API를 호출하는 웹앱: 코드 구성

이전 문서에서는 Microsoft Entra에 애플리케이션을 등록했습니다. 이 문서에서는 애플리케이션 코드를 구성하고 사용자를 로그인할 뿐만 아니라 이제 웹 API를 호출하도록 웹앱을 수정하는 방법을 보여 줍니다. 만든 애플리케이션은 OAuth 2.0 권한 부여 코드 흐름을 사용하여 사용자를 로그인합니다. 이 흐름에는 두 단계가 있습니다.

  1. 인증 코드를 요청합니다. 이 부분에서는 사용자와의 프라이빗 대화 상자를 Microsoft ID 플랫폼에 위임합니다. 해당 대화가 진행되는 동안 사용자는 로그인하여 웹 API 사용에 동의합니다. 프라이빗 대화 상자가 성공적으로 종료되면 웹앱은 해당 리디렉션 URI에 대한 인증 코드를 수신합니다.
  2. 인증 코드를 교환하여 API에 대한 액세스 토큰을 요청합니다.

필수 조건

웹앱을 지원하는 Microsoft 라이브러리

다음 Microsoft 라이브러리는 웹앱을 지원합니다.

언어 / 프레임워크 프로젝트 설정
GitHub
Package(패키지) 가져오기
시작됨
사용자 로그인 웹 API 액세스 GA(일반 공급) 또는
공개 미리 보기1
.NET MSAL.NET Microsoft.Identity.Client 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 없습니다. 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 있습니다. GA
.NET Microsoft.IdentityModel Microsoft.IdentityModel 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 없습니다.2 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 없습니다.2 GA
ASP.NET Core ASP.NET Core Microsoft.AspNetCore.Authentication 빠른 시작 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 있습니다. 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 없습니다. GA
ASP.NET Core Microsoft.Identity.Web Microsoft.Identity.Web 빠른 시작 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 있습니다. 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 있습니다. GA
Java MSAL4J msal4j 빠른 시작 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 있습니다. 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 있습니다. GA
Spring spring-cloud-azure-starter-active-directory spring-cloud-azure-starter-active-directory 자습서 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 있습니다. 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 있습니다. GA
Node.js MSAL 노드 msal-node 빠른 시작 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 있습니다. 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 있습니다. GA
Python MSAL Python msal 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 있습니다. 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 있습니다. GA
Python identity identity 빠른 시작 라이브러리에서 사용자 로그인에 대한 ID 토큰을 요청할 수 있습니다. 라이브러리는 보호된 웹 API에 대한 액세스 토큰을 요청할 수 있습니다. --

(1)온라인 서비스에 대한 유니버설 사용 조건공개 미리 보기의 라이브러리에 적용됩니다.

(2)Microsoft.IdentityModel 라이브러리는 토큰의 유효성 검사만 수행하고 ID 또는 액세스 토큰은 요청할 수 없습니다.

관심 있는 플랫폼에 대한 탭을 선택합니다.

클라이언트 암호 또는 클라이언트 인증서

이제 웹앱이 다운스트림 웹 API를 호출하므로 appsettings.json 파일에 클라이언트 암호나 클라이언트 인증서를 제공합니다. 다음을 지정하는 섹션을 추가할 수도 있습니다.

  • 다운스트림 웹 API의 URL
  • API를 호출하는 데 필요한 범위

다음 예에서는 GraphBeta 섹션에서 이러한 설정을 지정합니다.

{
  "AzureAd": {
    "Instance": "https://login.microsoftonline.com/",
    "ClientId": "[Enter_the_Application_Id_Here]",
    "TenantId": "common",

   // To call an API
   "ClientCredentials": [
    {
      "SourceType": "ClientSecret",
      "ClientSecret":"[Enter_the_Client_Secret_Here]"
    }
  ]
 },
 "GraphBeta": {
    "BaseUrl": "https://graph.microsoft.com/beta",
    "Scopes": ["user.read"]
    }
}

참고 항목

Azure Kubernetes용 워크로드 ID 페더레이션과 같은 자격 증명이 없는 솔루션을 포함하여 클라이언트 자격 증명 컬렉션을 제안할 수 있습니다. 이전 버전의 Microsoft.Identity.Web은 "ClientCredentials" 대신 단일 속성 "ClientSecret"으로 클라이언트 암호를 표현했습니다. 이는 이전 버전과의 호환성을 위해 계속 지원되지만 "ClientSecret" 속성과 "ClientCredentials" 컬렉션을 모두 사용할 수는 없습니다.

클라이언트 암호 대신 클라이언트 인증서를 제공할 수 있습니다. 다음 코드 조각에서는 Azure Key Vault에 저장된 인증서를 사용하는 방법을 보여줍니다.

{
  "AzureAd": {
    "Instance": "https://login.microsoftonline.com/",
    "ClientId": "[Enter_the_Application_Id_Here]",
    "TenantId": "common",

   // To call an API
   "ClientCredentials": [
      {
        "SourceType": "KeyVault",
        "KeyVaultUrl": "https://msidentitywebsamples.vault.azure.net",
        "KeyVaultCertificateName": "MicrosoftIdentitySamplesCert"
      }
   ]
  },
  "GraphBeta": {
    "BaseUrl": "https://graph.microsoft.com/beta",
    "Scopes": ["user.read"]
  }
}

Warning

Scopes를 배열로 변경하는 것을 잊은 경우 IDownstreamApi를 사용하려고 하면 범위가 null로 나타나고 IDownstreamApi는 다운스트림 API에 대해 익명(인증되지 않은) 호출을 시도합니다. 401/unauthenticated.

Microsoft.Identity.Web은 구성이나 코드를 통해 인증서를 설명 하는 여러 가지 방법을 제공합니다. 자세한 내용은 GitHub에서 Microsoft.Identity.Web - 인증서 사용을 참조하세요.

Startup.cs 파일 수정

웹앱은 다운스트림 API에 대한 토큰을 획득해야 합니다. .AddMicrosoftIdentityWebApp(Configuration) 뒤에 .EnableTokenAcquisitionToCallDownstreamApi() 줄을 추가하여 이를 지정합니다. 이 줄은 컨트롤러 및 페이지 작업에서 사용할 수 있는 IAuthorizationHeaderProvider 서비스를 제공합니다. 그러나 다음 두 가지 옵션에 표시 된 것처럼 더 간단하게 수행할 수 있습니다. 또한 .AddInMemoryTokenCaches()처럼 Startup.cs에서 토큰 캐시 구현을 선택해야 합니다.

using Microsoft.Identity.Web;

public class Startup
{
  // ...
  public void ConfigureServices(IServiceCollection services)
  {
  // ...
  services.AddAuthentication(OpenIdConnectDefaults.AuthenticationScheme)
          .AddMicrosoftIdentityWebApp(Configuration, "AzureAd")
            .EnableTokenAcquisitionToCallDownstreamApi(new string[]{"user.read" })
            .AddInMemoryTokenCaches();
   // ...
  }
  // ...
}

EnableTokenAcquisitionToCallDownstreamApi 에 전달되는 범위는 선택 사항이며, 웹앱이 범위를 요청하고 사용자가 로그인할 때 범위에 사용자 동의를 요청할 수 있도록 합니다. 범위를 지정하지 않으면 Microsoft.Identity.Web이 증분 동의 환경을 사용하도록 설정합니다.

Microsoft.Identity.Web은 토큰을 얻지 않고도 웹앱에서 웹 API를 호출할 수 있는 두 가지 메커니즘을 제공합니다. 선택할 옵션은 Microsoft Graph 또는 다른 API를 호출하는지 여부에 따라 달라집니다.

옵션 1: Microsoft Graph 호출

Microsoft Graph를 호출하려면 Microsoft.Identity.Web을 통해 직접 GraphServiceClient(Microsoft Graph SDK에 의해 노출됨)를 API 작업에 사용할 수 있습니다. Microsoft Graph를 공개하려면:

  1. 프로젝트에 Microsoft.Identity.Web.GraphServiceClient NuGet 패키지를 추가합니다.

  2. .AddMicrosoftGraph().EnableTokenAcquisitionToCallDownstreamApi() 뒤에, Startup.cs 파일에서 추가합니다. .AddMicrosoftGraph() 에는 여러 재정의가 있습니다. 구성 섹션을 매개 변수로 사용하는 재정의를 사용하면 코드가 다음과 같이 됩니다.

    using Microsoft.Identity.Web;
    
    public class Startup
    {
      // ...
      public void ConfigureServices(IServiceCollection services)
      {
      // ...
      services.AddAuthentication(OpenIdConnectDefaults.AuthenticationScheme)
              .AddMicrosoftIdentityWebApp(Configuration, "AzureAd")
                .EnableTokenAcquisitionToCallDownstreamApi(new string[]{"user.read" })
                   .AddMicrosoftGraph(Configuration.GetSection("GraphBeta"))
                .AddInMemoryTokenCaches();
       // ...
      }
      // ...
    }
    

옵션 2: Microsoft Graph 이외의 다운스트림 웹 API 호출

Microsoft Graph 이외의 API를 호출하려는 경우 Microsoft.Identity.Web을 사용하면 API 작업에서 IDownstreamApi 인터페이스를 사용할 수 있습니다. 이 인터페이스를 사용하려면:

  1. 프로젝트에 Microsoft.Identity.Web.DownstreamApi NuGet 패키지를 추가합니다.

  2. .AddDownstreamApi().EnableTokenAcquisitionToCallDownstreamApi() 뒤에, Startup.cs 파일에서 추가합니다. .AddDownstreamApi()에는 두 개의 인수가 있으며 다음 코드 조각에 표시됩니다.

    • 해당 구성을 참조하기 위해 컨트롤러 작업에서 사용되는 서비스(API)의 이름
    • 다운스트림 웹 API를 호출하는 데 사용되는 매개 변수를 나타내는 구성 섹션.
    using Microsoft.Identity.Web;
    
    public class Startup
    {
      // ...
      public void ConfigureServices(IServiceCollection services)
      {
      // ...
      services.AddAuthentication(OpenIdConnectDefaults.AuthenticationScheme)
              .AddMicrosoftIdentityWebApp(Configuration, "AzureAd")
                .EnableTokenAcquisitionToCallDownstreamApi(new string[]{"user.read" })
                   .AddDownstreamApi("MyApi", Configuration.GetSection("GraphBeta"))
                .AddInMemoryTokenCaches();
       // ...
      }
      // ...
    }
    

요약

웹 API와 마찬가지로 다양 한 토큰 캐시 구현을 선택할 수 있습니다. 자세한 내용은 GitHub의 Microsoft.Identity.Web - 토큰 캐시 serialization을 참조하세요.

다음 이미지는 Microsoft.Identity.Web의 다양한 가능성과 Startup.cs 파일에 미치는 영향을 보여줍니다.

웹 API를 호출하고 토큰 캐시 구현을 지정하는 시작점 C S의 서비스 구성 옵션을 보여주는 블록 다이어그램

참고 항목

여기의 코드 예제를 완전히 이해하려면 ASP.NET Core 기본, 특히 종속성 주입옵션에 대해 잘 알고 있어야 합니다.

인증 코드를 교환하는 코드입니다.

Microsoft.Identity.Web은 올바른 OpenID Connect 설정을 지정하고, 코드를 받은 이벤트를 구독하고, 코드를 교환하여 코드를 단순화합니다. 인증 코드를 교환하는 데 필요한 추가 코드는 없습니다. 이 작업을 수행하는 방법에 대한 자세한 내용은 Microsoft.Identity.Web 소스 코드를 참조하세요.

클라이언트 암호 대신 클라이언트 인증서 또는 클라이언트 어설션을 사용하여 기밀 클라이언트 애플리케이션에서 해당 ID를 증명할 수도 있습니다. 클라이언트 어설션을 사용하는 것은 고급 시나리오로, 클라이언트 어설션에 자세히 설명되어 있습니다.

토큰 캐시

Important

웹앱 또는 웹 API에 대한 토큰 캐시 구현은 데스크톱 애플리케이션에 대한 구현과 다르며, 이는 종종 파일 기반입니다. 보안 및 성능상의 이유로, 웹앱 및 웹 API의 경우 사용자 계정마다 하나의 토큰 캐시가 있는지 확인하는 것이 중요합니다. 각 계정의 토큰 캐시를 직렬화해야 합니다.

ASP.NET Core 자습서에서는 종속성 주입을 사용하여 애플리케이션에 대한 Startup.cs 파일에서 토큰 캐시 구현을 결정할 수 있습니다. Microsoft.Identity.Web에는 토큰 캐시 직렬화에 설명된 미리 작성된 토큰 캐시 직렬 변환기가 제공됩니다. ASP.NET Core 분산 메모리 캐시를 선택할 수도 있습니다.

// Use a distributed token cache by adding:
    services.AddMicrosoftIdentityWebAppAuthentication(Configuration, "AzureAd")
            .EnableTokenAcquisitionToCallDownstreamApi(
                initialScopes: new string[] { "user.read" })
            .AddDistributedTokenCaches();

// Then, choose your implementation.
// For instance, the distributed in-memory cache (not cleared when you stop the app):
services.AddDistributedMemoryCache();

// Or a Redis cache:
services.AddStackExchangeRedisCache(options =>
{
 options.Configuration = "localhost";
 options.InstanceName = "SampleInstance";
});

// Or even a SQL Server token cache:
services.AddDistributedSqlServerCache(options =>
{
 options.ConnectionString = _config["DistCache_ConnectionString"];
 options.SchemaName = "dbo";
 options.TableName = "TestCache";
});

토큰 캐시 공급자에 대한 자세한 내용은 Microsoft.Identity.Web의 토큰 캐시 직렬화 문서와 웹앱 자습서의 ASP.NET Core 웹앱 자습서 | 토큰 캐시 단계를 참조하세요.

다음 단계

이 시점에서 사용자가 로그인하면 토큰이 토큰 캐시에 저장됩니다. 웹앱의 다른 부분에서 사용되는 방법을 살펴보겠습니다.

전역 로그아웃 시 캐시에서 계정을 제거합니다.