Azure Key Vault is a powerful resource to have when deploying your applications in Microsoft Azure. This article will cover some integrations that can be made in Azure DevOps to allow the provision of the Key Vault and populate it with some data that can be used down the road by other components in the pipeline.
Naming convention is the key to success
The naming convention is key for any successful infrastructure-as-code (IaC) endeavor. Some people like to pass parameters for the name of the objects. However, it is completely supported and used. As you get larger environments, the work required to connect all parameters with the implementation may become cumbersome.
The recommendation is to create a strong naming convention that doesn’t matter where you are. You can always find the resources based on the naming convention. The names can be constructed as variables, thus eliminating the input from end-users, and it will make our code more consistent and resilient across environments.
In this article, we will use two-three digits for the resource, the region code, the environment, and the name of the application. A simple example of this naming convention would be the Key Vault label as KV-CaC-DEV-ProjectX
Provisioning Azure Key Vault and some tricks from the field
To provision a Key Vault, we need just the name (Item 1). However, in our code, we will add access policies (Item 2) and network ACLS (Item 3) from the parameters files. All other values from the template are standard, and you can change them based on your current corporate standards (for example: enable purge protection, the number of days for sot deleted content, and so forth).
Since we mentioned the parameters that we will require, here is a list of all parameters that we will require in our ARM template.
We have to perform a slight detour in our article to determine the ObjectID of the service principal running the Azure DevOps release pipeline. That is important because we will use that account to assign permission in the Key Vault Access Policies, and that will give us enough reach to add information to the Azure Key Vault during deployment time. How cool is that?
For this article, we will create a simple pipeline that deploys our code (pretty much an Azure Key Vault with all the features discussed in this article). In the pipeline, we need to find out information about our Azure Resource Manager Connection by clicking on Manage (Item 1).
Note: If you are not certain how to get the release pipeline up and running, please look at my series that shows how to do that from scratch. Here is the link.
On the new page, click on Manage Service Principal. We will be redirected to the Azure Active Directory. On this page, we will configure the name of the Service Principal. Click on Branding (Item 1), define the name (in our case AP6Labs-Techgenix.svc.account, as shown in Item 2), finally click on Save (Item 3).
If we go back to the Overview page, we can gather the Tenant ID, which will be used later in this article.
One last stop before going back to the code is finding the ObjectID of the Service Principal account that we are using the Azure DevOps.
Open Azure Active Directory item in the Azure Portal, click on Enterprise Applications. In the new blade, select All applications, and type the name of the service principal. Click on it from the list below.
We found it! Copy the Object ID highlighted in the image below. We will need that information in our parameters file waiting for us in our repository in Azure DevOps.
The last step is to go to the parameter files (in this article, we labeled them as keyvault.dev.json), and we need to define the parameters, such as environment, region code, Key Vault Network ACLs, and the Access Policies.
The Access Policies are highlighted in the image below. We need to provide the objectID and tenantID, and the permissions we want for either secret, key, or certificate.
After deploying the Azure Key Vault using the code that we covered so far, the result will be a new entry in the access policies to our service principal account and the permissions defined in the parameters file.
Populating a new Key Vault from the release pipeline
We have all plumbing required to go the next step: populate a Key Vault with keys, secrets, and certs as part of the Azure DevOps pipeline!
We’ll create two files to support this initiative (keyvault.csv and keyvault.ps1). The CSV file will have two columns (name and secret). We will populate that with information that can be added to the repo or static values, but we will also use the random string to generate a strong string during the execution and add it to the Azure Key Vault.
The PowerShell script created for this exercise is simple: We receive a single argument (environment), which will help us create the Key Vault name within the script. The second step is to load the Azure Key Vault modules, the CSV file, and check each one of the secrets that exist in the Vault. If they do not, we will create them accordingly.
We use a function to create a random password. (I found that one on the Internet and tweak it a little to meet my requirements.)
In the current release pipeline, we need to add new tasks from the Azure PowerShell type and specify the subscription, the script file, and the environment. Using a variable that matches the stage name is useful when we copy stages. As long as we label them with the proper environment name, the script will be receiving the right value.
After running our updated release pipeline, the result is a bunch of secrets that we defined in our CSV file. Some of them have static values, some have randomly generated strings used by other components of the pipeline that nobody is aware of the data.
Keys to the Azure Key Vault
In this article, we described a couple of basic steps that, when combined, allow us to go deeper in the Azure DevOps implementation and even load Azure Key Vault with values required for future deployments throughout the pipeline. The PowerShell script is simple but checks to see if there are secrets already in place. If there are, no actions are taken. We can apply the same idea and import certificates, and even use Key Vault to retrieve the certificate password during the import process.
Featured image: Pixabay