Azure deployment script keeps complaining "CurrentStorageAccount is not set" - powershell

I want to do automated deployment with Bamboo (a Continuous Integration solution). I found in here(http://www.windowsazure.com/en-us/develop/net/common-tasks/continuous-delivery/#script) a piece of script to help. The main code snippet:
#configure powershell with Azure 1.7 modules
Import-Module Azure
#configure powershell with publishsettings for your subscription
$pubsettings = $subscriptionDataFile
Import-AzurePublishSettingsFile $pubsettings
Set-AzureSubscription -CurrentStorageAccount $storageAccountName -SubscriptionName $selectedsubscription
write-host $storageAccountName
write-host "$selectedsubscription"
#set remaining environment variables for Azure cmdlets
$subscription = Get-AzureSubscription $selectedsubscription
$subscriptionname = $subscription.subscriptionname
$subscriptionid = $subscription.subscriptionid
$slot = $environment
#main driver - publish & write progress to activity log
Write-Output "$(Get-Date –f $timeStampFormat) - Azure Cloud Service deploy script started."
Write-Output "$(Get-Date –f $timeStampFormat) - Preparing deployment of $deploymentLabel for $subscriptionname with Subscription ID $subscriptionid."
Publish
$deployment = Get-AzureDeployment -slot $slot -serviceName $servicename
$deploymentUrl = $deployment.Url
Write-Output "$(Get-Date –f $timeStampFormat) - Created Cloud Service with URL $deploymentUrl."
Write-Output "$(Get-Date –f $timeStampFormat) - Azure Cloud Service deploy script finished."
I just first tried running this script from cmd by executing powershell E:\CI\OCZDeployment\publish_cloud_service.ps1 -environment Staging -serviceName "ocz" -storageAccountName "t2vsoft" -packageLocation OCZ.cspkg -cloudConfigLocation ServiceConfiguration.Cloud.cscfg -subscriptionDataFile E:\CI\OCZDeployment\SubscriptionDataFile.publishsettings -selectedsubscription "Development Subscription"
, where the publishsettings file is downloaded from Azure.
But I kept getting the error message:
New-AzureDeployment : CurrentStorageAccount is not set. Use Set-AzureSubscription subname -CurrentStorageAccount storageaccount to set it.
It has definitely been set in the snippet. I even tried copy & paste the Set-AzureSubscription line to inside New-AzureDeployment function. No luck.
Help me! Thank you!

Fixed. Don't know what was exactly the cause but i removed all registered azure subscriptions by executing:
PS> Get-AzureSubscription | ForEach-Object { Remove-AzureSubscription $_.SubscriptionName }
and re-imported the subscription by executing:
PS> Import-AzurePublishSettingsFile xxx.publishsettings
and it all worked! :)
There really were some similarly-named subscriptions in the subscription list. There might have been conflicts as such the azure scripts didn't know which one they really wanted.

If you have multiple subscriptions then you need to make sure the subscription that you want to use is set to the default. This can be done with the following:
Select-AzureSubscription -SubscriptionName "{subscriptionName}" -Default
if you aren't sure what your subscription name is you can use the following to see all of your subscriptions:
Get-AzureSubscription

Related

How to create a azure resource through powershell task in azure devops release pipeline?

I want to create an App Service Plan (Consumption) through powershell task. For this i used Azure Powershell task, And my code is:
[cmdletbinding()]
param (
$AppServicePlanLocation,
$AppServicePlanResourceGroupName,
$AppServicePlan_Name
)
$location = $AppServicePlanLocation
$resourceGroupName = $AppServicePlanResourceGroupName
$appServicePlanName = $AppServicePlan_Name
Write-Host "SafeCreateAppServicePlan.Parameter:location: $location"
Write-Host "SafeCreateAppServicePlan.Parameter:resourceGroupName: $resourceGroupName"
Write-Host "SafeCreateAppServicePlan.Parameter:appServicePlanName: $appServicePlanName"
$SkuName = "Y1"
$SkuTier = "Dynamic"
$WebAppApiVersion = "2015-08-01"
$fullObject = #{
location = $location
sku = #{
name = $SkuName
tier = $SkuTier
}
}
Write-Host "Ensuring the $appServicePlanName app service plan exists"
$plan = Get-AzureRmAppServicePlan -Name $appServicePlanName -ResourceGroupName $resourceGroupName -ErrorAction SilentlyContinue
if(-not $plan) {
Write-Host "Creating $appServicePlanName app service plan"
New-AzureRmResource -ResourceGroupName $resourceGroupName -ResourceType Microsoft.Web/serverfarms -Name $appServicePlanName -IsFullObject -PropertyObject $fullObject -ApiVersion $WebAppApiVersion -Force
}
else {
Write-Host "$appServicePlanName app service plan already exists"
}
But it is giving error:
The term 'Get-AzureRmAppServicePlan' is not recognized as the name of a cmdlet, function, script file, or operable program. Check the spelling of the name, or if a path was included, verify that the path is correct and try again.
Azure Powershell task is not recognizing Get-AzureRmAppServicePlan command.
Note: I have not used simple powershell task, I have used Azure Powershell task.
If you are using the latest version of the task - replace all the *AzureRM* commands with *Az* (or enable backwards compatibility) as this is the supported Azure Powershell module, current (the AzureRM one is depreciated and no longer supported).
https://learn.microsoft.com/en-us/powershell/azure/migrate-from-azurerm-to-az?view=azps-3.3.0
ps. If you are using a previous version of the task - AzureRM should work
You don't mention what Task version of the Azure PowerShell task you are using, or the context the agent is running in, Hosted\Private. Both those can effect if the module would be available.
Can check and see if the AzureRM.Websites Module is available.
$ Get-Module Azure* -list | Select-Object Name,Version,Path
You may need to manually load the module, or specify an older version of the Azure PowerShell task, as the AzureRM modules aren't automatically available when using the newer version of the task.

Switch-AzureRmWebAppSlot does not swap the physical site only the application settings

I have been running the following command via powershell for AZURE but all that gets swapped are the application settings:
Switch-AzureRmWebAppSlot -ResourceGroupName 'myresourcegroup' -Name 'mywebsitename' -SourceSlotName "staging" -DestinationSlotName "production" -confirm -verbose
The same thing happens when I run this command:
Switch-AzureRmWebAppSlot -ResourceGroupName 'myresourcegroup' -Name 'mywebsitename' -SourceSlotName "staging" -DestinationSlotName "production" -SwapWithPreviewAction CompleteSlotSwap -confirm -verbose
I cannot use Switch-AzureWebsite as I cannot set a default subscription with my permissions.
Using the Login-AzureRMAccount the only way I found to switch slots is as follows:
$ParametersObject = #{targetSlot = "production"}
$RGN = 'resource-group-name-'
Invoke-AzureRmResourceAction -ResourceGroupName $RGN -ResourceType Microsoft.Web/sites/slots -ResourceName website-name/staging -Action slotsswap -Parameters $ParametersObject -Verbose -force
This was hard to find, in part because many examples required you to set your Azure default subscription prior to executing Switch-AzureWebsite and the other switch only moved the configuration elements over. I am curious if anyone has a clever way to discover power shell commands or ARM template commands aside from the ones generated for deployments on Azure. Ideally, I could perform an action on Azure an then see same thing scripted as PowerShell.
REF: Microsoft Docs Here

How do I deploy to Azure App Service with PowerShell?

I have looked around and with the thousands of commands in the Azure and AzureRM commandlets in PowerShell, I'm still not sure how to do this.
What I have working so far:
Installed Azure and AzureRM modules and imported them to the script
Generated the "*.publishsettings" file from the get-AzurePublishSettingsFile command
Imported the "*.publishsettings" file
Can acccess the website with the "Stop-AzureWebsite" and "Start-AzureWebsite" commandlets
What I need to do:
create a new deployment and push files to the app-service site.
Notes: I do not have a Visual Studio project and .csproj file configs. I simply want to take the contents of a folder and push that to the website.
Any help would be useful as the documentation is really bad on details and there are thousands of commands in PowerShell to go through.
You could check this blog:Deploy an App Service using Azure PowerShell to a Deployment Slot.
Get-AzurePublishSettingsFile
Import-AzurePublishSettingsFile .\Your-Publish-Settings-credentials.publishsettings
Get-AzureSubscription
Select-AzureSubscription -SubscriptionName "The Subscription Name containing the slot"
Set-AzureSubscription -SubscriptionId "ID of subscription"
$WebAppName = "standard(staging)"
Get-AzureWebsite -Name $WebAppName
Publish-AzureWebsiteProject -Name $WebAppName -Package "C:\PowerShell\standard.zip" -Slot "staging"
The above link (https://blogs.msdn.microsoft.com/benjaminperkins/2016/10/01/deploy-an-app-service-using-azure-powershell-to-a-deployment-slot/)talks about a GIT based deployment. OP wanted something from a folder.
Check this one out -
Create an Azure Website with PowerShell and FTP
Unfortunately the accepted answer gave me the following error:
Get-AzureWebSite : Requested value 'PremiumV2' was not found
This StackOverflow answer suggests to use Get-AzureRmWebApp instead, but this introduces some challenges with authentication. After some searching I found the following article which explained exactly what I needed: an approach to do a publish to Azure without any human interaction.
Please see a very simplified version of the script below.
#In the Azure portal go to (search for) "Azure Active Directory" ->
#"Properties" -> Directory ID
$TenantId = "<Azure Active Directory Id>"
#In the Azure portal go to (search for) "Subscriptions" -> Subscription ID
$SubscriptionId = "<Azure Subscription Id>"
#In the Azure portal go to (search for) "Azure Active Directory" -> "App registrations" ->
#Create a new registration, this will give you the ID and Secret below.
#Make sure to give your new app registration sufficient rights to your app service
$ServicePrincipleApplicationId = "<Service Principle Id>"
$ServicePrincipleApplicationSecret = "<Service Principle Secret>"
$WebAppPath = "<Local folder where your package is located>"
$ResourceGroupName = "<The name of the Azure resource group that contains your app service>"
$WebAppName = "<The name of your Azure app service>"
$WebAppSlot = "<The name of the deployment slot you want to publish to>"
$MSDeployPath = "C:\Program Files\IIS\Microsoft Web Deploy V3\msdeploy.exe"
$source = "-source:contentPath=$WebAppPath"
$publishProfileOutputPath = Join-Path -Path $ENV:Temp -ChildPath 'publishprofile.xml'
$dest = "-dest:contentPath=d:\home\site\wwwroot\,publishSettings=$publishProfileOutputPath"
$SecurePassword = $ServicePrincipleApplicationSecret | ConvertTo-SecureString -AsPlainText -Force
$Credential = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList $ServicePrincipleApplicationId, $securePassword
$connectParameters = #{
Credential = $Credential
TenantId = $TenantId
SubscriptionId = $SubscriptionId
}
Add-AzureRmAccount #connectParameters -ServicePrincipal
Get-AzureRmWebAppSlotPublishingProfile -OutputFile $publishProfileOutputPath -Format WebDeploy -ResourceGroupName $ResourceGroupName -Name $WebAppName -Slot $WebAppSlot
Stop-AzureRmWebAppSlot -ResourceGroupName $ResourceGroupName -Name $WebAppName -Slot $WebAppSlot
& $MSDeployPath #('-verb:sync', $source, $dest)
Start-AzureRmWebAppSlot -ResourceGroupName $ResourceGroupName -Name $WebAppName -Slot $WebAppSlot
To deploy your zip package to Azure Web App Service using PowerShell cmdlet.
Refer MS Docs.
Connect to Azure Subscription via PowerShell. Execute Publish-AzWebApp to deploy Web App.
$webAppName = "<NameOfWebAppService>"
$resourceGroup = "<WebAppResourceGroupName>"
$zipArchiveFullPath = "<zip-package-filePath\FileName.zip>"
Publish-AzWebApp -ResourceGroupName "$resourceGroup" -Name "$webAppName" -ArchivePath "$($zipArchiveFullPath)" -Force

Get job status in Azure Runbook

I would like to have a runbook run on a schedule but exit if the last job hasn't finished running (i.e. if the schedule is every 2 hours and a job takes 2.5 hours then the next job shouldn't run).
I've tried to use Get-AzureAutomationJob to get the last job status (https://azure.microsoft.com/en-gb/documentation/articles/automation-runbook-execution/#retrieving-job-status-using-windows-powershell), but I can't get it to work. I presume all the preamble to get the subscription etc is required.
"Get-AzureAutomationJob : The Automation account was not found."
$ConnectionAssetName = "AzureClassicRunAsConnection"
# Get the connection
$connection = Get-AutomationConnection -Name $connectionAssetName
# Authenticate to Azure with certificate
Write-Verbose "Get connection asset: $ConnectionAssetName" -Verbose
$Conn = Get-AutomationConnection -Name $ConnectionAssetName
if ($Conn -eq $null)
{
throw "Could not retrieve connection asset: $ConnectionAssetName. Assure that this asset exists in the Automation account."
}
$CertificateAssetName = $Conn.CertificateAssetName
Write-Verbose "Getting the certificate: $CertificateAssetName" -Verbose
$AzureCert = Get-AutomationCertificate -Name $CertificateAssetName
if ($AzureCert -eq $null)
{
throw "Could not retrieve certificate asset: $CertificateAssetName. Assure that this asset exists in the Automation account."
}
Write-Verbose "Authenticating to Azure with certificate." -Verbose
Set-AzureSubscription -SubscriptionName $Conn.SubscriptionName - SubscriptionId $Conn.SubscriptionID -Certificate $AzureCert
Select-AzureSubscription -SubscriptionId $Conn.SubscriptionID
$job = (Get-AzureAutomationJob –AutomationAccountName "THE NAME OF THE AUTOMATION ACCOUNT AS IT APPEARS IN THE PORTAL" –Name "JobStatusTest" | sort LastModifiedDate –desc)[0]
Well, you would need to use Get-AzureRMAutomation job for that. Let me elaborate on that, I think in march 2016 Microsoft removed Azure Automation from the OLD azure model and now it is present only in the new one. so you would need to add RM to your commandlets

Deploying web role in Azure throws exception on CurrentAccountStorageName

I want to deploy a web role to Azure using the PowerShell CmdLets.
My script is as follows:
$subscription = "<name-of-subscription>"
$service = "<name-of-cloudservice>"
$slot = "staging"
$package = "path\to\package.cspkg"
$configuration = path\to\config.cscfg"
$deploymentLabel = "Deploy to $service"
Import-Module "C:\Program Files (x86)\Microsoft SDKs\Windows Azure\PowerShell\Azure\Azure.psd1"
Import-AzurePublishSettingsFile "C:\path-to.publishsettings"
Set-AzureSubscription -CurrentStorageAccount $service -SubscriptionName $subscription
# some more stuff to check whether to upgrade or to create ...
Set-AzureDeployment -Upgrade -Slot $slot -Package $package -Configuration $configuration -label $deploymentLabel -ServiceName $service -Force
When I execute this it throws an error:
Exception: The subscription named <name-of-subscription> already exists.
I figured that since I'm importing my publishsettings-file already I could get rid of Set-AzureSubscription. However, once I do that I get the next error:
Exception: CurrentStorageAccountName is not set.
Use Set-AzureSubscription subname -CurrentStorageAccountName storageaccount to set it.
This is the line that gave me the error in the first place, so I'm not sure how I need to set the storageaccountname without causing an error.
I also ran a little test:
Import-AzurePublishSettingsFile "C:\path-to.publishsettings"
Get-AzureSubscription | Format-Table
Once I do this I get the following output (reformatted):
SubscriptionName: <name-of-subscription>
SubscriptionId: 123456789-123...
ServiceEndpoint: https://man....
ActiveDirectoryEndpoint:
ActiveDirectoryTenantId:
IsDefault: True
Certificate [Subject]
CurrentStorageAccountName
CurrentCloudStorageAccount
ActiveDirectoryUserId
As you can see, the CurrentStorageAccountName is empty, but I don't know how I can set it to a correct value.
I looked up some other scripts, but they all seem to be having this sequence of importing, then setting. Any idea why this is not working and how to solve it?
You are trying to set CurrentStorageAccount to the name of your cloudservice, but you should be setting it to the name of your blob storage account. Get the list of you storage accounts
PS U:\>Get-AzureStorageAccount |select StorageAccountName
StorageAccountName
------------------
portalvhdsgsomething
storage1
storage2
storage3
then run your previously failing line but with the name of your storage account ie.
Set-AzureSubscription -CurrentStorageAccount storage2 -SubscriptionName $subscription
You can confirm your changes with
PS U:\>Get-AzureSubscription | select CurrentStorageAccount
CurrentStorageAccount : storage2
You need to use -CurrentStorageAccountName as the parameter of Set-AzureSubscription.
For Set-AzureSubscription the MSDN doc shows the -SubscriptionName parameter as parameter 1, not as named. The error message's suggested fix even implied that you needed to do Set-AzureSubscription <service> -CurrentStorageAccount <storage solution> Perhaps simply moving that will solve it?
Set-AzureSubscription -SubscriptionName $subscription -CurrentStorageAccount $service
Reference: http://msdn.microsoft.com/en-us/library/dn495189.aspx
I have found out the reason. It appears that you cannot include the subscription name as a named parameter. Changing this line:
Set-AzureSubscription -CurrentStorageAccount $service -SubscriptionName $subscription
to this line did the trick
Set-AzureSubscription $subscription -CurrentStorageAccount $service