πŸš€ From Zero to Secure: Deploying a Hardened Azure Environment with Terraform & Azure CLI



This content originally appeared on DEV Community and was authored by Achref Rhouma

πŸš€ From Zero to Secure: Deploying a Hardened Azure Environment with Terraform & Azure CLI

Tags: #azure #devops #cloudsecurity #terraform

πŸ“– Why This Guide?

Passing a cloud security quiz is great β€” but real-world deployments require more than memorizing the right answer.

This article takes the concepts behind common Azure security questions and turns them into battle-tested deployments using Azure CLI and Terraform.

You’ll learn how to:

  1. Build a secure Network Security Group with least privilege inbound rules.
  2. Detect & respond to impossible travel sign-ins.
  3. Manage Key Vault data-plane access with Azure RBAC.
  4. Map and implement Defense in Depth layers.

1⃣ NSG Inbound β€” The Right Way

Scenario:

You need to allow HTTPS traffic from the Internet to your app subnet β€” but safely.

Principles:

  • Restrict by port and protocol.
  • Avoid * in source IPs unless unavoidable.
  • Use higher-level protections like WAF where possible.

Azure CLI:

RG=rg-secure-demo
LOC=westeurope
VNET=vnet-secure
SUBNET=app-subnet
NSG=nsg-app
RULE=Allow-HTTPS-Internet
PRIORITY=100

# Create RG and VNet
az group create -n $RG -l $LOC
az network vnet create -g $RG -n $VNET -l $LOC \
  --address-prefixes 10.10.0.0/16 \
  --subnet-name $SUBNET --subnet-prefix 10.10.1.0/24

# Create NSG
az network nsg create -g $RG -n $NSG

# Add inbound HTTPS rule
az network nsg rule create \
  -g $RG --nsg-name $NSG -n $RULE \
  --priority $PRIORITY \
  --direction Inbound --access Allow --protocol Tcp \
  --source-address-prefixes Internet \
  --destination-port-ranges 443

# Attach NSG to subnet
az network vnet subnet update \
  -g $RG --vnet-name $VNET -n $SUBNET \
  --network-security-group $NSG

2⃣ Detecting Impossible Travel

Concept: Impossible travel is when a user logs in from two locations so far apart that traveling between them in the elapsed time is physically impossible.

KQL Query in Log Analytics:

SigninLogs
| where ResultType == 0
| project TimeGenerated, UserPrincipalName, Location = tostring(LocationDetails.countryOrRegion)
| order by UserPrincipalName, TimeGenerated
| extend PrevLocation = prev(Location), PrevTime = prev(TimeGenerated), PrevUser = prev(UserPrincipalName)
| where UserPrincipalName == PrevUser and Location != PrevLocation
| where datetime_diff('minute', PrevTime, TimeGenerated) < 60

Real-World Action:

  • Enable Azure AD Identity Protection.
  • Create Conditional Access policy:
    • Sign-in risk = Medium+
    • Action = Require MFA or Block
  • Start in report-only mode, then enforce.

3⃣ Key Vault Access with RBAC

Scenario:

Grant a specific Azure AD group permissions to create & delete keys in Key Vault.

Azure CLI:

RG=rg-secure-demo
LOC=westeurope
KV=kv-secure-$RANDOM
GROUP_NAME="kv-crypto-admins"

# Create Key Vault
az keyvault create -n $KV -g $RG -l $LOC

# Create AAD group
GROUP_ID=$(az ad group create --display-name "$GROUP_NAME" --mail-nickname "$GROUP_NAME" --query id -o tsv)

# Assign Key Vault Administrator role
ROLE="Key Vault Administrator"
SCOPE=$(az keyvault show -n $KV -g $RG --query id -o tsv)
az role assignment create \
  --assignee-object-id $GROUP_ID \
  --assignee-principal-type Group \
  --role "$ROLE" \
  --scope "$SCOPE"

Best Practice:

Use RBAC instead of legacy access policies for unified permissions management.

4⃣ Implementing Defense in Depth

Layer Mapping:

Layer Controls Azure Services
Perimeter DDoS/WAF, TLS termination Azure DDoS, Front Door
Network Segmentation, ACLs VNet, NSG, ASG
Compute Hardening, patching Azure VM, Defender for Cloud
Identity AuthN/Z, least privilege Entra ID, Conditional Access
Application Input validation, data access Key Vault, Managed Identity
Data Encryption, backups SSE, Azure Backup
Monitoring Detect/respond Log Analytics, Sentinel

🧹 Clean-Up

az group delete -n rg-secure-demo --yes --no-wait

πŸ“Œ Key Takeaways

  • NSG rules should be precise β€” no blanket * inbound.
  • Impossible travel is a high-confidence detection signal.
  • Key Vault RBAC is modern, scalable, and auditable.
  • Security works best in layers.

πŸ’¬ Question for you:

What’s one Azure security trick you use that isn’t in Microsoft’s documentation? Drop it in the comments, and I’ll build a full code example for it.


This content originally appeared on DEV Community and was authored by Achref Rhouma