首页 > 解决方案 > 将标签从资源组应用到资源的脚本

问题描述

尝试将在资源组级别设置的标签应用于资源组中的任何资源(所有资源)。

网上找了一个脚本,稍微修改了一下。

它应该确保标签 NAME 和标签 VALUE 都基于资源组设置(例如:如果资源组具有标签名称“ABCD”和标签值“1234”,并且资源组下的资源具有标签“ABCD”和标签值“4567”,那么它应该用“1234”覆盖该值)所有资源都应该设置一个标签。我们知道的名称,但我们不知道的值。

我注意到它需要很长时间才能运行。包含 10 个资源的资源组可能需要 1-2 分钟才能运行脚本

有什么想法或建议吗?

#List all Resources within the Subscription
$Resources = Get-AzureRmResource

#For each Resource apply the Tag of the Resource Group
Foreach ($resource in $Resources)
{
$Rgname = $resource.Resourcegroupname

$resourceid = $resource.resourceId
$RGTags = (Get-AzureRmResourceGroup -Name $Rgname).Tags

$resourcetags = $resource.Tags

If ($resourcetags -eq $null)
    {
        Write-Output "---------------------------------------------"
        Write-Output "Applying the following Tags to $($resourceid)" $RGTags
        Write-Output "---------------------------------------------"
        $Settag = Set-AzureRmResource -ResourceId $resourceid -Tag $RGTagS -Force

    }
Else
    {
        $RGTagFinal = @{}
        $RGTagFinal = $RGTags                  
                Foreach ($resourcetag in $resourcetags.GetEnumerator())
                {

                If ($RGTags.Keys -inotcontains $resourcetag.Key)
                    {                        
                            Write-Output "------------------------------------------------"
                            Write-Output "Keydoesn't exist in RG Tags adding to Hash Table" $resourcetag
                            Write-Output "------------------------------------------------"
                            $RGTagFinal.Add($resourcetag.Key,$resourcetag.Value)
                    }    

                }
        Write-Output "---------------------------------------------"
        Write-Output "Applying the following Tags to $($resourceid)" $RGTagFinal
        Write-Output "---------------------------------------------"
        $Settag = Set-AzureRmResource -ResourceId $resourceid -Tag $RGTagFinal -Force
    }   
}

脚本也应该做一些事情,我不确定这个脚本会做。

  1. 如果资源已经有 15 个标签,则不会覆盖具有资源组级别标签的标签;它会跳过它
  2. 不是将所有标签从资源组复制到资源,而是只有一个标签。例如,如果资源组具有“ABCDEFG”标签,我们可以将逻辑放在哪里,它会复制它吗?还有其他标签不会吗?
  3. 也许为了加快速度,是否可以只检查资源级别的标签名称和值是否与资源组级别的标签匹配,如果已经匹配则不要覆盖它。我怀疑这是需要时间的写入,而仅仅阅读标签则不是。

标签: azurepowershell

解决方案


这个应该让你非常接近你正在寻找的东西

$tagName = "ABCD"
$tagFallbackValue = "123"

$subscriptionId = "ewn3k4l4jh32jæ42æ3lj4æl12j4"

Connect-AzureRmAccount

$sub = Get-AzureRmSubscription -SubscriptionId $subscriptionId

Set-AzureRmContext -SubscriptionObject $sub

$resGroups = Get-AzureRmResourceGroup

foreach ($resGroup in $resGroups) {
    #Some ResourceGroups might not have tags defined at all.
    if($null -eq $resGroup.Tags) {
        $Tag = @{}
        $null = $Tag.Add($tagName, $tagFallbackValue)

        Set-AzureRmResourceGroup -Tag $Tag -Id $resGroup.ResourceId
    }#Some ResourceGroups might have tags but missing ours.
    elseif ($resGroup.Tags.ContainsKey($tagName) -eq $false) {
        $Tag = $resGroup.Tags
        $null = $Tag.Add($tagName, $tagFallbackValue)

        Set-AzureRmResourceGroup -Tag $Tag -Id $resGroup.ResourceId
    }#We need to test those that have our tag, if they have the desired tag value
    else {
        if($resGroup.Tags.$tagName -ne $tagFallbackValue) {
            $Tag = $resGroup.Tags
            $Tag.$tagName = $tagFallbackValue

            Set-AzureRmResourceGroup -Tag $Tag -Id $resGroup.ResourceId
        }
    }

    $tagValue = $resGroup.Tags.$tagName
    $resGroupName = $resGroup.ResourceGroupName

    #Some resources might already have our tag, find them and test if they have the correct value
    $resHasTag = Get-AzureRmResource -ResourceGroupName $resGroupName | Where-Object {$null -ne $_.tags -and $_.Tags.ContainsKey($tagName) -eq $true}
    foreach ($res in $resHasTag) {
        if($res.Tags.$tagName -ne $tagValue) {
            $Tag = $res.Tags
            $Tag.$tagName = $tagValue

            Set-AzureRmResource -ResourceId $res.ResourceId -Tag $Tag -Force
        }
    }

    #Some resources might not have tags defined at all.
    $resNoTags = Get-AzureRmResource -ResourceGroupName $resGroupName | Where-Object {$null -eq $_.tags -or $_.tags.Count -lt 1}
    foreach ($res in $resNoTags) {
        $Tag = @{}
        $null = $Tag.Add($tagName, $tagValue)
        Set-AzureRmResource -ResourceId $res.ResourceId -Tag $Tag -Force
    }

    #We need to find all resources that is missing our tag and have less than 15 tags
    $resOtherTags = Get-AzureRmResource -ResourceGroupName $resGroupName | Where-Object {$null -ne $_.tags -and $_.tags.Count -lt 15 -and $_.Tags.ContainsKey($tagName) -eq $false}
    foreach ($res in $resOtherTags) {
        $Tag = $res.Tags
        $null = $Tag.Add($tagName, $tagValue)

        Set-AzureRmResource -ResourceId $res.ResourceId -Tag $Tag -Force
    }
}

符合新要求的更新版本

$tagName = "COSTCODE"

Connect-AzureRmAccount

$subscriptions = Get-AzureRmSubscription

foreach ($sub in $subscriptions) {
    Set-AzureRmContext -SubscriptionObject $sub

    $resGroups = Get-AzureRmResourceGroup

    foreach ($resGroup in $resGroups) {
        #Some ResourceGroups might not have tags defined at all, we skip those.
        if ($null -eq $resGroup.Tags) { continue }

        #Some ResourceGroups might have tags but missing ours, we skip those.
        elseif ($resGroup.Tags.ContainsKey($tagName) -eq $false) { continue }
        #We need to test those that have our tag, if they have the desired tag value

        $tagValue = $resGroup.Tags.$tagName
        $resGroupName = $resGroup.ResourceGroupName

        #Some resources might already have our tag, find them and test if they have the correct value
        $resHasTag = Get-AzureRmResource -ResourceGroupName $resGroupName | Where-Object {$null -ne $_.tags -and $_.Tags.ContainsKey($tagName) -eq $true}
        foreach ($res in $resHasTag) {
            if ($res.Tags.$tagName -ne $tagValue) {
                $Tag = $res.Tags
                $Tag.$tagName = $tagValue

                Set-AzureRmResource -ResourceId $res.ResourceId -Tag $Tag -Force
            }
        }

        #Some resources might not have tags defined at all.
        $resNoTags = Get-AzureRmResource -ResourceGroupName $resGroupName | Where-Object {$null -eq $_.tags -or $_.tags.Count -lt 1}
        foreach ($res in $resNoTags) {
            $Tag = @{}
            $null = $Tag.Add($tagName, $tagValue)
            Set-AzureRmResource -ResourceId $res.ResourceId -Tag $Tag -Force
        }

        #We need to find all resources that is missing our tag and have less than 15 tags
        $resOtherTags = Get-AzureRmResource -ResourceGroupName $resGroupName | Where-Object {$null -ne $_.tags -and $_.tags.Count -lt 15 -and $_.Tags.ContainsKey($tagName) -eq $false}
        foreach ($res in $resOtherTags) {
            $Tag = $res.Tags
            $null = $Tag.Add($tagName, $tagValue)

            Set-AzureRmResource -ResourceId $res.ResourceId -Tag $Tag -Force
        }
    }
}

推荐阅读