如何通过资源类型和标识符识别ARM模板中的天蓝色资源是否存在
答案 0 :(得分:9)
实际上是可能的。您可以使用资源组标签来标记当前已部署的版本,如果设置了标签,则可以跳过部署。所有这些都可以通过链接模板来实现。
请注意,我们本身并不检查资源是否存在,但仍然允许编写可能包含一次初始化模板的ARM模板。如果资源组被删除并且资源丢失(如果您再次创建了资源组),则最后一个将还原资源。您可以扩展它以支持每个资源的标签,这在某些情况下会更加有用。
开始部署的模板可能如下所示:
{
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"DeploymentTemplateLink": {
"type": "string"
},
"DeploymentVersion": {
"defaultValue": 1,
"type": "int"
}
},
"variables": {
"rgWithDefaultVersion": {
"tags": {
"Version": "0"
}
}
},
"resources": [
{
"type": "Microsoft.Resources/deployments",
"apiVersion": "2017-05-10",
"name": "DeploymentTemplate",
"condition": "[less(int(union(variables('rgWithDefaultVersion'), resourceGroup()).tags['Version']), parameters('DeploymentVersion'))]",
"properties": {
"mode": "Incremental",
"templateLink": {
"uri": "[parameters('DeploymentTemplateLink')]",
"contentVersion": "1.0.0.0"
},
"parameters": {
"DeploymentVersion": {
"value": "[parameters('DeploymentVersion')]"
}
}
}
}
]
}
链接的模板的条件会查询标记,并且仅当当前版本(存储在标记中)小于请求的版本时才返回true。实际上,您不必维护版本控制:只需不设置 DeploymentVersion 参数,它将仅在第一次部署。如果仍然决定重新部署,则始终可以选择增加版本,这将导致链接模板的部署(也称为“主部署”)。
主部署模板在您身上,但是它应该包含一个 tags 资源,以维护逻辑。
{
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"DeploymentVersion": {
"defaultValue": 1,
"type": "int"
}
},
"variables": {},
"resources": [
{
"type": "Microsoft.Resources/tags",
"name": "default",
"apiVersion": "2019-10-01",
"dependsOn": [],
"properties": {
"tags": {
"Version": "[string(parameters('DeploymentVersion'))]"
}
}
}
]
}
注释,用于那些不了解 union()和 rgWithDefaultVersion 的人。如果引用的对象不包含属性,则ARM模板部署将失败。在我们的例子中,我们有两个这样的属性:'tags'和'Version'。 “标签” 仅在特定资源组具有或曾经具有标签的情况下存在。 “版本” 仅在我们已经编写一次之后(在主部署中)才存在。因此,在访问它们之前,我们使用适当的默认值对返回的对象执行 union()操作,以确保我们可以安全地访问所提到的属性。
答案 1 :(得分:1)
在手臂模板中无法做到这一点。您可以使用一些外部源(例如powershell)来确定并传递具有适当值的参数,或者,您可以使用标签来弄清楚(具有表示资源存在/不存在的标签)。
答案 2 :(得分:0)
资源管理器提供以下用于获取资源值的功能:Resource functions for Azure Resource Manager templates
您可以用一块powershell来包装模板,无论使用哪种方法,它都会确定资源是否存在,并根据该参数传递参数值,并在模板中使用条件语句,该条件语句将根据输入(但是输入必须来自其他地方)
答案 3 :(得分:0)
您可能会发现https://docs.microsoft.com/en-us/azure/developer/terraform/overview对解决您的案件很有帮助。
Hashicorp Terraform是用于置备和管理云基础架构的开源工具。它将基础结构编入描述云资源拓扑的配置文件中。这些资源包括虚拟机,存储帐户和网络接口。 Terraform CLI提供了一种简单的机制来将配置文件部署和版本化到Azure。
但这需要您离开ARM模板。
答案 4 :(得分:-1)
最近我需要一个解决方案来基本上对SQL Server进行增量更新。既然你做不到,模板将失败,并显示NameAlreadyExists错误。 因此,我需要检查资源是否存在,并仅在不存在的情况下创建。
添加“条件”检查,确定天蓝色资源ID是否存在;不要创建它。
{
...
"condition": "[empty(resourceId('[resourceGroup().id]', 'Microsoft.SQL/servers', parameters('serverName')))]",
...
}
您可以对任何资源类型执行此操作。