Azure Resource Manager authentication from a PowerShell script
The infrastructure that makes up your application is often composed of various different components. For instance, you might simply be running a web site, but behind the scenes you have an Azure web site deployed, a Storage account for tables, blobs, and queues, a couple of VMs running a database cluster, a couple more VMs running Redis cache. The list could go on.
What is Azure Resource Manager?
These all relate to this single application. The old way of doing things was to use the Service Management API. Each piece of infrastructure was treated separately in the Azure Portal. Deployment consisted of manually creating them, or lots of effort creating scripts using PowerShell or the Azure CLI, for example. You would have to handle trying to initialise infrastructure in serial or parallel yourself. If you wanted to deploy just part of your infrastructure you would have to understand what was already there and take actions accordingly, either manually or in your scripts.
Azure Resource Manager is the new and recommended way of interacting with Azure. In the Azure Portal things now reside in Resource Groups. Multiple different services and bits of infrastructure can all be grouped together under a single Resource Group. For example if you want to clean up a deployment that consists of 10 different resources, you can simply delete the group and Azure handles removing everything within that group.
Azure Resource Manager allows you to define a declarative template for your group of resources, then deploy, monitor and manage them as a group. Azure handles things like parallelising as much of the deployment as possible without any extra effort on your part. It also deploys in an idempotent way i.e. incrementally adds anything missing while leaving anything already deployed in place, so you can rerun the template deployment multiple times safely.
Installing the AzureRM PowerShell modules
To get started with Azure Resource Manager using PowerShell, you need to have the right PowerShell modules installed.
If you haven't yet installed the AzureRM PowerShell modules, take a look at this document for how to install them.
This boils down to running the following cmdlets, which downloads the required modules from the PowerShell Gallery:
Deploying an Azure RM template using PowerShell
When running this locally you can using the cmdlet Login-AzureRmAccount. With no other parameters provided this will pop up a login box where you can directly enter your Azure credentials. This creates an authentication context for your PowerShell session. Once the session finishes the context is gone. The cmdlet Get-AzureRmContext will provide some details such as the current storage account associated with the session.
But how do you do the same thing non-interactively, like running the script on a build server?
You need the equivalent of a service account, that has been set up with the minimum permissions needed for this scenario.
Creating an Azure RM service principal
First, login using your own account. This will allow you to set up the service principal, that can then be used in future from other PowerShell scripts non-interactively. Setting up the service principal will be a one-time effort.
Second, create an Azure RM AD application. This is a record that identifies an application to Azure Active Directory.
Third, create a service principal for that application. This is an instance of the application that needs to access other resources.
Assign that service principal a role. There are a number of built in roles, for example Contributor which is allowed to manage everything except access. It is also possible to create custom roles.
Authenticating using a service principal
The username for your service principal is the application id, which is a GUID. When used for logging in the username needs to be given in the form "username@domain". The domain looks like <something>.onmicrosoft.com. If you aren't sure what the domain is, you should be able to see it when logged into the portal by hovering over the dropdown with your name, at the top right of the screen. The overall username used should look like:
92c22f1f-d1d4-46a1-b025-edb47fc03809@something.onmicrosoft.com
Create a PSCredential object:
Now you can login using that credential object:
Assuming you've successfully logged in (you'll see an error if not!), you can carry on with any other AzureRM related work for example creating a new resource group using New-AzureRmResourceGroup and deploying a template into that resource group using New-AzureRmResourceGroupDeployment.