7
votes

Update:

Seems like someone else had the same issue and reported it.


I am facing an issue with a simple PowerShell script when invoking it from an Azure Automation Runbook. The same piece of code works flawless when running it locally.

I have added a Service Principal in an Azure Active Directory (hosted in Azure German Cloud) with password credential and grant it contributor access to a subscription (also hosted in Azure German Cloud).

The Azure Automation service is hosted in North Europe since it's currently not available in the Azure German Cloud.

All I try to do is to login to my subscription with the above mentioned principal using the Add-AzureRmAccount cmdlet. After that I try to set the current context using the Set-AzureRmContext and getting the following error message:

Set-AzureRmContext : Please provide a valid tenant or a valid subscription.
At line:26 char:1
+ Set-AzureRmContext -TenantId $TenantId -Su ...
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : CloseError: (:) [Set-AzureRmContext], ArgumentException
    + FullyQualifiedErrorId : Microsoft.Azure.Commands.Profile.SetAzureRMContextCommand

Here is the script I try to run (left the configuration blank):

$TenantId = ""
$ApplicationId = ""
$ClientSecret = ""
$SubscriptionId = ""

$secpasswd = ConvertTo-SecureString $ClientSecret -AsPlainText -Force
$mycreds = New-Object System.Management.Automation.PSCredential ($ApplicationId , $secpasswd)

Add-AzureRmAccount -ServicePrincipal -Environment 'AzureGermanCloud' -Credential $mycreds -TenantId $TenantId
Set-AzureRmContext -TenantId $TenantId -SubscriptionId $SubscriptionId

I also tried to use Login-AzureRmAccount without success. Also I am able to use the Get-AzureRmResourceGroup cmdlet to retrieve the resource groups so the login seems to work.

All Azure modules are updated to the latest version.


TLTR:

My main goal is to start a SQL export job using the New-AzureRmSqlDatabaseExport from the runnbook but it seems like the above mentioned error causes the cmdlet to fail with the following message:

New-AzureRmSqlDatabaseExport : Your Azure credentials have not been set up or have expired, please run 
Login-AzureRMAccount to set up your Azure credentials.
At line:77 char:18
+ ... rtRequest = New-AzureRmSqlDatabaseExport -ResourceGroupName $Resource 
4
so if the login works, why do you needs set-azurermcontext? just add -SubscriptionId to add-azurermaccount4c74356b41
@4c74356b41 Because the New-AzureRmSqlDatabaseExport will still throw that exception. I tried to provide a minimal example to reproduce my issue and I think the answer why the Set-AzureRmContext doesn't work will help me with my main goal.Martin Brandl
why would it still do that?4c74356b41
@4c74356b41 If I knew that I would not asked that question. I tried it already. Also when I try to get the subscription using the Get-AzureRmSubscription with the -SubscriptionId and -TenantId parameter, I receive the message Subscription xxx was not found in tenant Martin Brandl
wrong tenantid or subscriptionid?4c74356b41

4 Answers

3
votes

I had the same issue a few weeks ago and what worked was to first login to Azure account (which I think you already did) using:

Login-AzureRmAccount

Then get the subscription ID from Azure and use select the subscription using the ID instead of the name as follows:

Select-AzureRmSubscription -SubscriptionId {insert-subscription-id}
3
votes

Below is the code that worked for me (regular dc regions). If it doesn't work, go to the Automation Account >> Modules >> Update Azure Modules.

$ClientSecret = ""
$ApplicationId = ""
$SubscriptionId = ""

#New PSCredential Object
$secpasswd = ConvertTo-SecureString $ClientSecret -AsPlainText -Force
$mycreds = New-Object System.Management.Automation.PSCredential ($ApplicationId , $secpasswd)

#Login to subscription
Login-AzureRmAccount -Credential $mycreds -SubscriptionId $SubscriptionId

#Export Database
New-AzureRmSqlDatabaseExport -ResourceGroupName "<RG>" -ServerName "<SQLSERVERNAME>" -DatabaseName "<DATABASENAME>" -StorageKeyType "StorageAccessKey" -StorageKey "<STRKEY>" -StorageUri "<URITOFILE>" -AdministratorLogin "<DBLOGIN>" -AdministratorLoginPassword "<DBPASS>"

Update

Maybe running with a Run As Account can be a workaround for the issue. Create one by navigating to the Azure Automation Account >> Account Settings >> Run As Accounts. Here's an example code.

# Authenticate to Azure with service principal and certificate, and set subscription
$connectionAssetName = "AzureRunAsConnection"
$conn = Get-AutomationConnection -Name $ConnectionAssetName

Add-AzureRmAccount -ServicePrincipal -Tenant $conn.TenantID -ApplicationId $conn.ApplicationId -CertificateThumbprint $conn.CertificateThumbprint -ErrorAction Stop | Write-Verbose
Set-AzureRmContext -SubscriptionId $conn.SubscriptionId -ErrorAction Stop | Write-Verbose
2
votes

It looks like this is a known issue and I wasn't able to find a fix for that. But there are two workarounds:

  1. Using a Hybrid Runnbook Worker (mentioned by Walter - MSFT)
  2. Using a RunAsAccount with certificate credentials (mentioned by Bruno Faria)

It is important to specify the -Environment parameter. Otherwise I got the following exception:

Login-AzureRmAccount : AADSTS90038: Confidential Client is not supported in Cross Cloud request.

Here is the code I am using to login to AzureGermanCloud (MCD) from an Azure Runbook hosted in NorthEurope:

$connectionAssetName = "AzureRunAsConnection"
$conn = Get-AutomationConnection -Name $ConnectionAssetName

Login-AzureRmAccount `
    -ServicePrincipal `
    -CertificateThumbprint $conn.CertificateThumbprint `
    -ApplicationId $conn.ApplicationId `
    -TenantId $conn.TenantID `
    -Environment AzureGermanCloud
1
votes

When you login your Azure account, you could use specified subscription id. You could try following script.

$subscriptionId=""
$tenantid=""
$clientid=""
$password=""
$userPassword = ConvertTo-SecureString -String $password -AsPlainText -Force
$userCredential = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList $clientid, $userPassword
Add-AzureRmAccount -TenantId $tenantid -ServicePrincipal -SubscriptionId $subscriptionId -Credential $userCredential -Environment 'AzureGermanCloud'