Azure PowerShell如何使用基于用户名/密码的身份验证?

时间:2015-05-26 09:35:02

标签: powershell authentication azure azure-powershell

我想了解Azure PowerShell如何使用基于AAD用户名/密码的凭据进行Azure API调用。

我的理解是,应用程序在进行Azure API调用之前需要一个client-id。此客户端ID必须在用户的帐户中注册。

Azure PowerShell是否具有客户端ID?如果是这样,如果没有明确地将其注册到Azure帐户,它是如何工作的?这是一个特殊的ID,已经在帐户中列入白名单吗?

2 个答案:

答案 0 :(得分:4)

您无需在Azure Active Directory中为Azure Powershell创建应用程序注册。要利用Azure AD用户的用户名/密码凭据,可以使用Add-AzureAccount cmdlet:

$username = "admin@your_account.onmicrosoft.com"
$password = "SuperSecretPassword" | ConvertTo-SecureString -AsPlainText -Force

$credential = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList $username, $password 
Add-AzureAccount -Credential $credential 

确保安装了最新版本的Azure PowerShell模块,并且您使用的帐户是组织帐户(而不是Microsoft帐户)或本机Azure AD用户。

要回答问题的最后部分,Azure PowerShell有一个众所周知的客户端ID(“1950a258-227b-4e31-a9cf-717495945fc2”)。它在Azure Powershell模块中进行了硬编码,可用于在直接调用Azure管理API时向Azure AD验证PowerShell脚本:

# Load Active Directory Authentication Library (ADAL) Assemblies
$adal = "${env:ProgramFiles(x86)}\Microsoft SDKs\Azure\PowerShell\ServiceManagement\Azure\Services\Microsoft.IdentityModel.Clients.ActiveDirectory.dll"
$adalforms = "${env:ProgramFiles(x86)}\Microsoft SDKs\Azure\PowerShell\ServiceManagement\Azure\Services\Microsoft.IdentityModel.Clients.ActiveDirectory.WindowsForms.dll"
[System.Reflection.Assembly]::LoadFrom($adal)
[System.Reflection.Assembly]::LoadFrom($adalforms)

# Set Azure AD Tenant name
$adTenant = "yourtenant.onmicrosoft.com" 

# Set well-known client ID for Azure PowerShell
$clientId = "1950a258-227b-4e31-a9cf-717495945fc2" 

# Set redirect URI for Azure PowerShell
$redirectUri = "urn:ietf:wg:oauth:2.0:oob"

# Set Resource URI to Azure Service Management API
$resourceAppIdURI = "https://management.core.windows.net/"

# Set Authority to Azure AD Tenant
$authority = "https://login.windows.net/$adTenant"

# Set user credentials (*** obviously you wouldn't have the password in clear text in a production script ***)
$userName = "admin@your_tenant.onmicrosoft.com"
$password = "SecretPassword"
$creds = New-Object "Microsoft.IdentityModel.Clients.ActiveDirectory.UserCredential" -ArgumentList $userName,$password

# Create AuthenticationContext tied to Azure AD Tenant
$authContext = New-Object "Microsoft.IdentityModel.Clients.ActiveDirectory.AuthenticationContext" -ArgumentList $authority

# Acquire token
$authResult = $authContext.AcquireToken($resourceAppIdURI,$clientId,$creds)

答案 1 :(得分:0)

您还可以获得所需的行为,即应用程序的用户只需要像Azure PowerShell一样提供用户名和密码。

这也是你可以做的。

a)为了让您的租户目录之外的用户访问您的web api,web api需要是多租户。我们假设你继续在Azure AD中配置它。

b)接下来,在目录中创建一个本机应用程序,其中包含对web api的委派权限。

c)然后,通过更新其清单,将本机客户端应用程序ID添加到web api knownClientIds属性中。这样做的原因是同意流,在用户批准后获得在用户目录中配置的Web API SPN。这需要针对多租户应用程序进行。阅读更多here

现在,我们假设您发送了一个调用Web API的应用程序(例如Azure powerShell)。您只需在应用程序中对客户端ID和APP ID URI(重定向URI)进行硬编码,用户就不需要提供它。

但现在最重要的是使用正确的ADAL API。 如果您使用以下API,则会引发错误

var uc = new UserCredential(userName, userPassword); authresult = context.AcquireToken(webapiresourceid, nativeclientID, uc);

AADSTS65001: The user or administrator has not consented to use the application with ID '<app id guid>'. Send an interactive authorization request for this user and resource.

原因是用户必须同意,因为Web API是多租户。对于本机客户端应用程序,这是不需要的,因为默认情况下它们是多租户。

因此,您必须使用以下API,这将提出同意书(仅限第一次)

result = context.AcquireToken( webapiresourceid, nativeclientID, new Uri("nativeclientRedirectURI"), PromptBehavior.Auto, new UserIdentifier(userName, UserIdentifierType.RequiredDisplayableId));

请注意,本机客户端ID和本机客户端URI都可以进行硬编码,就像Azure PowerShell在上面的答案中所做的那样。