You apply tags to your Azure resources giving metadata to logically organize them into a taxonomy. Each tag consists of a name and a value pair. For example, you can apply the name "Environment" and the value "Production" to all the resources in production.
After you apply tags, you can retrieve all the resources in your subscription with that tag name and value. Tags enable you to retrieve related resources from different resource groups. This approach is helpful when you need to organize resources for billing or management.
Your taxonomy should consider a self-service metadata tagging strategy in addition to an auto-tagging strategy to reduce the burden on users and increase accuracy.
The following limitations apply to tags:
- Not all resource types support tags. To determine if you can apply a tag to a resource type, see Tag support for Azure resources.
- Each resource or resource group can have a maximum of 50 tag name/value pairs. Currently, storage accounts only support 15 tags, but that limit will be raised to 50 in a future release. If you need to apply more tags than the maximum allowed number, use a JSON string for the tag value. The JSON string can contain many values that are applied to a single tag name. A resource group can contain many resources that each have 50 tag name/value pairs.
- The tag name is limited to 512 characters, and the tag value is limited to 256 characters. For storage accounts, the tag name is limited to 128 characters, and the tag value is limited to 256 characters.
- Generalized VMs don't support tags.
- Tags applied to the resource group are not inherited by the resources in that resource group.
- Tags can't be applied to classic resources such as Cloud Services.
- Tag names can't contain these characters:
<
,>
,%
,&
,\
,?
,/
To apply tags to resources, the user must have write access to that resource type. To apply tags to all resource types, use the Contributor role. To apply tags to only one resource type, use the contributor role for that resource. For example, to apply tags to virtual machines, use the Virtual Machine Contributor.
Note
This article provides steps for how to delete personal data from the device or service and can be used to support your obligations under the GDPR. If you’re looking for general info about GDPR, see the GDPR section of the Service Trust portal.
Policies
You can use Azure Policy to enforce tagging rules and conventions. By creating a policy, you avoid the scenario of resources being deployed to your subscription that don't comply with the expected tags for your organization. Instead of manually applying tags or searching for resources that aren't compliant, you can create a policy that automatically applies the needed tags during deployment. The following section shows example policies for tags.
Tags
PowerShell
Note
This article has been updated to use the new Azure PowerShell Az module. You can still use the AzureRM module, which will continue to receive bug fixes until at least December 2020. To learn more about the new Az module and AzureRM compatibility, see Introducing the new Azure PowerShell Az module. For Az module installation instructions, see Install Azure PowerShell.
To see the existing tags for a resource group, use:
Azure PowerShell
(Get-AzResourceGroup -Name examplegroup).Tags
That script returns the following format:
PowerShell
Name Value
---- -----
Dept IT
Environment Test
To see the existing tags for a resource that has a specified resource ID, use:
Azure PowerShell
(Get-AzResource -ResourceId /subscriptions/<subscription-id>/resourceGroups/<rg-name>/providers/Microsoft.Storage/storageAccounts/<storage-name>).Tags
Or, to see the existing tags for a resource that has a specified name and resource group, use:
Azure PowerShell
(Get-AzResource -ResourceName examplevnet -ResourceGroupName examplegroup).Tags
To get resource groups that have a specific tag, use:
Azure PowerShell
(Get-AzResourceGroup -Tag @{ Dept="Finance" }).ResourceGroupName
To get resources that have a specific tag, use:
Azure PowerShell
(Get-AzResource -Tag @{ Dept="Finance"}).Name
To get resources that have a specific tag name, use:
Azure PowerShell
(Get-AzResource -TagName Dept).Name
Every time you apply tags to a resource or a resource group, you overwrite the existing tags on that resource or resource group. Therefore, you must use a different approach based on whether the resource or resource group has existing tags.
To add tags to a resource group without existing tags, use:
Azure PowerShell
Set-AzResourceGroup -Name examplegroup -Tag @{ Dept="IT"; Environment="Test" }
To add tags to a resource group that has existing tags, retrieve the existing tags, add the new tag, and reapply the tags:
Azure PowerShell
$tags = (Get-AzResourceGroup -Name examplegroup).Tags
$tags.Add("Status", "Approved")
Set-AzResourceGroup -Tag $tags -Name examplegroup
To add tags to a resource without existing tags, use:
Azure PowerShell
$r = Get-AzResource -ResourceName examplevnet -ResourceGroupName examplegroup
Set-AzResource -Tag @{ Dept="IT"; Environment="Test" } -ResourceId $r.ResourceId -Force
To add tags to a resource that has existing tags, use:
Azure PowerShell
$r = Get-AzResource -ResourceName examplevnet -ResourceGroupName examplegroup
$r.Tags.Add("Status", "Approved")
Set-AzResource -Tag $r.Tags -ResourceId $r.ResourceId -Force
To apply all tags from a resource group to its resources, and not keep existing tags on the resources, use the following script:
Azure PowerShell
$groups = Get-AzResourceGroup
foreach ($g in $groups)
{
Get-AzResource -ResourceGroupName $g.ResourceGroupName | ForEach-Object {Set-AzResource -ResourceId $_.ResourceId -Tag $g.Tags -Force }
}
To apply all tags from a resource group to its resources, and keep existing tags on resources that aren't duplicates, use the following script:
Azure PowerShell
$group = Get-AzResourceGroup "examplegroup"
if ($null -ne $group.Tags) {
$resources = Get-AzResource -ResourceGroupName $group.ResourceGroupName
foreach ($r in $resources)
{
$resourcetags = (Get-AzResource -ResourceId $r.ResourceId).Tags
if ($resourcetags)
{
foreach ($key in $group.Tags.Keys)
{
if (-not($resourcetags.ContainsKey($key)))
{
$resourcetags.Add($key, $group.Tags[$key])
}
}
Set-AzResource -Tag $resourcetags -ResourceId $r.ResourceId -Force
}
else
{
Set-AzResource -Tag $group.Tags -ResourceId $r.ResourceId -Force
}
}
}
To remove all tags, pass an empty hash table:
Azure PowerShell
Set-AzResourceGroup -Tag @{} -Name examplegroup
Azure CLI
To see the existing tags for a resource group, use:
Azure CLI
az group show -n examplegroup --query tags
That script returns the following format:
JSON
{
"Dept" : "IT",
"Environment" : "Test"
}
Or, to see the existing tags for a resource that has a specified name, type, and resource group, use:
Azure CLI
az resource show -n examplevnet -g examplegroup --resource-type "Microsoft.Network/virtualNetworks" --query tags
When looping through a collection of resources, you might want to show the resource by resource ID. A complete example is shown later in this article. To see the existing tags for a resource that has a specified resource ID, use:
Azure CLI
az resource show --id <resource-id> --query tags
To get resource groups that have a specific tag, use
az group list
:
Azure CLI
az group list --tag Dept=IT
To get all the resources that have a particular tag and value, use
az resource list
:
Azure CLI
az resource list --tag Dept=Finance
Every time you apply tags to a resource or a resource group, you overwrite the existing tags on that resource or resource group. Therefore, you must use a different approach based on whether the resource or resource group has existing tags.
To add tags to a resource group without existing tags, use:
Azure CLI
az group update -n examplegroup --set tags.Environment=Test tags.Dept=IT
To add tags to a resource without existing tags, use:
Azure CLI
az resource tag --tags Dept=IT Environment=Test -g examplegroup -n examplevnet --resource-type "Microsoft.Network/virtualNetworks"
To add tags to a resource that already has tags, retrieve the existing tags, reformat that value, and reapply the existing and new tags:
Azure CLI
jsonrtag=$(az resource show -g examplegroup -n examplevnet --resource-type "Microsoft.Network/virtualNetworks" --query tags)
rt=$(echo $jsonrtag | tr -d '"{},' | sed 's/: /=/g')
az resource tag --tags $rt Project=Redesign -g examplegroup -n examplevnet --resource-type "Microsoft.Network/virtualNetworks"
To apply all tags from a resource group to its resources, and not keep existing tags on the resources, use the following script:
Azure CLI
groups=$(az group list --query [].name --output tsv)
for rg in $groups
do
jsontag=$(az group show -n $rg --query tags)
t=$(echo $jsontag | tr -d '"{},' | sed 's/: /=/g')
r=$(az resource list -g $rg --query [].id --output tsv)
for resid in $r
do
az resource tag --tags $t --id $resid
done
done
To apply all tags from a resource group to its resources, and keep existing tags on resources, use the following script:
Azure CLI
groups=$(az group list --query [].name --output tsv)
for rg in $groups
do
jsontag=$(az group show -n $rg --query tags)
t=$(echo $jsontag | tr -d '"{},' | sed 's/: /=/g')
r=$(az resource list -g $rg --query [].id --output tsv)
for resid in $r
do
jsonrtag=$(az resource show --id $resid --query tags)
rt=$(echo $jsonrtag | tr -d '"{},' | sed 's/: /=/g')
az resource tag --tags $t$rt --id $resid
done
done
Templates
To tag a resource during deployment, add the
tags
element to the resource you're deploying. Provide the tag name and value.Apply a literal value to the tag name
The following example shows a storage account with two tags (
Dept
and Environment
) that are set to literal values:
JSON
{
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"location": {
"type": "string",
"defaultValue": "[resourceGroup().location]"
}
},
"resources": [
{
"apiVersion": "2019-04-01",
"type": "Microsoft.Storage/storageAccounts",
"name": "[concat('storage', uniqueString(resourceGroup().id))]",
"location": "[parameters('location')]",
"tags": {
"Dept": "Finance",
"Environment": "Production"
},
"sku": {
"name": "Standard_LRS"
},
"kind": "Storage",
"properties": {}
}
]
}
To set a tag to a datetime value, use the utcNow function.
Apply an object to the tag element
You can define an object parameter that stores several tags, and apply that object to the tag element. Each property in the object becomes a separate tag for the resource. The following example has a parameter named
tagValues
that is applied to the tag element.
JSON
{
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"location": {
"type": "string",
"defaultValue": "[resourceGroup().location]"
},
"tagValues": {
"type": "object",
"defaultValue": {
"Dept": "Finance",
"Environment": "Production"
}
}
},
"resources": [
{
"apiVersion": "2019-04-01",
"type": "Microsoft.Storage/storageAccounts",
"name": "[concat('storage', uniqueString(resourceGroup().id))]",
"location": "[parameters('location')]",
"tags": "[parameters('tagValues')]",
"sku": {
"name": "Standard_LRS"
},
"kind": "Storage",
"properties": {}
}
]
}
Apply a JSON string to the tag name
To store many values in a single tag, apply a JSON string that represents the values. The entire JSON string is stored as one tag that can't exceed 256 characters. The following example has a single tag named
CostCenter
that contains several values from a JSON string:
JSON
{
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"location": {
"type": "string",
"defaultValue": "[resourceGroup().location]"
}
},
"resources": [
{
"apiVersion": "2019-04-01",
"type": "Microsoft.Storage/storageAccounts",
"name": "[concat('storage', uniqueString(resourceGroup().id))]",
"location": "[parameters('location')]",
"tags": {
"CostCenter": "{\"Dept\":\"Finance\",\"Environment\":\"Production\"}"
},
"sku": {
"name": "Standard_LRS"
},
"kind": "Storage",
"properties": {}
}
]
}
Apply tags from resource group
To apply tags from a resource group to a resource, use the resourceGroup function. When getting the tag value, use the
tags.[tag-name]
syntax instead of the tags.tag-name
syntax, because some characters aren't parsed correctly in the dot notation.
JSON
{
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"location": {
"type": "string",
"defaultValue": "[resourceGroup().location]"
}
},
"resources": [
{
"apiVersion": "2019-04-01",
"type": "Microsoft.Storage/storageAccounts",
"name": "[concat('storage', uniqueString(resourceGroup().id))]",
"location": "[parameters('location')]",
"tags": {
"Dept": "[resourceGroup().tags['Dept']]",
"Environment": "[resourceGroup().tags['Environment']]"
},
"sku": {
"name": "Standard_LRS"
},
"kind": "Storage",
"properties": {}
}
]
}
Portal
- To view the tags for a resource or a resource group, looks for existing tags in the overview. If you have not previously applied tags, the list is empty.
- To add a tag, select Click here to add tags.
- Provide a name and value. Select + to add the tag.
- Continue adding tags as needed. When done, select Save.
- The tags are now displayed in the overview.
- To add or delete a tag, select change.
- To delete a tag, select the trash icon. Then, select Save.
To bulk assign tags to multiple resources:
- From any list of resources, select the checkbox for the resources you want to assign the tag.
- Select Assign tags
- After each name and value, select +. When done, select Assign.
To view all resources with a tag:
- Select All services and Tags.
- Select the tag for viewing resources.
- All resources with that tag are displayed.
- For quick access, pin the view to the dashboard.
- The view is available from the dashboard.
REST API
The Azure portal and PowerShell both use the Resource Manager REST API behind the scenes. If you need to integrate tagging into another environment, you can get tags by using GET on the resource ID and update the set of tags by using a PATCH call.
Tags and billing
You can use tags to group your billing data. For example, if you're running multiple VMs for different organizations, use the tags to group usage by cost center. You can also use tags to categorize costs by runtime environment, such as the billing usage for VMs running in the production environment.
You can retrieve information about tags through the Azure Resource Usage and RateCard APIs or the usage comma-separated values (CSV) file. You download the usage file from the Azure Account Center or Azure portal. For more information, see Download or view your Azure billing invoice and daily usage data. When downloading the usage file from the Azure Account Center, select Version 2. For services that support tags with billing, the tags appear in the Tags column.
For REST API operations, see Azure Billing REST API Reference.
Next steps
- Not all resource types support tags. To determine if you can apply a tag to a resource type, see Tag support for Azure resources.
- For an introduction to using the portal, see Using the Azure portal to manage your Azure resources.