Azure CLI & PowerShell — Core Commands Cheat Sheet

BeginnerCheat Sheet10 min5 min read20 Jan 2025Azure

Essential Azure CLI and Azure PowerShell patterns — login, subscriptions, resource groups, output formats, queries, and scripting conventions every Azure admin must know.

Installation & Setup

# Install Azure CLI (Ubuntu/Debian)
curl -sL https://aka.ms/InstallAzureCLIDeb | sudo bash

# Upgrade Azure CLI
az upgrade

# Check version
az version

# Install Azure CLI extension
az extension add --name account
az extension list --output table
# Install Az module (PowerShell 7+)
Install-Module -Name Az -AllowClobber -Scope CurrentUser

# Update Az module
Update-Module -Name Az

# Check version
Get-Module -Name Az -ListAvailable | Select-Object Name, Version

Authentication

# Interactive login (opens browser)
az login

# Login with service principal
az login \
  --service-principal \
  --username <app-id> \
  --password <secret> \
  --tenant <tenant-id>

# Login with managed identity (from Azure VM/container)
az login --identity

# List logged-in accounts
az account list --output table

# Show current subscription
az account show

# Set active subscription
az account set --subscription "My Subscription Name"
az account set --subscription <subscription-id>

# Logout
az logout
# Interactive login
Connect-AzAccount

# Login with service principal
$cred = New-Object System.Management.Automation.PSCredential("<app-id>", (ConvertTo-SecureString "<secret>" -AsPlainText -Force))
Connect-AzAccount -ServicePrincipal -Credential $cred -Tenant "<tenant-id>"

# List subscriptions
Get-AzSubscription

# Set active subscription
Set-AzContext -SubscriptionId "<subscription-id>"

# Disconnect
Disconnect-AzAccount

Resource Groups

# Create resource group
az group create \
  --name myRG \
  --location eastus

# List resource groups
az group list --output table

# Show resource group
az group show --name myRG

# Delete resource group (and all resources!)
az group delete --name myRG --yes --no-wait

# Export resource group as ARM template
az group export --name myRG > template.json

# List resources in a group
az resource list --resource-group myRG --output table
New-AzResourceGroup -Name "myRG" -Location "EastUS"
Get-AzResourceGroup
Remove-AzResourceGroup -Name "myRG" -Force
Get-AzResource -ResourceGroupName "myRG"

Output Formats

# Table (human-readable)
az vm list --output table

# JSON (default, full detail)
az vm list --output json

# TSV (tab-separated, good for scripting)
az vm list --output tsv

# YAML
az vm list --output yaml

# JSONC (JSON with comments)
az vm show -g myRG -n myVM --output jsonc

JMESPath Queries (--query)

# Extract single property
az vm show -g myRG -n myVM \
  --query "hardwareProfile.vmSize" -o tsv

# Extract list of names
az vm list -g myRG \
  --query "[].name" -o tsv

# Filter and extract
az vm list -g myRG \
  --query "[?powerState=='VM running'].name" -o tsv

# Multiple properties (object projection)
az vm list -g myRG \
  --query "[].{Name:name, Size:hardwareProfile.vmSize, Location:location}" -o table

# Nested property
az vm list -g myRG \
  --query "[].{Name:name, OS:storageProfile.osDisk.osType}" -o table

# First item
az vm list -g myRG --query "[0].name" -o tsv

# Count
az vm list -g myRG --query "length(@)" -o tsv

# Filter by tag
az resource list \
  --query "[?tags.environment=='production'].name" -o tsv

Variables and Scripting

# Capture output to variable
RG_ID=$(az group show --name myRG --query id -o tsv)
VM_IP=$(az vm list-ip-addresses -g myRG -n myVM --query "[0].virtualMachine.network.publicIpAddresses[0].ipAddress" -o tsv)

# Loop over resources
az vm list -g myRG --query "[].name" -o tsv | while read vmname; do
  echo "Stopping $vmname"
  az vm deallocate -g myRG -n "$vmname" --no-wait
done

# Conditional (check if resource exists)
if az group show --name myRG &> /dev/null; then
  echo "Resource group exists"
else
  az group create --name myRG --location eastus
fi
# Capture output
$vmId = (Get-AzVM -ResourceGroupName "myRG" -Name "myVM").Id

# Loop
$vms = Get-AzVM -ResourceGroupName "myRG"
foreach ($vm in $vms) {
  Write-Host "Stopping $($vm.Name)"
  Stop-AzVM -ResourceGroupName "myRG" -Name $vm.Name -Force
}

# Conditional
$rg = Get-AzResourceGroup -Name "myRG" -ErrorAction SilentlyContinue
if (-not $rg) {
  New-AzResourceGroup -Name "myRG" -Location "EastUS"
}

Tags

# Add tags to a resource group
az group update \
  --name myRG \
  --tags environment=production owner=ops-team

# Add tags to a VM
az vm update \
  --resource-group myRG \
  --name myVM \
  --set tags.environment=production tags.owner=ops-team

# List resources with a specific tag
az resource list \
  --tag environment=production \
  --output table

# Remove a specific tag
az resource update \
  --ids $(az resource show -g myRG -n myVM --resource-type Microsoft.Compute/virtualMachines --query id -o tsv) \
  --remove tags.owner
Set-AzResourceGroup -Name "myRG" -Tag @{environment="production"; owner="ops-team"}
$vm = Get-AzVM -ResourceGroupName "myRG" -Name "myVM"
Update-AzTag -ResourceId $vm.Id -Tag @{environment="production"} -Operation Merge
Get-AzResource -TagName "environment" -TagValue "production"

Azure Cloud Shell

# Cloud Shell runs in browser — no install needed
# Access at: https://shell.azure.com
# Or from Azure Portal > Cloud Shell icon (top nav)

# Storage persistence
# Cloud Shell mounts an Azure Files share at ~/clouddrive
ls ~/clouddrive

# Upload files to Cloud Shell
# Use the upload button in the Cloud Shell toolbar

# Switch between Bash and PowerShell
bash
pwsh

# Persistent files go in home directory
echo "alias k=kubectl" >> ~/.bashrc

Useful Global Flags

FlagDescription
--output / -ojson, table, tsv, yaml, jsonc, none
--queryJMESPath query to filter output
--no-waitDon't wait for operation to complete
--yes / -ySkip confirmation prompts
--debugShow verbose HTTP requests
--verboseShow operation progress
--only-show-errorsSuppress warnings
--subscriptionOverride active subscription
--help / -hShow command help

Key Facts for AZ-104

ConceptDetail
az loginCaches token in ~/.azure/; valid ~1 hour
Service principalNon-interactive auth for automation/CI
Managed identityNo credentials to manage; auto-rotated
Cloud ShellAlways up-to-date; persists in Azure Files
JMESPathAzure CLI's query language; -o tsv removes quotes
--no-waitStarts operation asynchronously; check with az group deployment show

More in Microsoft Azure