Menu Home

Azure Service Bus Queues and SAS with ARM templates

Previously I posted about how to create Azure Service Bus topics with ARM templates. This post is a follow up where I show how to create Service Bus queues (in case you didn’t figure it out already). In addition I will also, by popular demand, show how to create Shared Access Signatures policies for a specific queue instead of for the entire namespace as I did in the first post.

Lets look at the complete template. To shorten the template I have not included my trick to generate the primary and secondary keys in this template, but you can read about it in my first post.

{
  "$schema": "http://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
  "contentVersion": "1.0.0.0",
  "parameters": {
    "sbNamespace": {
      "type": "string",
      "metadata": {
        "description": "The service bus namespace"
      }

    },
    "primaryKey": {
      "type": "string",
      "defaultValue": "DG4TcCs+XnDN83VZcT2e5NfVeSFvTuiYUiWtXhxnJ2s="
    },
    "secondaryKey": {
      "type": "string",
      "defaultValue": "tegikp1IoeEFCF9NRSV78nYomDlFjsz21X9aVKPL4Eo="
    }
  },
  "variables": {
    "location": "[resourceGroup().location]",
    "sbVersion": "2014-09-01",
    "namespaceName": "[concat(parameters('sbNamespace'),uniqueString(resourceGroup().id))]",   
    "queueName": "testQueue"
  },
  "resources": [
    {
      "apiVersion": "[variables('sbVersion')]",
      "name": "[variables('namespaceName')]",
      "type": "Microsoft.ServiceBus/namespaces",
      "location": "[variables('location')]",
      "properties": {
        "messagingSku": 2
      },
      "resources": [
        {
          "apiVersion": "[variables('sbVersion')]",
          "name": "[variables('queueName')]",
          "type": "Queues",
          "dependsOn": [
            "[concat('Microsoft.ServiceBus/namespaces/', variables('namespaceName'))]"
          ],
          "properties": {
            "path": "[variables('queueName')]"
          },
          "resources": [
            {
              "apiVersion": "[variables('sbVersion')]",
              "name": "ReadOnlyKey",
              "type": "AuthorizationRules",
              "dependsOn": [
                "[variables('queueName')]"
              ],
              "properties": {
                "keyName": "ReadOnlyKey",
                "claimType": "SharedAccessKey",
                "claimValue": "None",
                "primaryKey": "[parameters('primaryKey')]",
                "secondaryKey": "[parameters('secondaryKey')]",
                "rights": [ "Send" ],
                "revision": -1
              }
            },
            {
              "apiVersion": "[variables('sbVersion')]",
              "name": "ListenOnlyKey",
              "type": "AuthorizationRules",
              "dependsOn": [
                "[variables('queueName')]"
              ],
              "properties": {
                "keyName": "ListenOnlyKey",
                "claimType": "SharedAccessKey",
                "claimValue": "None",
                "primaryKey": "[parameters('primaryKey')]",
                "secondaryKey": "[parameters('secondaryKey')]",
                "rights": [ "Listen" ],
                "revision": -1
              }
            }
          ]
        }

      ]
    }
  ],
  "outputs": {

  }
}

Creating a Service Bus queue, is very similar to create a topic. You add the following to the resource collection of the namespace.

{
          "apiVersion": "[variables('sbVersion')]",
          "name": "[variables('queueName')]",
          "type": "Queues",
          "dependsOn": [
            "[concat('Microsoft.ServiceBus/namespaces/', variables('namespaceName'))]"
          ],
          "properties": {
            "path": "[variables('queueName')]"
          },
          "resources": []
}

In order to create Shared Access Signature policies for this specific queue, we have to use the resource collection.

An access policy for that allows you to listen to the queue can be made with.

{
              "apiVersion": "[variables('sbVersion')]",
              "name": "ReadOnlyKey",
              "type": "AuthorizationRules",
              "dependsOn": [
                "[variables('queueName')]"
              ],
              "properties": {
                "keyName": "ReadOnlyKey",
                "claimType": "SharedAccessKey",
                "claimValue": "None",
                "primaryKey": "[parameters('primaryKey')]",
                "secondaryKey": "[parameters('secondaryKey')]",
                "rights": [ "Send" ],
                "revision": -1
              }
            }

The template is quite similar to that for creating shared access signature policies for namespaces. The few things to note are

  • The type should just be AuthorizationRules
  • The depends on should at least contain the parent resource (don’t ask me why this is a requirement, I think it is stupid, the Azure Resource Manager should be able to deduct that dependency, but if you leave it out you get an error when trying to deploy the template)
  • The claim type should be SharedAccessKey
  • Keyname and name of the resource should match

If you want to grab it from github, I have updated the repository from the first post, you find it here: https://github.com/sjkp/Azure.ARM.ServiceBus

For people who are wondering how I was able to find out how to do this, I can recommend using ARMClient, with ARM client you can quickly create requests to the different ARM endpoints to probe what they return, after you have created the resource in the portal. You can also use resources.azure.com, but that tool doesn’t work for Service Bus, whereas the ARM clients work for all Azure Resource Manager providers, as long as you are able to guess the endpoints (which for most parts are quite easy, as the endpoints are logically named REST endpoints.)
armclient

Categories: Windows Azure

Tagged as:

Simon J.K. Pedersen

14 replies

  1. Hi Simon,
    Thanks for this article and for the ARMClient info. Is there a way to generate primary and secondary keys on the go and for them to be fully random (other than the trick from previous post)? Also you can get list of all providers, locations available and api versions from https://management.azure.com/subscriptions/yoursubscriptionId/providers?$skiptoken={skiptoken}&api-version=2015-01-01 using fiddler or postman Content-Type is application/ json and Authorization is Bearer token acquired from AuthenticationContext

  2. Hi Milen,

    I don’t think there is ARM way to get the keys generated fully random. If it exists I don’t know about it. But I will pass it on to some folks at Microsoft.

    Thanks for the tips about listen the providers 🙂

  3. Ok, thanks for doing this. The only reason I’m asking is that I have a copy operation and I’d like to assign unique Read and Listen keys for each queue that I’m creating.

  4. I got a reply from Ryan Jones, the arm template are not supposed to be random, they have to be deterministic (so we can run them multiple times without side effects) so they have no plan to implement a real random function.

  5. First of all, thank you for blogging about this! This saves me a lot of time (and headaches) figuring out how to do it!

    A quick question: I noticed that in the previous (Topic) example you used a readable namespace, while in this (Queue) example it is postfixed with the id of the resourcegroup resulting in an ugly (i.e. difficult to remember) name. I am wondering what the reasoning behind that is? Is it necessary for some scenario, or ‘just for fun’ 🙂

    Thanks again!
    Reinhard

  6. Simon,

    Thanks for the article. Very well written, and has helped in my understanding of ARM templates. I am very new to Azure and ARM, and still have a lot of learning to do. How does one determine find the child resource options (and syntax) under Service Bus? I have gone to the 2015-01-01 schema and looked at all the files, and I can’t even find a reference to the Microsoft.ServiceBus provider. Any guidance you can provide for educating myself would be greatly appreciated.

  7. I trying to move away from manually created names, with many of my resources where the name is not visible to the outside world. The reason is that, I should never really care about the resource after it is created and I via the arm template set the connection string to it. For service bus it is really nice, not to use manually created name, because the service bus namespaces are reserved for a week after they are deleted, so if I delete the entire resource group and provision it again with the same name it will fail.

  8. Thanks for a very useful blog! I’m having trouble with ARMClient GET for a service bus ARM resource when the resource name contains the path delimiter character “/”, as a service bus topic might do, for instance “orders/new”.
    I’ve tried escaping with %2F and various variants of this with no luck:
    ARMClient.exe GET /subscriptions/xx/resourceGroups/myresgroup/providers/Microsoft.ServiceBus/namespaces/myns/topics/producs%2Fnew?api-version=2014-09-01
    Error returned is “No HTTP resource was found that matches the request URI”
    It works fine for topics with simple names like “foo”. Have you came across this before or have any idea how this can be handled?

    Thanks,

    /Asle

Leave a Reply

Your email address will not be published. Required fields are marked *