使用 Azure SDK for Python 向 Azure 服务验证 Python 应用身份

当应用需要访问 Azure 资源(如 Azure 存储、Azure 密钥保管库或 Azure AI 服务)时,必须向 Azure 验证应用身份。 此要求适用于所有应用,无论它们是部署到 Azure、在本地部署还是在本地开发人员工作站上开发。 本文介绍在使用 Azure SDK for Python 时向 Azure 验证应用身份的推荐方法。

当应用向 Azure 资源进行身份验证时,请对应用使用基于令牌的身份验证,而不是连接字符串。 适用于 Python 的 Azure 标识客户端库提供支持基于令牌的身份验证的类,并允许应用无缝地对 Azure 资源进行身份验证,无论应用是在本地开发中、部署到 Azure 还是部署到本地服务器。

应用用于对 Azure 资源进行身份验证的基于令牌的特定类型取决于应用的运行位置。 基于令牌的身份验证类型如下图所示。

一个图表,显示了根据应用程序运行位置推荐的基于令牌的身份验证策略。

  • 当开发人员在本地开发期间运行应用时:应用使用用于本地开发的应用程序服务主体或开发人员的 Azure 凭据向 Azure 进行身份验证。 这些选项在本地开发期间的身份验证一节中介绍。
  • 当应用托管在 Azure 上时:应用使用托管标识向 Azure 资源进行身份验证。 此选项在服务器环境中的身份验证一节中讨论。
  • 在本地托管和部署应用时:应用使用应用程序服务主体向 Azure 资源进行身份验证。 此选项在服务器环境中的身份验证一节中讨论。

DefaultAzureCredential

Azure 标识客户端库提供的 DefaultAzureCredential 类允许应用根据其运行的环境使用不同的身份验证方法。 通过这种方式,应用程序可以从本地开发升级到测试环境再到生产环境,而无需更改代码。

你可以为每个环境配置适当的身份验证方法,然后 DefaultAzureCredential 会自动检测和使用该身份验证方法。 使用 DefaultAzureCredential 优于手动编码条件逻辑或功能标志,以便在不同环境中使用不同的身份验证方法。

有关使用 DefaultAzureCredential 类的详细信息,请参阅在应用程序中使用 DefaultAzureCredential 部分。

基于令牌的身份验证的优势

在为 Azure 生成应用时,请使用基于令牌的身份验证,而不是使用连接字符串。 与使用连接字符串进行身份验证相比,基于令牌的身份验证具有以下优势:

  • 本文中所述的基于令牌的身份验证方法允许你在 Azure 资源上建立应用所需的特定权限。 这种做法遵循最低特权原则原则。 相比之下,连接字符串授予对 Azure 资源的完全权限。
  • 具有连接字符串的任何人或任何应用都可以连接到 Azure 资源,但基于令牌的身份验证方法仅将对资源的访问范围限定为旨在访问该资源的应用。
  • 使用托管标识时,无需存储应用程序机密。 该应用更安全,因为没有可以泄露的连接字符串或应用程序机密。
  • azure-identity 包会为你获取和管理 Microsoft Entra 令牌。 因此,使用基于令牌的身份验证与使用连接字符串一样简单。

将连接字符串的使用限制在不访问生产或敏感数据的初始概念验证应用或开发原型中。 否则,在向 Azure 资源进行身份验证时,Azure 标识客户端库中提供的基于令牌的身份验证类始终是首选。

在服务器环境中进行身份验证

当在服务器环境中托管时,每个应用都会为应用运行的每个环境分配一个唯一的应用程序标识。 在 Azure 中,应用程序标识由服务主体表示。 这种特殊类型的安全主体对 Azure 的应用进行标识和身份验证。 要为应用使用的服务主体类型取决于应用的运行位置:

身份验证方法 说明
Azure 中托管的应用 Azure 中托管的应用应该使用托管标识服务主体。 托管标识旨在表示 Azure 中托管的应用的标识,并且只能用于 Azure 托管的应用。

例如,托管在 Azure 应用程序服务中的 Django Web 应用将被分配一个托管标识。 然后,分配给该应用的托管标识将用于通过其他 Azure 服务对应用进行身份验证。

在 Azure Kubernetes 服务 (AKS) 中运行的应用可以使用工作负载标识凭据。 此凭据基于与 AKS 服务帐户具有信任关系的托管标识。
,
托管在 Azure 外部的应用
(例如,本地应用)
托管在 Azure 外部的且需要连接到 Azure 服务的应用(例如本地应用)应使用应用程序服务主体。 应用程序服务主体表示 Azure 中的应用的标识,是通过应用程序注册过程创建的。

例如,考虑一个使用 Azure Blob 存储的本地托管的 Django Web 应用。 可以使用应用程序注册过程为应用创建应用程序服务主体。 AZURE_CLIENT_IDAZURE_TENANT_IDAZURE_CLIENT_SECRET 都将存储为环境变量,以便应用程序在运行时读取,并允许应用使用应用程序服务主体向 Azure 进行身份验证。

在本地开发期间进行身份验证

当应用在本地开发期间在开发人员的工作站上运行时,它仍然必须向应用使用的任何 Azure 服务进行身份验证。 在本地开发期间,向 Azure 验证应用身份有两种主要策略:

身份验证方法 说明
创建要在本地开发期间使用的专用应用程序服务主体对象。 在此方法中,通过使用应用注册过程设置专用应用程序服务主体对象,以便在本地开发期间使用。 然后,服务主体的标识将存储为环境变量,供应用在本地开发环境中运行时访问。

使用此方法可将应用所需的特定资源权限分配给开发人员在本地开发期间使用的服务主体对象。 这种做法可确保应用程序仅有权访问它所需的特定资源,并复制应用程序在生产环境中将具有的权限。

这种方法的缺点是需要为每个在应用程序上工作的开发人员创建单独的服务主体对象。

在本地开发期间,使用开发人员的凭据向 Azure 验证应用身份。 在此方法中,开发人员必须从其本地工作站上的 Azure CLI、Azure PowerShell 或 Azure 开发人员 CLI 登录到 Azure。 然后,应用程序可以访问凭据存储中的开发人员凭据,并使用这些凭据从应用访问 Azure 资源。

此方法的优点是设置更简单,因为开发人员只需通过上述开发人员工具之一登录到其 Azure 帐户。 此方法的缺点是,开发人员帐户拥有的权限可能比应用程序所需的权限更多。 因此,应用程序无法准确复制在生产环境中运行时所需的权限。

在应用程序中使用 DefaultAzureCredential

DefaultAzureCredential 是用于对 Microsoft Entra ID 进行身份验证的有序机制序列。 每个身份验证机制都是一个实现 TokenCredential 协议的类,称为凭据。 在运行时,DefaultAzureCredential 尝试使用第一个凭据进行身份验证。 如果该凭据无法获取访问令牌,则会尝试序列中的下一个凭据,以此类推,直到成功获取访问令牌。 这样,应用就可在不同的环境中使用不同的凭据,而无需编写特定于环境的代码。

若要在 Python 应用中使用 DefaultAzureCredential,请将 azure-identity 包添加到应用程序。

pip install azure-identity

使用各种 Azure SDK 客户端库中的专用客户端类访问 Azure 服务。 下面的代码示例演示如何实例化 DefaultAzureCredential 对象并将其与 Azure SDK 客户端类结合使用。 在这种情况下,它是用于访问 Azure Blob 存储的 BlobServiceClient 对象。

from azure.identity import DefaultAzureCredential
from azure.storage.blob import BlobServiceClient

# Acquire a credential object
credential = DefaultAzureCredential()

blob_service_client = BlobServiceClient(
        account_url="https://<my_account_name>.blob.core.windows.net",
        credential=credential)

当上述代码在本地开发工作站上运行时,它会在环境变量中查找应用程序服务主体,或在本地安装的开发人员工具(如 Azure CLI)中查找一组开发人员凭据。 在本地开发期间,两种方法都可用于对访问 Azure 资源的应用进行身份验证。

部署到 Azure 时,此相同代码还可以向 Azure 资源验证你的应用。 DefaultAzureCredential 可以检索环境设置和托管标识配置,以自动向 Azure 服务进行身份验证。