Ever wondered what other properties are available in ARM template objects? Like for instance I can do resourceGroup().name
to get a Resource Group’s name, or resourceGroup().location
to get its location. I never wondered much to be honest until today when I was playing with an ARM template to create a key vault, a key, and a disk encryption set that makes use of this key… and one of the things I had to do was feed the URL of the key to the disk encryption set template.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
{ "name": "string", "type": "Microsoft.Compute/diskEncryptionSets", "apiVersion": "2020-09-30", "location": "string", "tags": {}, "identity": { "type": "string" }, "properties": { "encryptionType": "string", "activeKey": { "sourceVault": { "id": "string" }, "keyUrl": "string" } } } |
That brought me to the reference
function in ARM templates. This can create a reference to any object and you can refer to the properties of these objects. It’s very simple actually, using this, to figure out what properties an object has.
For instance, I want to find the key URL. All I have to do is make an ARM template like this:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
{ "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", "contentVersion": "1.0.0.0", "parameters": { "keyvaultName": { "type": "string" }, "keyName": { "type": "string" } }, "resources": [ ], "outputs": { "fullReferenceOutput": { "type": "object", "value": "[reference(resourceId(resourceGroup().name, 'Microsoft.KeyVault/vaults/keys', parameters('keyvaultName'), parameters('keyName')), '2019-09-01', 'Full')]" } } } |
This takes as parameter input the key vault & key names, and gives as output a reference to the key. Since I am not deploying the key vault or key as part of this template (note the resources
section is blank) I have to create a resourceId()
to the object and get a reference to that. I also have to specify the API version of the resource. The Full
parameter is optional and gives you all the properties, I could have skipped that I suppose but no harm as this gives me an idea of what all is available.
I can run the above template thus to get the properties of the key I am passing in the command line:
1 2 3 4 |
az deployment group create \ --resource-group myResourceGroup \ --template-file azdeploy.json \ --parameters keyvaultName=my-keyvault keyName=mykey |
The output looks similar to this:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
"outputs": { "fullReferenceOutput": { "type": "Object", "value": { "apiVersion": "2019-09-01", "condition": true, "isAction": false, "isConditionTrue": true, "isTemplateResource": false, "location": "northeurope", "properties": { "attributes": { "created": 1616419086, "enabled": true, "recoveryLevel": "Recoverable", "updated": 1616419086 }, "keyOps": [ "encrypt", "decrypt", "sign", "verify", "wrapKey", "unwrapKey" ], "keySize": 4096, "keyUri": "https://my-keyvault.vault.azure.net/keys/mykey", "keyUriWithVersion": "https://my-keyvault.vault.azure.net/keys/mykey/292c21eeaa59464c8810dc4ea7f62baa", "kty": "RSA" }, "provisioningOperation": "Read", "referenceApiVersion": "2019-09-01", "resourceGroupName": "myResourceGroup", "resourceId": "Microsoft.KeyVault/vaults/my-keyvault/keys/mykey", "scope": "", "subscriptionId": "2aaaabec-feaf-428e-abb6-88b0ccf21bfc" } } }, |
This way I know keyUriWithVersion
is what I am interested in and I can refer to it thus: "[reference(resourceId('Microsoft.KeyVault/vaults/keys', variables('keyvaultName'), variables('keyName')), '2019-09-01', 'Full').properties.keyUriWithVersion]"
Similarly, once I create the disk encryption set it has a system assigned ID and I need to identify that so I can give it permissions to the key vault. I haven’t figured out how to give permissions yet, but now I know I can get the identity property via: "[reference(resourceId('Microsoft.Compute/diskEncryptionSets', variables('diskencsetName')), '2019-07-01', 'Full').identity.PrincipalId]"
I figured this via another template file, similar to the one above:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
{ "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", "contentVersion": "1.0.0.0", "parameters": { "diskencsetname": { "type": "string" } }, "resources": [ ], "outputs": { "fullReferenceOutput": { "type": "object", "value": "[reference(resourceId(resourceGroup().name, 'Microsoft.Compute/diskEncryptionSets', parameters('diskencsetname')), '2019-07-01', 'Full')]" } } } |
In the case of the disk encryption set I could have found the property name from the exported ARM template so I didn’t really need to do the above. But in the case of the key there wasn’t a way to get it as an ARM template so the above was useful.