Udostępnij za pośrednictwem


Implementowanie transformatora właściwości i modułu zbierającego w szablonie usługi Azure Resource Manager

W artykule Używanie obiektów jako parametrów w pętli kopiowania w szablonie usługi Azure Resource Manager można zobaczyć, jak przechowywać wartości właściwości zasobów w obiekcie i jak zastosować je do zasobu podczas wdrażania. Jest to bardzo przydatny sposób zarządzania parametrami, ale wymaga mapowania właściwości obiektu na właściwości zasobu za każdym razem, gdy używasz obiektu w szablonie.

Aby obejść ten proces, można zaimplementować szablon przekształcania właściwości i modułu zbierającego, który iteruje tablicę obiektów i przekształca ją w schemat JSON dla zasobu.

Ważne

Takie podejście wymaga dogłębnego zrozumienia szablonów i funkcji Resource Manager.

Przyjrzyjmy się przykładowi, który implementuje moduł zbierający i przekształcanie właściwości w celu wdrożenia sieciowej grupy zabezpieczeń. Na poniższym diagramie przedstawiono, jak nasze szablony są powiązane z zasobami w tych szablonach:

moduł zbierający właściwości i architektura transformatora

Nasz szablon wywołujący zawiera dwa zasoby:

  • Link szablonu, który wywołuje szablon modułu zbierającego
  • Zasób sieciowej grupy zabezpieczeń do wdrożenia

Nasz szablon modułu zbierającego zawiera dwa zasoby:

  • Zasób zakotwiczenia
  • Link szablonu, który wywołuje szablon przekształcenia w pętli kopiowania

Nasz szablon przekształcania zawiera jeden zasób: pusty szablon ze zmienną, która przekształca nasz source kod JSON na schemat JSON, który jest oczekiwany przez nasz zasób sieciowej grupy zabezpieczeń w głównym szablonie.

Obiekt parametru

Używamy obiektu securityRulesparametrów z use objects as parameters in a copy loop in an Azure Resource Manager template (Używanie obiektów jako parametrów w pętli kopiowania w szablonie usługi Azure Resource Manager). Nasz szablon przekształcania przekształca każdy obiekt w tablicy securityRules na schemat JSON, który jest oczekiwany przez zasób sieciowej grupy zabezpieczeń w naszym szablonie wywołującym.

{
    "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentParameters.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "networkSecurityGroupsSettings": {
            "value": {
                "securityRules": [
                    {
                        "name": "RDPAllow",
                        "description": "allow RDP connections",
                        "direction": "Inbound",
                        "priority": 100,
                        "sourceAddressPrefix": "*",
                        "destinationAddressPrefix": "10.0.0.0/24",
                        "sourcePortRange": "*",
                        "destinationPortRange": "3389",
                        "access": "Allow",
                        "protocol": "Tcp"
                    },
                    {
                        "name": "HTTPAllow",
                        "description": "allow HTTP connections",
                        "direction": "Inbound",
                        "priority": 200,
                        "sourceAddressPrefix": "*",
                        "destinationAddressPrefix": "10.0.1.0/24",
                        "sourcePortRange": "*",
                        "destinationPortRange": "80",
                        "access": "Allow",
                        "protocol": "Tcp"
                    }
                ]
            }
        }
    }
}

Najpierw przyjrzyjmy się naszemu szablonowi transformacji .

Przekształć szablon

Nasz szablon przekształcania zawiera dwa parametry przekazywane z szablonu modułu zbierającego:

  • source jest obiektem, który odbiera jeden z obiektów wartości właściwości z tablicy właściwości. W naszym przykładzie każdy obiekt z tablicy securityRules jest przekazywany pojedynczo.
  • state to tablica, która odbiera łączone wyniki wszystkich poprzednich przekształceń. Jest to kolekcja przekształconych danych JSON.

Nasze parametry wyglądają następująco:

{
    "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "source": {
            "type": "object"
        },
        "state": {
            "type": "array",
            "defaultValue": []
        }
    },

Nasz szablon definiuje również zmienną o nazwie instance , która przekształca nasz source obiekt w wymagany schemat JSON:

"variables": {
    "instance": [
        {
            "name": "[parameters('source').name]",
            "properties": {
                "description": "[parameters('source').description]",
                "protocol": "[parameters('source').protocol]",
                "sourcePortRange": "[parameters('source').sourcePortRange]",
                "destinationPortRange": "[parameters('source').destinationPortRange]",
                "sourceAddressPrefix": "[parameters('source').sourceAddressPrefix]",
                "destinationAddressPrefix": "[parameters('source').destinationAddressPrefix]",
                "access": "[parameters('source').access]",
                "priority": "[parameters('source').priority]",
                "direction": "[parameters('source').direction]"
            }
        }
    ]
}

output Na koniec szablon łączy zebrane przekształcenia naszego state parametru z bieżącą transformacją wykonywaną przez naszą instance zmienną:

"resources": [],
"outputs": {
    "collection": {
        "type": "array",
        "value": "[concat(parameters('state'), variables('instance'))]"
    }
}

Następnie przyjrzyjmy się naszemu szablonowi modułu zbierającego , aby zobaczyć, jak przekazuje nasze wartości parametrów.

Szablon modułu zbierającego

Nasz szablon modułu zbierającego zawiera trzy parametry:

  • source jest naszą kompletną tablicą obiektów parametrów. Jest on przekazywany przez szablon wywołujący. Ma taką samą nazwę jak source parametr w szablonie przekształcania, ale istnieje jedna kluczowa różnica: chociaż jest to kompletna tablica, przekazujemy tylko jeden element tablicy jednocześnie do szablonu transformacji.
  • transformTemplateUri to identyfikator URI naszego szablonu transformacji. Definiujemy go jako parametr umożliwiający ponowne użycie szablonu.
  • state jest początkowo pustą tablicą, którą przekazujemy do naszego szablonu transformacji. Przechowuje kolekcję przekształconych obiektów parametrów po zakończeniu pętli kopiowania.

Nasze parametry wyglądają następująco:

"parameters": {
    "source": {
        "type": "array"
    },
    "transformTemplateUri": {
        "type": "string"
    },
    "state": {
        "type": "array",
        "defaultValue": []
    }
}

Następnie zdefiniujemy zmienną o nazwie count. Jego wartością jest długość tablicy obiektów parametrów source :

"variables": {
    "count": "[length(parameters('source'))]"
}

Używamy go dla liczby iteracji w naszej pętli kopiowania.

Teraz przyjrzyjmy się naszym zasobom. Definiujemy dwa zasoby:

  • loop-0 to zasób oparty na zera dla naszej pętli kopiowania.
  • loop- element jest połączony z wynikiem copyIndex(1) funkcji w celu wygenerowania unikatowej nazwy opartej na iteracji dla naszego zasobu, zaczynając od 1.

Nasze zasoby wyglądają następująco:

"resources": [
    {
        "type": "Microsoft.Resources/deployments",
        "apiVersion": "2015-01-01",
        "name": "loop-0",
        "properties": {
            "mode": "Incremental",
            "parameters": { },
            "template": {
                "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
                "contentVersion": "1.0.0.0",
                "parameters": { },
                "variables": { },
                "resources": [ ],
                "outputs": {
                    "collection": {
                        "type": "array",
                        "value": "[parameters('state')]"
                    }
                }
            }
        }
    },
    {
        "type": "Microsoft.Resources/deployments",
        "apiVersion": "2015-01-01",
        "name": "[concat('loop-', copyindex(1))]",
        "copy": {
            "name": "iterator",
            "count": "[variables('count')]",
            "mode": "serial"
        },
        "dependsOn": [
            "loop-0"
        ],
        "properties": {
            "mode": "Incremental",
            "templateLink": { "uri": "[parameters('transformTemplateUri')]" },
            "parameters": {
                "source": { "value": "[parameters('source')[copyindex()]]" },
                "state": { "value": "[reference(concat('loop-', copyindex())).outputs.collection.value]" }
            }
        }
    }
]

Przyjrzyjmy się bliżej parametrom przekazywanym do szablonu przekształcenia w szablonie zagnieżdżonym. Jak pamiętasz, source nasz parametr przekazuje bieżący obiekt w tablicy obiektów parametrów source . Parametr state to miejsce, w którym odbywa się kolekcja, ponieważ pobiera dane wyjściowe poprzedniej iteracji pętli kopiowania i przekazuje ją do bieżącej iteracji. Zwróć uwagę, że reference() funkcja używa copyIndex() funkcji bez parametru w celu odwołania name się do poprzedniego połączonego obiektu szablonu.

output Na koniec szablon zwraca output ostatnią iterację naszego szablonu przekształcenia:

"outputs": {
    "result": {
        "type": "array",
        "value": "[reference(concat('loop-', variables('count'))).outputs.collection.value]"
    }
}

Może się wydawać nieintuicyjne, aby zwrócić output ostatnią iterację naszego szablonu transformacji do naszego szablonu wywołującego, ponieważ wydaje się, że przechowujemy go w naszym source parametrze. Jest to jednak ostatnia iteracja naszego szablonu przekształcania , która zawiera pełną tablicę przekształconych obiektów właściwości i to właśnie chcemy zwrócić.

Na koniec przyjrzyjmy się, jak wywołać szablon modułu zbierającego z naszego szablonu wywołującego.

Szablon wywołujący

Nasz szablon wywołujący definiuje pojedynczy parametr o nazwie networkSecurityGroupsSettings:

...
"parameters": {
    "networkSecurityGroupsSettings": {
        "type": "object"
    }
}

Następnie nasz szablon definiuje pojedynczą zmienną o nazwie collectorTemplateUri:

"variables": {
    "collectorTemplateUri": "[uri(deployment().properties.templateLink.uri, 'collector.template.json')]"
}

Jest to identyfikator URI szablonu modułu zbierającego , który jest używany przez nasz połączony zasób szablonu:

{
    "apiVersion": "2020-06-01",
    "name": "collector",
    "type": "Microsoft.Resources/deployments",
    "properties": {
        "mode": "Incremental",
        "templateLink": {
            "uri": "[variables('collectorTemplateUri')]",
            "contentVersion": "1.0.0.0"
        },
        "parameters": {
            "source": {
                "value": "[parameters('networkSecurityGroupsSettings').securityRules]"
            },
            "transformTemplateUri": {
                "value": "[uri(deployment().properties.templateLink.uri, 'transform.json')]"
            }
        }
    }
}

Przekazujemy dwa parametry do szablonu modułu zbierającego:

  • source to nasza tablica obiektów właściwości. W naszym przykładzie jest to nasz networkSecurityGroupsSettings parametr.
  • transformTemplateUri to zmienna, która została właśnie zdefiniowana za pomocą identyfikatora URI szablonu modułu zbierającego.

Na koniec zasób Microsoft.Network/networkSecurityGroups bezpośrednio przypisuje output zasób połączonego collector szablonu do jego securityRules właściwości:

"resources": [
    {
        "apiVersion": "2020-05-01",
        "type": "Microsoft.Network/networkSecurityGroups",
        "name": "networkSecurityGroup1",
        "location": "[resourceGroup().location]",
        "properties": {
            "securityRules": "[reference('collector').outputs.result.value]"
        }
    }
],
"outputs": {
    "instance": {
        "type": "array",
        "value": "[reference('collector').outputs.result.value]"
    }
}

Wypróbuj szablon

Przykładowy szablon jest dostępny w witrynie GitHub. Aby wdrożyć szablon, sklonuj repozytorium i uruchom następujące polecenia interfejsu wiersza polecenia platformy Azure :

git clone https://github.com/mspnp/template-examples.git
cd template-examples/example4-collector
az group create --location <location> --name <resource-group-name>
az deployment group create -g <resource-group-name> \
    --template-uri https://raw.githubusercontent.com/mspnp/template-examples/master/example4-collector/deploy.json \
    --parameters deploy.parameters.json

Następne kroki