I’m a big fan of Test Kitchen for testing Chef, and I really like the
kitchen-azurerm driver. I started my client with it two years ago, and they’re using it for all of their cookbook CI/CD now. It’s fantastic. However, we’ve had a little nagging problem ever since we started using it: what to do with that darn client secret of the service principal. We had been saving it as an environment variable both on our workstations and on Jenkins, but you can see why that’s not desirable - too easy to let it lose out into the wild.
Last fall, Microsoft introduced Azure Managed Identities. In its documentation, they outline our problem exactly:
A common challenge when building cloud applications is how to manage the credentials in your code for authenticating to cloud services. Keeping the credentials secure is an important task. Ideally, the credentials never appear on developer workstations and aren’t checked into source control. Azure Key Vault provides a way to securely store credentials, secrets, and other keys, but your code has to authenticate to Key Vault to retrieve them.
To solve this, they created managed identities. Basically, you create a “user-assigned managed identity” in your subscription as a stand-alone resource. From there, Azure assigns that resource an Active Directory identity - kind of like creating a service principal. But then, unlike a service principal that you use on a machine, you assign this identity to a machine, and now that machine has all of the permissions assigned to the managed identity. I love this. I think it’s so convenient.
Problem solved, right? Oh, but how can I assign an identity to my test kitchen nodes? Well, you couldn’t until recently when zanecodes added its functionality to the kitchen-azurerm driver.
Now, all you have to do is create a Test Kitchen identity resource in your subscription with all of the permissions that it needs, nothing less, nothing more. And then add that one little line
user_assigned_identities to the driver section of the
.kitchen.yml of your cookbook.
driver: name: azurerm subscription_id: '555-your-sub-id-here-555' location: 'Central US' machine_size: 'Standard_D2_V2' image_urn: MicrosoftWindowsServer:WindowsServer:2016-Datacenter:latest user_assigned_identities: - /subscriptions/555-your-sub-id-here-555/resourcegroups/test_kitchen_stuff/providers/Microsoft.ManagedIdentity/userAssignedIdentities/test-kitchen-identity
And you can remove that dreaded client secret from your environment variables! Yay for security!