One of the elements of ARM templates that is often overlooked is the capability to write your own functions. The syntax for writing functions in JSON can be a bit cumbersome, especially when comparing to full programming languages, but they can really help to make your ARM templates more readable.

Here is an example that I use in my own ARM templates:

"functions": [
    {
      "namespace": "hb",
      "members": {
        "createKeyVaultReference": {
          "parameters": [
            {
              "name": "keyVaultName",
              "type": "string"
            },
            {
              "name": "secretName",
              "type": "string"
            }
          ],
          "output": {
            "type": "string",
            "value": "[concat('@Microsoft.KeyVault(SecretUri=https://', parameters('keyVaultName'), '.vault.azure.net/secrets/', parameters('secretName'), '/)')]"
          }
        }
      }
    }
  ]

In my templates I frequently use the @Microsoft.KeyVault syntax for AppSettings to reference settings in the Key Vault. It is a very secure and convenient way for working with application secrets. The only downside isthat you have to remember the complete syntax for this notation every single time and have to remember to not forget the trailing slash. That last thing is a mistake that I see frequently. Using a function like this, we can now encode that knowledge in one location and reuse it throughout our template.

After the declaration above, we can invoke this function by prefixing the function name with the name of the function namespace and a dot. So calling the function declared above requires an invocation of hb.createKeyVaultReference:

{
    "name": "appsettings",
    "type": "config",
    "apiVersion": "2015-08-01",
    "dependsOn": [
        "[variables('functionsAppServiceName')]"
    ],
    "properties": {
        "someSetting": "[hb.createKeyVaultReference(variables('keyVaultName'), 'someSetting')]"
    }
}

Here the clutter of concatenating the different parts of the @Microsoft.KeyVault reference string is now removed and the knowledge on how to built that string is moved into one single location, ready for reuse by anyone.

Resources:

  • https://docs.microsoft.com/en-us/azure/azure-resource-manager/templates/template-syntax#functions
  • https://docs.microsoft.com/en-us/azure/azure-resource-manager/templates/template-user-defined-functions