2

I have a parent template that takes an array (websites) and invokes a childTemplate (website) multiple times using the copyIndex() method to loop through values in the array passed as a parameter.

Each of the child templates returns -- in its outputs -- the MSI principalId, as well as outgoingIPAddresses.

Is there a way one can assemble the returned individual principalId values into an array that can be used by subsequent child template invoked by the parent template (in order to loop through the resulting array of principalIds and give them all the same rights to a KeyVault)?

Thank you.

1 Answers1

1

Yes, this can be done, although, not as pretty\easy as you would like it to.

easiest way to do this, is assemble an array of values you need using output from the templates. you need each your template to take the output from the previous one and concat it with its own output and spit the result as an output. sample code:

    {
        "name": "reference0", << this one is needed so that the first real one has something to reference, as it cant reference itself
        "type": "Microsoft.Resources/deployments",
        "apiVersion": "2015-01-01",
        "properties": {
            "mode": "Incremental",
            "templateLink": {
                "uri": "yourtemplate",
                "contentVersion": "1.0.0.0"
            }
        },
        "parameters": {
            "state": {
                "value": []
            }
        }
    },
    {
        "name": "[concat('reference', copyIndex(1))]",
        "type": "Microsoft.Resources/deployments",
        "apiVersion": "2015-01-01",
        "copy": {
            "name": "loop",
            "count": "[variables('types')[resourceGroup().name]]"
        },
        "properties": {
            "mode": "Incremental",
            "templateLink": {
                "uri": "yourtemplate",
                "contentVersion": "1.0.0.0"
            },
            "parameters": {
                "state": {
                    "value": "[reference(concat('loop', copyIndex())).outputs.state.value]"
                }
            }
        }
    },

and your state output should just be something like this:

"outputs": {
    "state": {
        "type": "array",
        "value": "[concat(parameters('state'), array(your_actual_output))]"
}
4c74356b41
  • 69,186
  • 6
  • 100
  • 141
  • 1
    Thanks! Much appreciated: will get me out of a right pickly. PS: at this point, I've noticed its par for the course -- *nothing* is easy/pretty in ARM :-) – user10637838 Nov 12 '18 at 20:02
  • well, i wouldnt go that far, but certainly for anything remotely complex\flexible i tend to fight the syntax\work around weird behaviours mostly (oh and brackets) – 4c74356b41 Nov 12 '18 at 20:26
  • I'm ok with the brackets (ex-Lisper). It's the trailing non-JSON commas that get me. Anyway. Do you know if the above still works without having applying "mode": "serial", "batchSize": 1 as per https://learn.microsoft.com/en-us/azure/azure-resource-manager/resource-group-create-multiple ? – user10637838 Nov 13 '18 at 05:30
  • yes, because they all depend on each other, you dont need to change mode. also, vsts is (for example) is pretty good with commas. no so good with brackets – 4c74356b41 Nov 13 '18 at 05:50
  • How do you actually reference this elsewhere? Surely the last element in the copy is the one that has the full list of state? – David C Sep 13 '19 at 15:29
  • please raise a question and ping me the question url here, I'm not sure what you are asking exactly – 4c74356b41 Sep 13 '19 at 16:06
  • https://stackoverflow.com/questions/57927815/arm-template-how-to-reference-a-copyindex-deployment-output – David C Sep 13 '19 at 17:13