在 ASP.NET Core 应用中使用用于 .NET 的 Azure SDK
Azure SDK for .NET 使 ASP.NET Core 应用能够与许多不同的 Azure 服务集成。 本文介绍在 ASP.NET Core 应用中采用适用于 .NET 的 Azure SDK 的最佳做法和步骤。 将了解如何执行以下操作:
- 注册服务进行依赖项注入。
- 在不使用密码或机密的情况下向 Azure 进行身份验证。
- 实现集中式标准化配置。
- 配置常见的 Web 应用问题,例如日志记录和重试。
探索常见的 Azure SDK 客户端库
ASP.NET 连接到 Azure 服务的核心应用通常取决于以下 Azure SDK 客户端库:
- Microsoft.Extensions.Azure 提供了帮助程序方法,用于将客户端注册到依赖项注入服务集合,并处理各种问题,例如设置日志记录、处理 DI 服务生存期和身份验证凭据管理。
- Azure.Identity 支持跨 Azure SDK Microsoft Entra ID 身份验证支持。 它提供一组 TokenCredential 实现来构造支持 Microsoft Entra 身份验证的 Azure SDK 客户端。
Azure.<service-namespace>
库(如 Azure.Storage.Blobs 和 Azure.Messaging.ServiceBus)提供服务客户端和其他类型,以帮助连接和使用特定的 Azure 服务。 有关这些库的完整清单,请参阅 使用 Azure.Core 的库。
在前面的部分中,你将了解如何实现使用这些库的 ASP.NET Core 应用程序。
将 Azure SDK 客户端注册到 DI 服务集合
用于 .NET 的 Azure SDK 客户端库提供服务客户端,用于将应用连接到 Azure 服务,例如Azure Blob 存储和 Azure 密钥库。 将这些服务注册到应用的文件中的依赖项容器 Program.cs
,以便通过 依赖项注入提供这些服务。
完成以下步骤以注册所需的服务:
添加 Microsoft.Extensions.Azure 包:
dotnet add package Microsoft.Extensions.Azure
添加相关的
Azure.*
服务客户端包:dotnet add package Azure.Security.KeyVault.Secrets dotnet add package Azure.Storage.Blobs dotnet add package Azure.Messaging.ServiceBus
在
Program.cs
应用的文件中,从Microsoft.Extensions.Azure
库中调用AddAzureClients扩展方法,注册客户端以与每个 Azure 服务通信。 某些客户端库为 Azure 服务功能的特定子组提供其他 子组 。 可以通过扩展方法注册此类子实体进行依赖项注入 AddClient 。builder.Services.AddAzureClients(clientBuilder => { // Register a client for each Azure service using inline configuration clientBuilder.AddSecretClient(new Uri("<key_vault_url>")); clientBuilder.AddBlobServiceClient(new Uri("<storage_url>")); clientBuilder.AddServiceBusClientWithNamespace( "<your_namespace>.servicebus.windows.net"); // Register a subclient for each Azure Service Bus Queue var queueNames = new string[] { "queue1", "queue2" }; foreach (string queue in queueNames) { clientBuilder.AddClient<ServiceBusSender, ServiceBusClientOptions>( (_, _, provider) => provider.GetService<ServiceBusClient>() .CreateSender(queue)).WithName(queue); } // Register a shared credential for Microsoft Entra ID authentication clientBuilder.UseCredential(new DefaultAzureCredential()); });
将已注册的客户端注入 ASP.NET 核心应用组件、服务或 API 终结点:
app.MapGet("/reports", async ( BlobServiceClient blobServiceClient, IAzureClientFactory<ServiceBusSender> senderFactory) => { // Create the named client ServiceBusSender serviceBusSender = senderFactory.CreateClient("queue1"); await serviceBusSender.SendMessageAsync(new ServiceBusMessage("Hello world")); // Use the blob client BlobContainerClient containerClient = blobServiceClient.GetBlobContainerClient("reports"); List<BlobItem> reports = new(); await foreach (BlobItem blobItem in containerClient.GetBlobsAsync()) { reports.Add(blobItem); } return reports; }) .WithName("GetReports");
有关详细信息,请参阅 Azure SDK for .NET 的依赖项注入。
使用 Microsoft Entra ID 进行身份验证
使用 Microsoft Entra ID 进行基于令牌的身份验证是对 Azure 服务的请求进行身份验证的建议方法。 为了授权这些请求, Azure 基于角色的访问控制 (RBAC) 基于用户的 Microsoft Entra 标识和分配的角色管理对 Azure 资源的访问。
将 Azure 标识 库用于上述基于令牌的身份验证支持。 该库提供类,例如 DefaultAzureCredential
简化配置安全连接的过程。 DefaultAzureCredential
支持多种身份验证方法,并确定应在运行时使用哪种方法。 通过这种方法,你的应用可在不同环境(本地与生产)中使用不同的身份验证方法,而无需实现特定于环境的代码。 有关这些主题的更多详细信息,请访问 Azure SDK for .NET 文档的“身份验证”部分。
注意
许多 Azure 服务还允许使用密钥授权请求。 但是,应谨慎使用此方法。 开发人员必须尽量避免在不安全的位置公开访问密钥。 拥有访问密钥的任何人都可以授权针对关联的 Azure 资源的请求。
-
dotnet add package Azure.Identity
在
Program.cs
应用的文件中,从Microsoft.Extensions.Azure
库调用UseCredential扩展方法,为所有已注册的 Azure 服务客户端设置共享DefaultAzureCredential
实例:builder.Services.AddAzureClients(clientBuilder => { // Register a client for each Azure service using inline configuration clientBuilder.AddSecretClient(new Uri("<key_vault_url>")); clientBuilder.AddBlobServiceClient(new Uri("<storage_url>")); clientBuilder.AddServiceBusClientWithNamespace( "<your_namespace>.servicebus.windows.net"); // Register a subclient for each Azure Service Bus Queue var queueNames = new string[] { "queue1", "queue2" }; foreach (string queue in queueNames) { clientBuilder.AddClient<ServiceBusSender, ServiceBusClientOptions>( (_, _, provider) => provider.GetService<ServiceBusClient>() .CreateSender(queue)).WithName(queue); } // Register a shared credential for Microsoft Entra ID authentication clientBuilder.UseCredential(new DefaultAzureCredential()); });
DefaultAzureCredential
发现当前环境中的可用凭据,并使用它们向 Azure 服务进行身份验证。 有关扫描凭据的顺序和位置DefaultAzureCredential
,请参阅 DefaultAzureCredential 概述。 使用共享DefaultAzureCredential
实例可确保使用基础令牌缓存,从而提高应用程序复原能力和性能,因为对新令牌的请求更少。
应用配置
Azure SDK 服务客户端支持配置以更改其默认行为。 可通过两种方式配置服务客户端:
- JSON 配置文件 通常是推荐的方法,因为它们简化了在环境之间的应用部署方面的管理差异。
- 注册服务客户端时,可以应用内联代码配置。 例如,在 “注册客户端和子客户端 ”部分中,显式将 URI 变量传递给客户端构造函数。
IConfiguration
优先规则受 Microsoft.Extensions.Azure
扩展方法的尊重,这些方法在 配置提供程序 文档中进行了详细介绍。
完成以下部分中的步骤,将应用更新为针对相应环境使用 JSON 文件配置。 使用 appsettings.Development.json
该文件进行开发设置,将 appsettings.Production.json
文件用于生产环境设置。 可以将名称为类上的 ClientOptions 公共属性的配置设置添加到 JSON 文件。
配置已注册的服务
appsettings.<environment>.json
使用突出显示的服务配置更新应用中的文件:{ "Logging": { "LogLevel": { "Default": "Information", "Microsoft.AspNetCore": "Warning", "Azure.Messaging.ServiceBus": "Debug" } }, "AzureDefaults": { "Diagnostics": { "IsTelemetryDisabled": false, "IsLoggingContentEnabled": true }, "Retry": { "MaxRetries": 3, "Mode": "Exponential" } }, "KeyVault": { "VaultUri": "https://<your-key-vault-name>.vault.azure.net" }, "ServiceBus": { "Namespace": "<your_service-bus_namespace>.servicebus.windows.net" }, "Storage": { "ServiceUri": "https://<your-storage-account-name>.storage.windows.net" } }
在前面的 JSON 示例中:
- 顶级键名称、
KeyVault
和ServiceBus
Storage
,是用于引用代码中的配置部分的任意名称。 将这些名称传递给AddClient
扩展方法以配置给定客户端。 所有其他密钥名称都映射到特定的客户端选项,JSON 序列化以不区分大小写的方式执行。 - 和键值分别映射到
ServiceBus:Namespace> 和构造函数重载的参数SecretClient(Uri, TokenCredential, SecretClientOptions)ServiceBusClient(String)。BlobServiceClient(Uri, TokenCredential, BlobClientOptions) KeyVault:VaultUri
Storage:ServiceUri
使用构造函数的TokenCredential
变体,因为默认值TokenCredential
通过UseCredential(TokenCredential)方法调用设置。
- 顶级键名称、
Program.cs
更新该文件以检索 JSONIConfiguration
文件配置,并将其传递到服务注册中:builder.Services.AddAzureClients(clientBuilder => { // Register clients using a config file section clientBuilder.AddSecretClient( builder.Configuration.GetSection("KeyVault")); clientBuilder.AddBlobServiceClient( builder.Configuration.GetSection("Storage")); // Register clients using a specific config key-value pair clientBuilder.AddServiceBusClientWithNamespace( builder.Configuration["ServiceBus:Namespace"]);
配置 Azure 默认值和重试
你可能想要全局更改默认的 Azure 客户端配置或特定服务客户端。 例如,你可能需要不同的重试设置或使用不同的服务 API 版本。 你可以全局设置或按服务设置重试设置。
更新配置文件以设置默认 Azure 设置,例如所有已注册的 Azure 客户端都将使用的新默认重试策略:
{ "Logging": { "LogLevel": { "Default": "Information", "Microsoft.AspNetCore": "Warning", "Azure.Messaging.ServiceBus": "Debug" } }, "AzureDefaults": { "Diagnostics": { "IsTelemetryDisabled": false, "IsLoggingContentEnabled": true }, "Retry": { "MaxRetries": 3, "Mode": "Exponential" } }, "KeyVault": { "VaultUri": "https://<your-key-vault-name>.vault.azure.net" }, "ServiceBus": { "Namespace": "<your_service-bus_namespace>.servicebus.windows.net" }, "Storage": { "ServiceUri": "https://<your-storage-account-name>.storage.windows.net" } }
在
Program.cs
文件中,调用ConfigureDefaults
扩展方法以检索默认设置并将其应用于服务客户端:builder.Services.AddAzureClients(clientBuilder => { // Register clients using a config file section clientBuilder.AddSecretClient( builder.Configuration.GetSection("KeyVault")); clientBuilder.AddBlobServiceClient( builder.Configuration.GetSection("Storage")); // Register clients using a specific config key-value pair clientBuilder.AddServiceBusClientWithNamespace( builder.Configuration["ServiceBus:Namespace"]); // Register a subclient for each Azure Service Bus Queue string[] queueNames = [ "queue1", "queue2" ]; foreach (string queue in queueNames) { clientBuilder.AddClient<ServiceBusSender, ServiceBusClientOptions>( (_, _, provider) => provider.GetService<ServiceBusClient>() .CreateSender(queue)).WithName(queue); } clientBuilder.UseCredential(new DefaultAzureCredential()); // Set up any default settings clientBuilder.ConfigureDefaults( builder.Configuration.GetSection("AzureDefaults")); });
配置日志记录
用于 .NET 的 Azure SDK 客户端库可以记录客户端库操作,以监视对 Azure 服务的请求和响应。 客户端库还可以记录各种其他事件,包括重试、令牌检索以及来自各种客户端的服务特定事件。 使用 AddAzureClients 扩展方法注册 Azure SDK 客户端时,会 AzureEventSourceLogForwarder 向依赖项注入容器注册该客户端。 转发 AzureEventSourceLogForwarder
来自 Azure SDK 事件源的 ILoggerFactory 日志消息,以便使用标准 ASP.NET 核心日志记录配置进行日志记录。
下表描述了用于 .NET 的 Azure SDK EventLevel
如何映射到 ASP.NET Core LogLevel
。 有关这些主题和其他方案的详细信息,请参阅 使用用于 .NET 的 Azure SDK 和 用于 .NET 的 Azure SDK 进行依赖项注入的日志记录。
Azure SDK EventLevel |
ASP.NET Core LogLevel |
---|---|
Critical |
Critical |
Error |
Error |
Informational |
Information |
Warning |
Warning |
Verbose |
Debug |
LogAlways |
Information |
可以使用“配置身份验证”部分中概述的相同 JSON 配置更改默认日志级别和其他设置。 例如,通过将密钥设置为以下项,Logging:LogLevel:Azure.Messaging.ServiceBus
将日志级别切换ServiceBusClient
为Debug
:
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning",
"Azure.Messaging.ServiceBus": "Debug"
}
},
"AzureDefaults": {
"Diagnostics": {
"IsTelemetryDisabled": false,
"IsLoggingContentEnabled": true
},
"Retry": {
"MaxRetries": 3,
"Mode": "Exponential"
}
},
"KeyVault": {
"VaultUri": "https://<your-key-vault-name>.vault.azure.net"
},
"ServiceBus": {
"Namespace": "<your_service-bus_namespace>.servicebus.windows.net"
},
"Storage": {
"ServiceUri": "https://<your-storage-account-name>.storage.windows.net"
}
}