← Back to Learning Portal
AZ-500 Study Manual
Exam study guide for Azure Security Engineer Associate.
📘 AZ-500 EXAM STUDY GUIDE 2026
Comprehensive Guide with PowerShell/CLI Labs and Checklists
Exam: AZ-500 — Microsoft Azure Security Engineer Associate
Format: Deep-dive reference with hands-on labs and skill checklists
WEEK 1 STUDY GUIDE: IDENTITY AND ACCESS
Domain 1 Deep Dive — Manage Identity and Access
Skill Checklist: Microsoft Entra ID
- [ ] Explain the difference between Entra ID Free, P1, and P2 licences
- [ ] Create and manage users, groups, and group membership rules
- [ ] Configure guest access and external collaboration settings
- [ ] Understand device states: registered, joined, hybrid joined
- [ ] Configure SSPR (Self-Service Password Reset)
- [ ] Explain Entra Connect sync methods (PHS, PTA, Federation)
Skill Checklist: Azure RBAC
- [ ] List and explain all built-in roles with their boundaries
- [ ] Create a custom role using JSON or PowerShell
- [ ] Assign a role at different scopes (MG, subscription, RG, resource)
- [ ] Understand deny assignments and when they apply
- [ ] Configure resource locks (ReadOnly, CanNotDelete)
- [ ] Audit role assignments using Azure Policy or Log Analytics
Skill Checklist: Managed Identities
- [ ] Enable system-assigned managed identity on a VM
- [ ] Create a user-assigned managed identity
- [ ] Grant Key Vault access to a managed identity
- [ ] Use managed identity to access a storage account from App Service
Lab 1A: RBAC Custom Role — PowerShell
# Get the subscription ID
$subId = (Get-AzContext).Subscription.Id
# Define the custom role
$role = @{
Name = "VM Start/Stop Operator"
Description = "Can start and stop virtual machines but cannot manage them."
Actions = @(
"Microsoft.Compute/virtualMachines/start/action",
"Microsoft.Compute/virtualMachines/deallocate/action",
"Microsoft.Compute/virtualMachines/read"
)
NotActions = @()
DataActions = @()
NotDataActions = @()
AssignableScopes = @("/subscriptions/$subId")
}
# Create the role
$roleDefinition = New-AzRoleDefinition -Role $role
Write-Host "Created role: $($roleDefinition.Name)"
# Assign the role to a user
New-AzRoleAssignment `
-SignInName "user@contoso.com" `
-RoleDefinitionName "VM Start/Stop Operator" `
-Scope "/subscriptions/$subId/resourceGroups/prod-rg"
Lab 1B: Managed Identity + Key Vault — CLI
# Create a user-assigned managed identity
az identity create \
--name "app-identity" \
--resource-group "security-rg"
# Get the identity's principal ID
PRINCIPAL_ID=$(az identity show \
--name "app-identity" \
--resource-group "security-rg" \
--query principalId --output tsv)
# Assign Key Vault Secrets User role to the identity
az role assignment create \
--assignee "$PRINCIPAL_ID" \
--role "Key Vault Secrets User" \
--scope "/subscriptions/{sub}/resourceGroups/security-rg/providers/Microsoft.KeyVault/vaults/myvault"
# Assign the identity to an App Service
az webapp identity assign \
--resource-group "security-rg" \
--name "mywebapp" \
--identities "/subscriptions/{sub}/resourceGroups/security-rg/providers/Microsoft.ManagedIdentity/userAssignedIdentities/app-identity"
Lab 2A: Conditional Access Policy — PowerShell (Graph)
# Install required module
Install-Module Microsoft.Graph -Scope CurrentUser
# Connect
Connect-MgGraph -Scopes "Policy.ReadWrite.ConditionalAccess"
# Create a Conditional Access policy requiring MFA for all users on Azure Portal
$policy = @{
displayName = "Require MFA for Azure Portal"
state = "enabled"
conditions = @{
users = @{
includeUsers = @("All")
excludeUsers = @("emergency-admin@contoso.com") # Break-glass account
}
applications = @{
includeApplications = @("797f4846-ba00-4fd7-ba43-dac1f8f63013") # Azure Management
}
}
grantControls = @{
operator = "OR"
builtInControls = @("mfa")
}
}
New-MgIdentityConditionalAccessPolicy -BodyParameter $policy
Lab 2B: PIM Role Assignment — PowerShell
# Connect to Microsoft Graph with PIM permissions
Connect-MgGraph -Scopes "RoleManagement.ReadWrite.Directory"
# Get the role definition ID for "Security Reader"
$roleDef = Get-MgRoleManagementDirectoryRoleDefinition `
-Filter "displayName eq 'Security Reader'"
# Get the user
$user = Get-MgUser -Filter "userPrincipalName eq 'alice@contoso.com'"
# Create an eligible PIM assignment
New-MgRoleManagementDirectoryRoleEligibilityScheduleRequest -BodyParameter @{
action = "AdminAssign"
justification = "Security team member needs eligible Security Reader role"
roleDefinitionId = $roleDef.Id
directoryScopeId = "/"
principalId = $user.Id
scheduleInfo = @{
startDateTime = (Get-Date).ToUniversalTime().ToString("o")
expiration = @{
type = "noExpiration"
}
}
}
Write-Host "Eligible assignment created for $($user.UserPrincipalName)"
WEEK 2 STUDY GUIDE: SECURE NETWORKING
Domain 2 Deep Dive — Secure Networking
Skill Checklist: NSGs
- [ ] Create an NSG with inbound and outbound rules
- [ ] Understand default rules and priority evaluation
- [ ] Configure Application Security Groups (ASGs)
- [ ] Enable NSG Flow Logs and Traffic Analytics
- [ ] Associate NSG with subnet and NIC
Skill Checklist: Azure Firewall
- [ ] Deploy Azure Firewall in a hub VNet
- [ ] Create DNAT, Network, and Application rules
- [ ] Configure threat intelligence in Alert and Deny mode
- [ ] Create a Firewall Policy with parent-child hierarchy
- [ ] Route spoke VNet traffic through the firewall (UDR)
Skill Checklist: WAF + DDoS
- [ ] Deploy Application Gateway with WAF_v2 SKU
- [ ] Configure WAF in Prevention mode
- [ ] Create a custom WAF rule
- [ ] Enable DDoS Network Protection on a VNet
- [ ] Understand DDoS mitigation telemetry
Lab 3A: Deploy Azure Firewall — CLI
# Create VNet with firewall subnet az network vnet create \ --resource-group security-rg \ --name hub-vnet \ --address-prefixes 10.0.0.0/16 \ --subnet-name AzureFirewallSubnet \ --subnet-prefixes 10.0.0.0/26 # Create public IP for firewall az network public-ip create \ --resource-group security-rg \ --name fw-pip \ --sku Standard \ --allocation-method Static # Create Azure Firewall az network firewall create \ --resource-group security-rg \ --name hub-firewall \ --location eastus \ --sku-tier Standard # Configure firewall IP az network firewall ip-config create \ --firewall-name hub-firewall \ --resource-group security-rg \ --name fw-ipconfig \ --public-ip-address fw-pip \ --vnet-name hub-vnet # Get firewall private IP FW_PRIVATE_IP=$(az network firewall show \ --resource-group security-rg \ --name hub-firewall \ --query "ipConfigurations[0].privateIPAddress" -o tsv) # Create application rule collection (allow Windows Update) az network firewall application-rule create \ --resource-group security-rg \ --firewall-name hub-firewall \ --collection-name "AllowWindowsUpdate" \ --priority 200 \ --action Allow \ --name "WindowsUpdate" \ --protocols Http=80 Https=443 \ --fqdn-tags WindowsUpdate # Create network rule (allow DNS) az network firewall network-rule create \ --resource-group security-rg \ --firewall-name hub-firewall \ --collection-name "AllowDNS" \ --priority 100 \ --action Allow \ --name "DNS" \ --protocols UDP \ --source-addresses "*" \ --destination-fqdns "*.dns.azure.com" \ --destination-ports 53 # Create route table to force traffic through firewall az network route-table create \ --resource-group security-rg \ --name spoke-rt az network route-table route create \ --resource-group security-rg \ --route-table-name spoke-rt \ --name DefaultRoute \ --address-prefix 0.0.0.0/0 \ --next-hop-type VirtualAppliance \ --next-hop-ip-address $FW_PRIVATE_IP
Lab 3B: NSG with ASGs — PowerShell
$rg = "security-rg"
$location = "eastus"
# Create Application Security Groups
$webASG = New-AzApplicationSecurityGroup `
-ResourceGroupName $rg `
-Name "WebServers-ASG" `
-Location $location
$dbASG = New-AzApplicationSecurityGroup `
-ResourceGroupName $rg `
-Name "DatabaseServers-ASG" `
-Location $location
# Create NSG
$nsg = New-AzNetworkSecurityGroup `
-ResourceGroupName $rg `
-Name "app-nsg" `
-Location $location
# Add rule: Allow web traffic from internet to web servers
$nsg | Add-AzNetworkSecurityRuleConfig `
-Name "Allow-HTTP-HTTPS-Inbound" `
-Priority 100 `
-Direction Inbound `
-Access Allow `
-Protocol Tcp `
-SourceAddressPrefix Internet `
-DestinationApplicationSecurityGroup $webASG `
-DestinationPortRange @(80, 443) | Set-AzNetworkSecurityGroup
# Add rule: Allow SQL from web servers to database servers only
$nsg | Add-AzNetworkSecurityRuleConfig `
-Name "Allow-SQL-from-Web" `
-Priority 200 `
-Direction Inbound `
-Access Allow `
-Protocol Tcp `
-SourceApplicationSecurityGroup $webASG `
-DestinationApplicationSecurityGroup $dbASG `
-DestinationPortRange 1433 | Set-AzNetworkSecurityGroup
Write-Host "NSG with ASGs created successfully"
WEEK 3 STUDY GUIDE: COMPUTE, STORAGE, AND DATABASE SECURITY
Domain 3 Deep Dive — Secure Compute, Storage, and Databases
Skill Checklist: Azure Key Vault
- [ ] Create a Key Vault with RBAC access model
- [ ] Store and retrieve secrets, keys, and certificates
- [ ] Enable soft-delete and purge protection
- [ ] Configure Key Vault firewall with private endpoint
- [ ] Rotate a key manually and configure auto-rotation
Skill Checklist: Storage Security
- [ ] Generate a User Delegation SAS token
- [ ] Configure storage firewall with VNet integration
- [ ] Assign RBAC data roles for blob access
- [ ] Enable Customer-Managed Keys (CMK) for storage
- [ ] Configure immutable storage policies
Skill Checklist: SQL Database Security
- [ ] Enable Transparent Data Encryption with CMK
- [ ] Configure Dynamic Data Masking rules
- [ ] Enable Microsoft Defender for SQL
- [ ] Configure auditing to Log Analytics
- [ ] Set up Always Encrypted for a column
Lab 4A: Azure Key Vault — Full Setup
$rg = "security-rg"
$location = "eastus"
$vaultName = "my-kv-$(Get-Random -Max 9999)"
# Create Key Vault with RBAC access model and purge protection
$vault = New-AzKeyVault `
-ResourceGroupName $rg `
-VaultName $vaultName `
-Location $location `
-Sku Standard `
-EnableRbacAuthorization ` # Use RBAC model (not access policies)
-EnableSoftDelete `
-SoftDeleteRetentionInDays 90 `
-EnablePurgeProtection
Write-Host "Created vault: $($vault.VaultName)"
# Assign 'Key Vault Administrator' role to yourself
$myId = (Get-AzADUser -UserPrincipalName (Get-AzContext).Account.Id).Id
New-AzRoleAssignment `
-ObjectId $myId `
-RoleDefinitionName "Key Vault Administrator" `
-Scope $vault.ResourceId
# Create a secret
$secret = ConvertTo-SecureString "MySecretPassword123!" -AsPlainText -Force
Set-AzKeyVaultSecret -VaultName $vaultName -Name "db-connection-string" -SecretValue $secret
# Create an RSA key
Add-AzKeyVaultKey -VaultName $vaultName -Name "encryption-key" -Destination Software -KeyType RSA -Size 2048
# Enable diagnostic logging
Set-AzDiagnosticSetting `
-ResourceId $vault.ResourceId `
-Name "kv-diagnostics" `
-WorkspaceId "/subscriptions/{sub}/resourceGroups/security-rg/providers/Microsoft.OperationalInsights/workspaces/security-law" `
-Enabled $true `
-Category @("AuditEvent")
Lab 4B: Storage Security — User Delegation SAS
# Grant yourself Storage Blob Data Contributor (needed for user delegation SAS)
az role assignment create \
--role "Storage Blob Data Contributor" \
--assignee "$(az account show --query user.name -o tsv)" \
--scope "/subscriptions/{sub}/resourceGroups/security-rg/providers/Microsoft.Storage/storageAccounts/mystorageaccount"
# Generate User Delegation SAS (uses your Entra ID identity - most secure)
az storage blob generate-sas \
--account-name mystorageaccount \
--container-name mycontainer \
--name myblob.txt \
--permissions r \
--expiry "$(date -u -d '1 hour' +%Y-%m-%dT%H:%MZ)" \
--auth-mode login \
--as-user \
--https-only
# Configure storage firewall - deny all, allow specific VNet
az storage account update \
--resource-group security-rg \
--name mystorageaccount \
--default-action Deny \
--bypass AzureServices
# Add VNet rule (requires service endpoint on subnet)
az storage account network-rule add \
--resource-group security-rg \
--account-name mystorageaccount \
--vnet-name "hub-vnet" \
--subnet "app-subnet"
Lab 5: Azure SQL Database Security — PowerShell
$serverName = "my-sql-server"
$dbName = "my-database"
$rg = "security-rg"
# Enable Transparent Data Encryption (should be on by default)
Set-AzSqlDatabaseTransparentDataEncryption `
-ResourceGroupName $rg `
-ServerName $serverName `
-DatabaseName $dbName `
-State Enabled
# Enable Entra ID administrator (disables SQL auth for admins)
Set-AzSqlServerActiveDirectoryAdministrator `
-ResourceGroupName $rg `
-ServerName $serverName `
-DisplayName "SQL-Admins-Group" `
-ObjectId (Get-AzADGroup -DisplayName "SQL-Admins-Group").Id
# Enable Microsoft Defender for SQL
Set-AzSqlServerAdvancedDataSecurityPolicy `
-ResourceGroupName $rg `
-ServerName $serverName `
-Enable $true
# Configure SQL auditing to Log Analytics
Set-AzSqlServerAudit `
-ResourceGroupName $rg `
-ServerName $serverName `
-WorkspaceResourceId "/subscriptions/{sub}/resourceGroups/security-rg/providers/Microsoft.OperationalInsights/workspaces/security-law" `
-State Enabled
# Add Dynamic Data Masking rule
New-AzSqlDatabaseDataMaskingRule `
-ResourceGroupName $rg `
-ServerName $serverName `
-DatabaseName $dbName `
-MaskingFunction "Email" `
-SchemaName "dbo" `
-TableName "Customers" `
-ColumnName "EmailAddress"
Write-Host "SQL security configured successfully"
WEEK 4 STUDY GUIDE: SECURITY OPERATIONS
Domain 4 Deep Dive — Manage Security Operations
Skill Checklist: Defender for Cloud
- [ ] Enable Defender plans for: Servers, Storage, SQL, Containers
- [ ] Review and action Secure Score recommendations
- [ ] Configure workflow automation for High severity alerts
- [ ] Export security data to Sentinel
- [ ] Configure regulatory compliance standards
- [ ] Enable JIT VM Access for a VM
Skill Checklist: Microsoft Sentinel
- [ ] Create a Log Analytics workspace and enable Sentinel
- [ ] Connect data connectors: Entra ID, Activity Log, Defender for Cloud
- [ ] Create a scheduled analytics rule with KQL
- [ ] Respond to and close an incident
- [ ] Create a playbook (Logic App) triggered by incident
- [ ] Run a hunting query and bookmark results
- [ ] Enable UEBA
Skill Checklist: Azure Policy
- [ ] Assign the Azure Security Benchmark initiative
- [ ] Create a custom Deny policy
- [ ] Create a DeployIfNotExists policy with managed identity
- [ ] Create and run a remediation task
- [ ] View and export compliance report
Lab 6A: Enable Defender for Cloud Plans — PowerShell
# Enable Defender for Servers Plan 2 Set-AzSecurityPricing -Name "VirtualMachines" -PricingTier "Standard" -SubPlan "P2" # Enable Defender for Storage Set-AzSecurityPricing -Name "StorageAccounts" -PricingTier "Standard" # Enable Defender for SQL (Azure SQL Databases) Set-AzSecurityPricing -Name "SqlServers" -PricingTier "Standard" # Enable Defender for Containers Set-AzSecurityPricing -Name "Containers" -PricingTier "Standard" # Enable Defender for Key Vault Set-AzSecurityPricing -Name "KeyVaults" -PricingTier "Standard" # Enable Defender for ARM Set-AzSecurityPricing -Name "Arm" -PricingTier "Standard" # Enable Defender for App Service Set-AzSecurityPricing -Name "AppServices" -PricingTier "Standard" # List all enabled Defender plans and their tiers Get-AzSecurityPricing | Select-Object Name, PricingTier, FreeTrialRemainingTime
Lab 6B: Microsoft Sentinel Setup — CLI
# Create Log Analytics workspace az monitor log-analytics workspace create \ --resource-group security-rg \ --workspace-name security-sentinel-law \ --location eastus \ --retention-time 90 LAW_ID=$(az monitor log-analytics workspace show \ --resource-group security-rg \ --workspace-name security-sentinel-law \ --query id -o tsv) # Enable Microsoft Sentinel on the workspace az sentinel workspace create \ --resource-group security-rg \ --workspace-name security-sentinel-law # Enable data connector: Azure Activity az sentinel data-connector create \ --resource-group security-rg \ --workspace-name security-sentinel-law \ --data-connector-id "AzureActivity" \ --name "AzureActivityConnector" echo "Sentinel workspace ready: $LAW_ID"
Lab 6C: Azure Policy — Deny and DeployIfNotExists
# Assign built-in policy: Deny storage accounts without HTTPS
New-AzPolicyAssignment `
-Name "Deny-Storage-HTTP" `
-DisplayName "Deny storage accounts that allow HTTP" `
-PolicyDefinition (Get-AzPolicyDefinition -Name "404c3081-a854-4457-ae30-26a93ef643f9") `
-Scope "/subscriptions/{subscriptionId}/resourceGroups/security-rg"
# Create custom Deny policy — require tags on resources
$policyDef = @{
mode = "All"
policyRule = @{
if = @{
field = "tags['Environment']"
exists = "false"
}
then = @{
effect = "Deny"
}
}
}
$policy = New-AzPolicyDefinition `
-Name "Require-Environment-Tag" `
-DisplayName "Require Environment tag on all resources" `
-Policy ($policyDef | ConvertTo-Json -Depth 10)
# Assign the custom policy
New-AzPolicyAssignment `
-Name "Require-Tag-Assignment" `
-PolicyDefinition $policy `
-Scope "/subscriptions/{subscriptionId}/resourceGroups/security-rg"
# Check compliance state
Get-AzPolicyState `
-PolicyAssignmentName "Require-Tag-Assignment" `
-ResourceGroupName "security-rg" |
Select-Object ResourceId, ComplianceState, PolicyDefinitionName
Lab 6D: Key KQL Queries for Security Operations
// ---- AUTHENTICATION EVENTS ----
// Failed sign-in attempts by location
SignInLogs
| where TimeGenerated > ago(24h)
| where ResultType != 0
| summarize FailedAttempts = count() by Location, UserPrincipalName
| top 20 by FailedAttempts
// Successful sign-ins from high-risk locations
SignInLogs
| where TimeGenerated > ago(7d)
| where ResultType == 0
| where RiskLevelDuringSignIn in ("medium", "high")
| project TimeGenerated, UserPrincipalName, IPAddress, Location, RiskLevelDuringSignIn
| order by TimeGenerated desc
// ---- PRIVILEGED ACTIVITY ----
// New global admin assignments
AuditLogs
| where TimeGenerated > ago(24h)
| where OperationName == "Add member to role"
| extend RoleName = tostring(parse_json(tostring(TargetResources[0].modifiedProperties))
[1].newValue)
| where RoleName contains "Global Administrator"
| project TimeGenerated, Initiator = tostring(InitiatedBy.user.userPrincipalName),
TargetUser = tostring(TargetResources[0].userPrincipalName), RoleName
// ---- RESOURCE CHANGES ----
// High-impact Azure ARM operations (deletes, security changes)
AzureActivity
| where TimeGenerated > ago(24h)
| where ActivityStatusValue == "Succeeded"
| where OperationNameValue has_any ("delete", "Write/securityPolicies", "Write/locks")
| project TimeGenerated, Caller, OperationNameValue, ResourceGroup, _ResourceId
| order by TimeGenerated desc
// ---- DEFENDER ALERTS ----
// High severity Defender for Cloud alerts
SecurityAlert
| where TimeGenerated > ago(7d)
| where AlertSeverity == "High"
| where ProviderName has "ASC"
| project TimeGenerated, AlertName, Description, RemediationSteps, Entities
| order by TimeGenerated desc
// ---- NETWORK EVENTS ----
// NSG Flow Logs — denied traffic
AzureNetworkAnalytics_CL
| where TimeGenerated > ago(1h)
| where FlowType_s == "ExternalPublic"
| where FlowStatus_s == "D" // Denied
| project TimeGenerated, DestIP_s, DestPort_d, SrcIP_s, NSGList_s
| summarize Count = count() by SrcIP_s, DestPort_d
| top 20 by Count
Key Azure Security Architecture Patterns
Defence-in-Depth (Azure Implementation)
Layer 1: Identity (Conditional Access, MFA, PIM) Layer 2: Perimeter (DDoS, Azure Firewall, WAF) Layer 3: Network (NSGs, VNet isolation, Private Endpoints) Layer 4: Compute (JIT access, Disk Encryption, Defender for Servers) Layer 5: Application (Key Vault, App Service auth, API keys) Layer 6: Data (Storage encryption, SQL TDE, Always Encrypted)
Zero Trust Principles in Azure
- 1. Verify explicitly: Conditional Access validates EVERY request (identity, device, location, risk)
- 2. Least privilege: PIM for JIT access, RBAC at minimum scope, Managed Identities over service accounts
- 3. Assume breach: Sentinel for SIEM, Defender for threat detection, segmentation via NSGs + Firewall
🔑 Pre-Exam Checklist
Domain 1 — Identity
- [ ] Know ALL Entra ID P2 features by heart
- [ ] Can explain PIM eligible vs active WITHOUT looking at notes
- [ ] Know every Conditional Access condition and grant control
- [ ] Understand the difference between Identity Protection risk policies and Conditional Access
- [ ] Know managed identity use cases cold
Domain 2 — Networking
- [ ] NSG rule evaluation order with subnet + NIC
- [ ] Azure Firewall rule processing: DNAT → Network → Application
- [ ] Firewall SKU features (especially Premium features)
- [ ] WAF Detection vs Prevention — which blocks, which logs
- [ ] Private endpoint DNS: what breaks without the private DNS zone
Domain 3 — Compute/Storage/DB
- [ ] Key Vault access policies vs RBAC — mutually exclusive
- [ ] Soft-delete retention vs purge protection — and that purge protection CANNOT be disabled
- [ ] SAS types — User Delegation SAS = most secure (uses Entra ID)
- [ ] ADE vs SSE vs encryption at host
- [ ] SQL Always Encrypted vs DDM — encryption vs masking
Domain 4 — Security Operations
- [ ] ALL Defender plans and what each protects
- [ ] Sentinel analytics rule types (Scheduled, NRT, Fusion, ML)
- [ ] Azure Policy effects in order
- [ ] DeployIfNotExists requires managed identity
- [ ] KQL: can write a basic query with where, summarize, project
*AZ-500 Study Guide 2026 — aligned with official exam objectives*