Skip to content

Azure Windows Server Firewall Bastion

Azure Hub-and-Spoke Landing Zone

Project Type

Cloud networking project — enterprise hub-and-spoke topology with centralized firewall, Bastion access, VNet peering, user-defined routes, and least-privilege segmentation.


Project Overview

This project covers the design, deployment, and validation of a hub-and-spoke network on Azure — one hub VNet hosting shared services (Bastion, Firewall, management) and two spoke VNets representing isolated workload tiers, connected via VNet peering with traffic controlled through a centralized Azure Firewall.

Goals

  • Implement a hub-and-spoke topology aligned with Microsoft's Cloud Adoption Framework landing zone reference
  • Centralize secure access via Azure Bastion (Standard SKU) — zero public IPs on workloads
  • Enforce spoke isolation by default (non-transitive peering) and enable controlled inter-spoke communication through a hub firewall
  • Demonstrate least-privilege segmentation between application and database tiers using firewall rules and UDRs
  • Validate connectivity, isolation, and policy enforcement through structured test plans

Architecture

Logical Topology

Hub-and-Spoke Topology

Network Segments

VNet Address Space Role Resource Group
vnet-hub 10.0.0.0/16 Shared services hub rg-hub-network
vnet-spoke1 10.1.0.0/16 Application tier rg-spoke1-prod
vnet-spoke2 10.2.0.0/16 Database tier rg-spoke2

Hub Subnets

Subnet CIDR Purpose
AzureBastionSubnet 10.0.1.0/26 Azure Bastion (Standard)
snet-mgmt 10.0.2.0/24 Management VMs
AzureFirewallSubnet 10.0.3.0/26 Azure Firewall (Standard)

VNet Peering Matrix

Pair Hub-side link Spoke-side link State
Hub ↔ Spoke 1 spoke-1-to-hub hub-to-spoke-1 Connected
Hub ↔ Spoke 2 spoke2-hub hub-spoke2 Connected

Environment

Compute

Attribute Value
VM SKU Standard D2s_v5 (2 vCPU, 8 GiB)
OS Windows Server 2022 Datacenter
Region Canada Central
Subscription Azure Free Trial ($200 / 30 days)

VM Inventory

VM VNet / Subnet Private IP Public IP Role
VM-hub vnet-hub / snet-mgmt 10.0.2.5 None (Bastion) Management
vm-spoke1 vnet-spoke1 / default 10.1.0.4 None Application tier
vm-spoke2 vnet-spoke2 / default 10.2.0.4 None Database tier

Shared Services (Hub)

Resource Type Details
vnet-hub-bastion Bastion Host Standard SKU, serves all spokes via peering
fw-hub Azure Firewall Standard SKU, private IP 10.0.3.4
fw-policy-hub Firewall Policy Network + application rule collections

Implementation

Phase 1 — Network Foundation

  • Created 3 VNets with non-overlapping /16 address spaces
  • Added hub subnets: AzureBastionSubnet (/26), snet-mgmt (/24), AzureFirewallSubnet (/26)
  • Deployed Azure Bastion (Standard) in the hub — enables browser-based RDP to all VMs including spokes over peering
  • Created VNet peering (hub ↔ spoke1, hub ↔ spoke2) with forwarded traffic enabled
  • Deployed 3 Windows Server 2022 VMs, one per VNet
  • Enabled ICMP on all VMs for connectivity testing:
Enable-NetFirewallRule -Name FPS-ICMP4-ERQ-In

Critical

Windows Firewall blocks ICMP by default. Skipping this step causes false-negative ping results that look like broken peering.


Phase 2 — Secured Hub (Azure Firewall + UDRs)

  • Deployed Azure Firewall Standard in AzureFirewallSubnet (private IP: 10.0.3.4)
  • Created User-Defined Route tables on each spoke subnet pointing cross-spoke traffic to the firewall:
Route Table Destination Next Hop
rt-spoke1 10.2.0.0/16 10.0.3.4 (Virtual Appliance)
rt-spoke2 10.1.0.0/16 10.0.3.4 (Virtual Appliance)
  • Configured firewall policy with least-privilege network rules:
Rule Source Destination Protocol Port Action
app-to-db-sql 10.1.0.0/16 10.2.0.0/16 TCP 1433 Allow

Key Concept

UDR creates the path; the firewall rule controls what's allowed. Deploying a firewall without routing does nothing — traffic never reaches it.


Phase 3 — Private PaaS (Planned)

  • Azure SQL Database with public access disabled
  • Private Endpoint in vnet-spoke2 giving the database a private IP
  • Private DNS Zone (privatelink.database.windows.net) linked to all VNets for automatic private name resolution
  • Validation: app tier connects to SQL privately through the firewall; public internet access to SQL fails

Troubleshooting

Bastion Connection Dropping in Browser

Symptom: Bastion threw "network connection appears unstable" and disconnected immediately.

Root Cause: Browser ad-blocker/privacy extension killed the persistent WebSocket connection.

Resolution: Opened Azure portal in Incognito/InPrivate window — connected immediately. Permanent fix: whitelist portal.azure.com and *.bastion.azure.com.


VM Size Not Available — NotAvailableForSubscription

Symptom: No B-series (free-tier) VMs appeared in the size picker for Canada Central.

Root Cause: Two Basics-tab filters hiding cheap SKUs simultaneously — Availability Zone = Zone 1 and Security type = Trusted launch.

Resolution: Set Availability options to No infrastructure redundancy required and Security type to Standard.

Diagnostic tip

When Azure says a size is unavailable, check whether your filters are hiding it before assuming the region lacks capacity.


Spoke-to-Spoke Ping Succeeds When It Shouldn't

Symptom: After adding a firewall, spoke-to-spoke ping unexpectedly works without an explicit allow rule.

Root Cause: Gateway transit or a UDR misconfiguration is bridging the spokes, or an ICMP allow rule was left from testing.

Resolution: Remove any temporary ICMP allow rules. Verify no gateway transit is enabled on peering settings.


Validation

Phase 1 — Peering & Isolation

Test From To Expected Result
T1 Hub → Spoke1 VM-hub 10.1.0.4 Success ✅ Passed
T2 Hub → Spoke2 VM-hub 10.2.0.4 Success ✅ Passed
T3 Spoke1 → Hub vm-spoke1 10.0.2.5 Success ✅ Passed
T4 Spoke2 → Hub vm-spoke2 10.0.2.5 Success ✅ Passed
T5 Spoke1 → Spoke2 vm-spoke1 10.2.0.4 Timeout ✅ Passed
T6 Spoke2 → Spoke1 vm-spoke2 10.1.0.4 Timeout ✅ Passed

Phase 2 — Firewall Control

Test Condition Expected Result
A1 Routes set, no allow rule spoke1 → spoke2 Timeout (default deny)
A2 ICMP allow rule added spoke1 → spoke2 Success
B1 Port 1433 (SQL) spoke1 → spoke2 Allowed
B2 Port 3389 (RDP) spoke1 → spoke2 Blocked

Key Learnings

  • Designing and deploying Azure hub-and-spoke aligned with Cloud Adoption Framework landing zone patterns
  • Configuring VNet peering with forwarded traffic and gateway transit controls
  • Deploying and managing Azure Bastion (Standard) for centralized, zero-public-IP access across peered VNets
  • Implementing Azure Firewall with policy-based rule collections for inter-spoke traffic control
  • Creating User-Defined Routes to force traffic through a centralized inspection point
  • Understanding the distinction between NSG (5-tuple filtering) and Azure Firewall (FQDN, application-layer, IDS/IPS)
  • Private Endpoints and Private DNS Zones for securing PaaS services without public exposure
  • Managing Azure free-trial cost constraints — budget alerts, SKU selection, teardown discipline

Core principle: Hub-and-spoke centralizes shared, expensive, security-sensitive services in a single hub. Spokes are isolated by default; cross-segment traffic routes through the hub firewall via UDRs. The routing creates the path; the firewall rule controls the permission.


Tools & Technologies

Category Technology
Cloud Platform Microsoft Azure
Networking VNet, VNet Peering, UDR, NSG
Firewall Azure Firewall (Standard)
Secure Access Azure Bastion (Standard SKU)
Compute Azure VMs (D2s_v5, Windows Server 2022)
PaaS Security Private Endpoints, Private DNS Zones
Framework Microsoft Cloud Adoption Framework (Landing Zones)
Diagnostics ping, Test-NetConnection, Azure Network Watcher
Cost Management Azure Cost Management + Budget Alerts