In this post I’m going to show you how simple it is to connect cloud services to a virtual network.
Before I do that let me explain a couple of reason of why you would want to do this.
There are a few use cases for this.
Web or Worker Roles that need to:
- Communicate with a Virtual Machine(s)
- Communicate with other web or worker roles in a separate cloud service (same subscription and region though)
- Communicate to an on-premises network over a site to site VPN tunnel (not covered in this post)
In at least the first two cases you could accomplish the connectivity by opening up public endpoints on the cloud services and connecting using the public IP address. However, this method introduces latency because you are making multiple hops over each cloud service load balancer. Not to mention that there is a good chance that the endpoint you are trying to connect to would be more secure if it wasn’t exposed as a public endpoint. Connecting through a VNET is much faster and much more secure.
For this example I’m going to walk through a simple VNET that will accomplish the goal of connecting cloud services.
Step 1: Create an affinity group for your virtual network in the region where your cloud services will be hosted.
Step 2: Create a simple virtual network and specify the previously created affinity group along with a single subnet network configuration.
For the subnet details I am specifying 10.1.0.0/16 which is a class B address space. I’m only carving one subnet (10.1.1.0/24) out of the address space to keep things simple. Unless you need connectivity back to on-premises or are planning to lock down traffic between subnets when Windows Azure supports ACLs this will likely be a sufficient solution for simple connectivity.
Step 3: Deploy a Cloud Service to the VNET.
Unlike deploying a Virtual Machine you cannot specify virtual network settings on provisioning through the portal. The networking configuration goes inside of the .cscfg file of your Windows Azure deployment package.
To connect to this virtual network all you would need to do is paste the following below the last Role tag in your service configuration file (.cscfg) and deploy.
<VirtualNetworkSite name="SimpleVNET" />
<Subnet name="AppSubnet" />
A few things to note about this configuration. If you have multiple roles in your deployment package you will need to add additional InstanceAddress elements to compensate. Another thing to point out is the purpose behind multiple subnets for each role. The idea is if you have an elastic service that has instances added/removed you could conceivably run out of addresses in the subnet you specify. If you specify multiple subnets to the role Windows Azure will automatically pull an address out of the next available subnet when the instance is provisioned if you run out of addresses from the first subnet.
Name resolution is another area to address. When deployed inside of a virtual network there is no default name resolution between instances. So if you are deploying a web role that will connect to a SQL Server running on a virtual machine you will need to specify the IP address of the SQL server in your web.config. For that specific scenario it would make sense to deploy the SQL VM first so you can actually get the internal IP address for your web app. It is of course possible to deploy your own DNS server in this environment. If you do you can specify the DNS server for your web/worker role instances with an additional XML configuration.
This would go right below the NetworkConfiguration element start tag:
<DnsServer name="mydns" IPAddress="10.1.1.4"/>
Finally, to make a truly connected solution you would want to deploy additional services such as VM or other cloud service/web worker roles to the VNET. The beauty of this configuration is every application deployed into this VNET will be on the same virtual network and have direct low latency and secure connectivity.
P.S. Virtual Network and Subnet Names are case sensitive in the configuration file.