Public/Set-CloudTag.ps1
|
function Set-CloudTag { <# .SYNOPSIS Sets tags or labels on a cloud resource across Azure, AWS, or GCP. .DESCRIPTION Set-CloudTag applies tags (Azure), tags (AWS), or labels (GCP) to cloud resources. For Azure, you can specify a VM by Name/ResourceGroup or any resource by ResourceId. For AWS, provide the ResourceId and Region. For GCP, provide the Project and Resource. You can also pipe CloudRecord objects from other PSCumulus commands. .EXAMPLE Set-CloudTag -Name 'vm01' -ResourceGroup 'rg-test' -Tags @{Environment='Dev'; Owner='TeamA'} Tags an Azure VM by name and resource group. .EXAMPLE Set-CloudTag -AzureResourceId '/subscriptions/123/resourceGroups/rg/providers/Microsoft.Compute/disks/disk01' -Tags @{Backup='Weekly'} Tags an Azure disk using its full resource ID (AzureById parameter set). .EXAMPLE Set-CloudTag -ResourceId 'i-1234567890abcdef0' -Region 'us-east-1' -Tags @{Environment='Prod'} Tags an AWS EC2 instance by its resource ID. .EXAMPLE Set-CloudTag -Project 'my-project' -Resource 'projects/my/zones/us-central1-a/instances/vm01' -Tags @{Owner='Ops'} Tags a GCP compute instance. .EXAMPLE Get-CloudDisk -Provider Azure | Set-CloudTag -Tags @{Encrypted='AES256'} Tags all Azure disks returned from Get-CloudDisk (piped input). #> [CmdletBinding( DefaultParameterSetName = 'Piped', SupportsShouldProcess = $true )] [OutputType([pscustomobject])] param( [Parameter(Mandatory, ParameterSetName = 'AzureByName')] [string]$Name, [Parameter(Mandatory, ParameterSetName = 'AzureByName')] [string]$ResourceGroup, [Parameter(Mandatory, ParameterSetName = 'AzureById')] [string]$AzureResourceId, [Parameter(Mandatory, ParameterSetName = 'AWS')] [string]$ResourceId, [Parameter(Mandatory, ParameterSetName = 'AWS')] [string]$Region, [Parameter(Mandatory, ParameterSetName = 'GCP')] [string]$Project, [Parameter(Mandatory, ParameterSetName = 'GCP')] [string]$Resource, [Parameter(Mandatory, ValueFromPipeline = $true, ParameterSetName = 'Piped')] [psobject]$InputObject, [Parameter(Mandatory)] [hashtable]$Tags, [switch]$Merge ) begin { $results = [System.Collections.Generic.List[psobject]]::new() } process { $targetInfo = $null switch ($PSCmdlet.ParameterSetName) { 'AzureByName' { $subscriptionId = $script:PSCumulusContext.Providers['Azure'].SubscriptionId $targetInfo = @{ Provider = 'Azure' Name = $Name ResourceGroup = $ResourceGroup ResourceId = "/subscriptions/$subscriptionId/resourceGroups/$ResourceGroup/providers/Microsoft.Compute/virtualMachines/$Name" } } 'AzureById' { $targetInfo = @{ Provider = 'Azure' ResourceId = $AzureResourceId Name = ($AzureResourceId -split '/')[-1] } } 'AWS' { $targetInfo = @{ Provider = 'AWS' ResourceId = $ResourceId Region = $Region } } 'GCP' { $targetInfo = @{ Provider = 'GCP' Project = $Project Resource = $Resource Name = $Resource -replace '.*/instances/' } } 'Piped' { if (-not $InputObject.Provider -or -not $InputObject.Name) { throw [System.ArgumentException]::new( "Set-CloudTag requires a PSCumulus CloudRecord, or any object with non-null Provider and Name properties." ) } $targetInfo = @{ Provider = $InputObject.Provider Name = $InputObject.Name InputObj = $InputObject } switch ($InputObject.Provider) { 'Azure' { $targetInfo.ResourceGroup = $InputObject.ResourceGroup $targetInfo.ResourceId = $InputObject.Id } 'AWS' { $targetInfo.ResourceId = $InputObject.InstanceId $targetInfo.Region = $InputObject.Region } 'GCP' { $targetInfo.Project = $InputObject.Project $targetInfo.Resource = $InputObject.Id } } } } if ($targetInfo) { $targetDisplay = switch ($targetInfo.Provider) { 'Azure' { if ($targetInfo.ResourceGroup) { "$($targetInfo.Name) (ResourceGroup: $($targetInfo.ResourceGroup))" } else { $targetInfo.ResourceId } } 'AWS' { "$($targetInfo.ResourceId) (Region: $($targetInfo.Region))" } 'GCP' { "$($targetInfo.Name) (Project: $($targetInfo.Project))" } } if ($PSCmdlet.ShouldProcess($targetDisplay, "Set tags $($Tags.Keys -join ', ')")) { $result = switch ($targetInfo.Provider) { 'Azure' { Set-AzureTag -ResourceId $targetInfo.ResourceId -Tags $Tags -Merge:$Merge } 'AWS' { Set-AWSTag -ResourceId $targetInfo.ResourceId -Tags $Tags -Merge:$Merge -Region $targetInfo.Region } 'GCP' { Set-GCPTag -Project $targetInfo.Project -Resource $targetInfo.Resource -Tags $Tags -Merge:$Merge } } if ($result) { $results.Add($result) } } } } end { $results | Write-Output } } |