Allow Application Running on An Azure Virtual Machine to Access Azure Key Vault using Managed Service Identity

Allow Application Running on An Azure Virtual Machine to Access Azure Key Vault using Managed Service Identity

In an earlier article I described what a Managed Service Identity is and how we can use it. In this article we’ll have a closer look at the scenario described in that article. Where we going to allow the application that is running in our Azure Virtual Machine to access an Azure Key Vault instance and retrieve secrets. The application in question is written using ASP.Net Core 2 and is hosted using IIS Inside Windows Server 2016 Virtual Machine on Azure.

Accessing Key Vault from the Web App

Web Application is really simple. Its just the out of the box ASP.Net Core 2 MVC application. I have modified the About page to show the secret taken from the Azure Key Vault.  To Access the Key Vault the following packages are installed.

  • Azure.KeyVault – Allows you to interact with the Azure Key Vault
  • Azure.Services.AppAuthentication (Pre-Release) – Allows the app to authenticate using the Azure AD.

Note: The Microsoft.Azure.Services.AppAuthentication Nuget package is still in pre-release

Then the HomeController is modified by changing the About() controller action. The code looks like this

public async Task<IActionResult> About()
{
  var tokenProvider = new AzureServiceTokenProvider();
  var vaultClient = new KeyVaultClient(new KeyVaultClient.AuthenticationCallback(tokenProvider.KeyVaultTokenCallback));

  var secret = await vaultClient.GetSecretAsync($"{keyVaultBaseUrl}/secrets/{secretKey}").ConfigureAwait(false);
  ViewBag.Secret = secret.Value;

  return View();
}

Here I am using the AzureServiceTokenProvider coming from the Microsoft.Azure.Services.AppAuthentication nuget package in combination with the KeyVaultClient to authenticate in to Azure Key Vault Instance and retrieve the secret stored in the Key Vault. The secret I am trying to receive is called mysecret and it’s a random string. Then I am passing the secret value in to the View using ViewBag. Here is how the about.cshtml file looks like

@{
    ViewData["Title"] = "About";
}
<h2>Secret From Key Vault: @ViewData["Secret"]</h2>

Once this is done. I have deployed the following application in to the Windows Server 2016 virtual machine using Visual Studio Team Service. Take a look at the following article to see how that is done.

Creating a Managed Service Identity for the Virtual Machine.

Once the application is deployed, the next step is to create the Managed Service Identity (MSI) for the Virtual Machine so we can add that identity in an access policy in Key Vault so the application can access the key vault. To do that, in the Virtual Machine blade on the Azure Portal, click on the Configuration link under the Settings menu section.

1-create-managed-service-identity

Here Under the Managed Service Identity select Yes for Register with Azure Active Directory option and click on Save button. This will create the Identity in the Azure Active Directory.

Creating the Access Policy on Azure Key Vault using the Managed Service Identity

Next, you need to create the access policy using the Managed Service Identity we created earlier in order for the VM to access the Key Vault, thus allowing the applications running inside the VM to access the Key Vault. Simply navigate to the Access Policy section under the Settings in the Azure Key Vault instance and click on Add New button.

2-add-new-access-policy

In the Select Principle section, search for the name of the Virtual Machine, (mine is qualityservices) and the newly created Service Principle should appear. Select it and click Select. Then I have given the Get permission for Secret Permissions. Then click on Ok to create the Principle.

3-create-access-policy

Don’t forget to click on Save button to make sure the new Access Policy is Saved. This could be easily missed. Trust me on this one. 😉

4-save

That is, it. Now if the application is deployed to the VM we should be able to access the secret keys from the Key Vault from the Application. When I navigate to the application, and go to the About view, I can now see the random string that was taken from the Azure Key Vault.

5-app-running.PNG

Running the Application Locally.

Yes, we have created a Managed Service Identity for the Virtual Machine that the application is running on. But for local development purposes we don’t have a MSI created. IF you try to run the application now on your local development environment, it will throw an exception trying to access the Key Vault, since the application can not authenticate in to the Azure Key Vault.

To run the application locally, you can use Azure CLI 2.0. Install Azure CLI 2.0 and login to your azure subscription using

az login

Then make sure you are in the correct subscription if you have multiple subscriptions, you have to be in the same subscription where the Key Vault you are trying to access is. If not use the following command to set the correct subscription.

az account set --subscription "your-subscription-id"

Make sure to keep the command line window running and then run the web application locally. You should now be able to access the Key Vault and retrieve the secrets.

6-running-locally

You can download the sample code from the GitHub Repository.

You Might Also Like
Comments