azure - 如何使用 ARM 模板副本有条件地为存储帐户提供 N 个角色分配?
问题描述
我正在尝试提供 N 个存储帐户、N 个角色分配(每个存储帐户 1 个)来授予对特定身份的访问权限,但只能有条件地部署角色分配。存储帐户和身份已经存在,并且它们的模板逻辑已经工作了一段时间。
如果我尝试部署以下模板片段,我会在“[concat(parameters('BackupStorageAccountRoleAssignmentsDeployment')[0].AccountName, '/Microsoft.Authorization /', guid(parameters('BackupStorageAccountRoleAssignmentsDeployment')[0].Name))]'" 当角色分配的输入数组为空时。
我已经在使用技巧将长度为 0 的副本强制为长度 = 1,然后在某个条件下保护部署。我尝试了使用大小为 1 的默认数组的变体,将我的角色分配部分移动到一个嵌套模板中,并手动将我的循环展开为 4 个角色分配。无论如何,我遇到了同样的错误。这个片段有什么问题?
{
"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"RoleAssignments": {
"type": "array"
},
"IdentityName": {
"type": "string"
},
"StorageAccounts": {
"type": "array"
}
},
"variables": {
"IdentityResourceId": "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', parameters('IdentityName'))]"
},
"resources": [
{ // Everything related to role assignments chokes completely, even if I unroll the loop
"dependsOn": [
"[variables('IdentityResourceId')]",
"storageaccountcopy"
],
"copy": {
"name": "RoleAssignmentsCopy",
"count": "[max(length(parameters('BackupStorageAccountRoleAssignmentsDeployment')), 1)]"
},
"condition": "[greater(length(parameters('RoleAssignments')), 0)]",
"type": "Microsoft.Storage/storageAccounts/providers/roleAssignments",
"apiVersion": "2020-04-01-preview",
"name": "[concat(parameters('RoleAssignments')[copyIndex()].AccountName, '/Microsoft.Authorization/', guid(parameters('RoleAssignments')[copyIndex()].Name))]",
"properties": {
"roleDefinitionId": "[parameters('RoleAssignments')[copyIndex()].RoleDefinitionId]",
"principalId": "[if(and(empty(parameters('RoleAssignments')[copyIndex()].ResourceId), not(empty(parameters('RoleAssignments')[copyIndex()].PrincipalId))),
parameters('RoleAssignments')[copyIndex()].PrincipalId,
reference(parameters('RoleAssignments')[copyIndex()].ResourceId, '2018-11-30').PrincipalId)]",
"scope": "[parameters('RoleAssignments')[copyIndex()].Scope]",
"principalType": "[parameters('RoleAssignments')[copyIndex()].PrincipalType]"
}
},
{ // Everthing related to storage account provisioning works fine, this was existing code
"condition": "[and(greater(length(parameters('StorageAccounts')), 0), not(parameters('SkipStorageAccountProvisioning')), equals(parameters('StorageAccountProvisioningDefault'), 'true'))]",
"copy": {
"name": "storageaccountcopy",
"count": "[length(parameters('StorageAccounts'))]"
},
"type": "Microsoft.Storage/storageAccounts",
"apiVersion": "2019-06-01",
"name": "[parameters('StorageAccounts')[copyIndex()].AccountName]",
"location": "[resourceGroup().location]",
"sku": {
"name": "[if(equals(parameters('StorageAccounts')[copyIndex()].AccountTypeOverride, parameters('StorageAccountTypeOverrideDefault')), parameters('StorageAccounts')[copyIndex()].AccountType, parameters('StorageAccounts')[copyIndex()].AccountTypeOverride)]",
"tier": "Standard"
},
"kind": "[parameters('StorageAccounts')[copyIndex()].AccountKind]",
"properties": {
"networkAcls": {
"bypass": "AzureServices",
"virtualNetworkRules": [],
"ipRules": [],
"defaultAction": "Allow"
},
"supportsHttpsTrafficOnly": true,
"encryption": {
"services": {
"file": {
"keyType": "Account",
"enabled": true
},
"blob": {
"keyType": "Account",
"enabled": true
}
},
"keySource": "Microsoft.Storage"
}
}
}
]
}
编辑:
根据反馈,我尝试将片段移动到嵌套模板中。以完全相同的错误失败,The template resource '[concat(parameters('RoleAssignments')[copyIndex()].AccountName, '/Microsoft.Authorization/', guid(parameters('BackupStorageAccountRoleAssignments')[copyIndex()].Name))]' at line '1' and column '837' is not valid: The language expression property array index '0' is out of bounds..
{
"dependsOn": [
"[variables('IdentityResourceId')]"
],
"type": "Microsoft.Resources/deployments",
"apiVersion": "2020-10-01",
"name": "RoleAssignmentsDeployment",
"properties": {
"mode": "Incremental",
"expressionEvaluationOptions": {
"scope": "inner"
},
"parameters": {
"RoleAssignments": {
"value": "[parameters('RoleAssignmentsDeployment')]"
}
},
"template": {
"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"RoleAssignments": {
"type": "array"
}
},
"resources": [
{
"dependsOn": [
"[resourceId('Microsoft.Storage/storageAccounts', parameters('RoleAssignments')[copyIndex()].AccountName)]"
],
"copy": {
"name": "RoleAssignmentsDeploymentCopy",
"count": "[max(length(parameters('RoleAssignments')), 1)]"
},
"condition": "[greater(length(parameters('RoleAssignments')), 0)]",
"type": "Microsoft.Storage/storageAccounts/providers/roleAssignments",
"apiVersion": "2020-10-01",
"name": "[concat(parameters('RoleAssignments')[copyIndex()].AccountName, '/Microsoft.Authorization/', guid(parameters('RoleAssignments')[copyIndex()].Name))]",
"properties": {
"scope": "[parameters('RoleAssignments')[copyIndex()].Scope]",
"principalType": "[parameters('RoleAssignments')[copyIndex()].PrincipalType]",
"roleDefinitionId": "[parameters('RoleAssignments')[copyIndex()].RoleDefinitionId]",
"principalId": "[if(and(empty(parameters('RoleAssignments')[copyIndex()].ResourceId), not(empty(parameters('RoleAssignments')[copyIndex()].PrincipalId))),
parameters('RoleAssignments')[copyIndex()].PrincipalId,
reference(parameters('RoleAssignments')[copyIndex()].ResourceId, '2020-10-01').PrincipalId)]"
}
}
]
}
}
}
解决方案
已知零长度数组上的复制循环问题,微软团队已在其路线图上修复它。
目前的解决方案是将循环移动到嵌套部署中,将数组作为参数传递,并通过检查数组是否为空来判断嵌套部署的条件。虽然我不确定部署是否必须在内部范围内。当然,它可以与设置为内部的变量范围一起工作。
推荐阅读
- symfony4 - API 平台 POST 相关对象
- protocol-buffers - 在 protobuf 消息中定义嵌套的 oneof 消息
- r - 在R中使用正则表达式删除字符串中除指定单词之外的所有字符
- java - 您如何将 Quickfixj 之类的 TCP 服务器实现集成到 Spring-Integration 项目中?
- python-3.x - 如何返回关于列表是否为特定大小的布尔值?
- python - 在尾递归中重用先前分配的空间
- ios - 从 Parse 服务器获取数据到 xcode
- php - 主题中显示的 ACF 字段
- excel - 从代码窗口运行时宏运行良好,但是从按钮运行时出现溢出错误
- jquery - 从列表中淡出和淡入图像