Uma API Web que chama APIs Web: configuração do código
Este artigo descreve como configurar o código para um aplicativo de API Web usando o fluxo do código de autorização do OAuth 2.0.
A Microsoft recomenda o uso do pacote do NuGet Microsoft.Identity.Web ao desenvolver uma API do ASP.NET Core protegida que chama APIs Web downstream. Confira API Web protegida: configuração do código | Microsoft.Identity.Web para uma apresentação rápida dessa biblioteca no contexto de uma API Web.
Pré-requisitos
Configurar o aplicativo
Escolha um idioma para sua API Web.
Segredos do cliente ou certificados do cliente
Considerando que sua API Web agora recorre a uma API Web downstream, forneça um segredo do cliente ou um certificado do cliente no arquivo appsettings.json. Você também pode adicionar uma seção que especifica:
- a URL da API Web downstream
- os escopos necessários para chamar a API
No exemplo a seguir, a seção GraphBeta
especifica essas configurações.
{
"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"]
}
}
Observação
Você pode propor uma coleção de credenciais de cliente, incluindo uma solução sem credenciais, como federação de identidade de carga de trabalho para o Kubernetes do Azure. As versões anteriores do Microsoft.Identity.Web expressam o segredo do cliente em uma única propriedade "ClientSecret" em vez de "ClientCredentials". Ela ainda tem suporte para compatibilidade com versões anteriores, mas você não pode usar a propriedade "ClientSecret" e a coleção "ClientCredentials".
Em vez de um segredo do cliente, você pode fornecer um certificado do cliente. O snippet de código a seguir mostra o uso de um certificado armazenado no 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"]
}
}
Aviso
Se você esquecer de alterar Scopes
para uma matriz, quando tentar usar os IDownstreamApi
escopos aparecerá nulo e IDownstreamApi
tentará uma chamada anônima (não autenticada) para a API downstream, o que resultará em um 401/unauthenticated
.
O Microsoft.Identity.Web fornece várias maneiras de descrever os certificados, tanto por configuração quanto por código. Para obter mais detalhes, confira o Microsoft.Identity.Web – usando certificados no GitHub.
Module.vb
using Microsoft.Identity.Web;
// ...
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddMicrosoftIdentityWebApi(Configuration, Configuration.GetSection("AzureAd"))
.EnableTokenAcquisitionToCallDownstreamApi()
.AddInMemoryTokenCaches();
// ...
Seu aplicativo Web precisará adquirir um token para a API downstream. Especifique-o adicionando a linha .EnableTokenAcquisitionToCallDownstreamApi()
após .AddMicrosoftIdentityWebApi(Configuration)
. Essa linha expõe o serviço ITokenAcquisition
, que você pode usar em suas ações de controlador/páginas.
No entanto, um método alternativo é implementar um cache de token. Por exemplo, adicionar .AddInMemoryTokenCaches()
, a Program.cs permitirá que o token seja armazenado em cache na memória.
using Microsoft.Identity.Web;
// ...
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddMicrosoftIdentityWebApi(Configuration, Configuration.GetSection("AzureAd"))
.EnableTokenAcquisitionToCallDownstreamApi()
.AddInMemoryTokenCaches();
// ...
Microsoft.Identity.Web fornece dois mecanismos para chamar uma API Web de downstream de outra API. A opção escolhida depende se você deseja chamar o Microsoft Graph ou outra API.
Opção 1: chamar o Microsoft Graph
Para chamar o Microsoft Graph, Microsoft.Identity.Web permite usar diretamente oGraphServiceClient
(exposto pelo Microsoft Graph SDK) nas ações da API.
Observação
Há um problema em andamento para o SDK do Microsoft Graph v5+. Para obter mais informações, confira o problema do GitHub.
Para expor o Microsoft Graph:
- Adicione o pacote NuGet Microsoft.Identity.Web.GraphServiceClient ao projeto.
- Adicione
.AddMicrosoftGraph()
depois.EnableTokenAcquisitionToCallDownstreamApi()
em Program.cs..AddMicrosoftGraph()
tem várias substituições. Usando a substituição que tem uma seção de configuração como um parâmetro, o código se torna:
using Microsoft.Identity.Web;
// ...
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddMicrosoftIdentityWebApi(Configuration, Configuration.GetSection("AzureAd"))
.EnableTokenAcquisitionToCallDownstreamApi()
.AddMicrosoftGraph(Configuration.GetSection("GraphBeta"))
.AddInMemoryTokenCaches();
// ...
Opção 2: chamar uma API Web downstream diferente do Microsoft Graph
- Adicione o pacote NuGet Microsoft.Identity.Web.MicrosoftGraph ao projeto.
- Adicione
.AddDownstreamApi()
depois.EnableTokenAcquisitionToCallDownstreamApi()
em Program.cs. O código se torna:
using Microsoft.Identity.Web;
// ...
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddMicrosoftIdentityWebApi(Configuration, "AzureAd")
.EnableTokenAcquisitionToCallDownstreamApi()
.AddDownstreamApi("MyApi", Configuration.GetSection("MyApiScope"))
.AddInMemoryTokenCaches();
// ...
onde;
MyApi
indica o nome da API Web downstream que sua API Web pretende chamarMyApiScope
é o escopo necessário para que sua API Web solicite a fim de interagir com a API Web downstream
Esses valores serão representados em seu JSON, que será semelhante ao trecho a seguir.
"DownstreamAPI": {
"BaseUrl": "https://downstreamapi.contoso.com/",
"Scopes": "user.read"
},
Se o aplicativo Web precisar chamar outro recurso de API, repita o método .AddDownstreamApi()
com o escopo relevante, conforme mostrado no snippet a seguir:
using Microsoft.Identity.Web;
// ...
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddMicrosoftIdentityWebApi(Configuration, "AzureAd")
.EnableTokenAcquisitionToCallDownstreamApi()
.AddDownstreamApi("MyApi", Configuration.GetSection("MyApiScope"))
.AddDownstreamApi("MyApi2", Configuration.GetSection("MyApi2Scope"))
.AddInMemoryTokenCaches();
// ...
Observe que .EnableTokenAcquisitionToCallDownstreamApi
é chamado sem nenhum parâmetro, o que significa que o token de acesso será adquirido bem a tempo, pois o controlador solicita o token especificando o escopo.
O escopo também pode ser passado ao chamar .EnableTokenAcquisitionToCallDownstreamApi
, o que faria com que o aplicativo Web adquira o token durante o logon inicial do usuário em si. Em seguida, o token será retirado do cache quando o controlador o solicitar.
Semelhante aos aplicativos Web, várias implementações de cache de token podem ser escolhidas. Para obter mais detalhes, confira Microsoft Identity Web – serialização de cache de token no GitHub.
A seguinte imagem mostra as possibilidades deMicrosoft.Identity.Web e o impacto em Program.cs:
Observação
Para entender totalmente os exemplos de código aqui, você precisa estar familiarizado com os conceitos básicos do ASP.NET Core e, particularmente, com a injeção de dependência e as opções.
Você também pode ver um exemplo de implementação de fluxo OBO em Node.js e Azure Functions.
Protocolo
Para obter mais informações sobre o protocolo OBO, confira a plataforma de identidade da Microsoft e o fluxo On-Behalf-Of do OAuth 2.0.