Secure Azure App Service to allow communication via private IP address only
Updated: Apr 1, 2019
By default Azure App Service is accessible from Internet over public IP address. If you use App Service to host application that needs to be accessible only from your company network there are several options you can consider.
Ideally securing Azure App Services is accomplished by deployment App Service within Azure App Service Environment (ASE) but this comes with higher cost.
The configuration below allows to achieve this goal without increased cost of deployment App Service within ASE. The required Access Control is achieved by placing App Service behind Application Gateway and using App Service IP restrictions to prevent any client except Application Gateway from accessing the App Service directly.
The diagram below presents an overview of this configuration.
Configuration steps summary
Configure the App Service with custom DNS and application certificate
Load application certificate to Application Gateway and configure Application Gateway in front of the App Service
Change DNS entry to point to to Application Gateway instead of App Service
Configure App Service to allow only Application Gateway IP to reach it
Note: While the configuration steps are shown below in Azure Portal for illustration purposes it is much more efficient to configure Azure Application Gateway via ARM template or PowerShell. The link to ARM template is provided in Automation section at the end of this post.
Configure the App Service with custom DNS
This part is standard and described in many documents. e.g. https://docs.microsoft.com/en-us/azure/app-service/app-service-web-tutorial-custom-domain
Note: Please make sure that TTL is short (e.g. 1 minute) since this DNS entry will need to be reconfigured later.
We also create certificate and and use it for SNI SSL binding for custom domain name.
Configure Application Gateway in front of the App Service
Setup Application Gateway with a private Frontend IP
Create backend pool in the Application Gateway and add the App Service
Create custom probe.
Set host name to a FQDN of the App Service
Configure http settings
Setup the rule and integrate the Listener, Backend pool and HTTP setting
Note: When performing multiple changes to Application Gateway it is a good practice is to ensure that previous changes have been completed before applying the next. Otherwise subsequent configuration may override the previous settings.
Change DNS entry
At the initial configuration of App Service Custom domain, DNS has been configured to point to the App Service using CNAME DNS record. e.g. mysecureappservice.mycustomdomain pointed to mysecureappservice.azurewebsites.net .
Now after Application Gateway is setup, the same DNS name mysecureappservice.mycustomdomain needs to be configured as A record to point to the private IP of Application Gateway.
Configure IP restrictions
Discover IP address that Application Gateway uses to talk to App Service via Log Stream
When an Application Gateway does not have a Public IP of its own and it needs to access a public resource, it will use a pseudo VIP (an available public IP from the data center pool) to initiate the connection.
As per Microsoft support If the APP GW does not have a public IP and we have a public instance added in the backend, then it WILL use a pseudo VIP to make this connection.
Scenarios as follows: If we have added a private IP in the backend pool, like in the case of ILB or VMs, then the APP GW will use its private IP to connect to backend. But in the backend if we have added a public IP or FQDN that resolves to public iP, then the APP needs to use a public IP for the connection. 1. When the APP GW needs to use a public IP for this connection, if it has its own public iP, it will use that. 2. If the APP GW does not have a public IP, then it will use a pseudo VIP.
And as long as we restrict access to allow only this VP it should work. We do not have control over which IP the APP GW would chose. But once chosen, it would not change unless the APP GW is stopped or redeployed.
However in the event that we stop/start or restart the App GW, then there are chances that this VIP changes. In this case we might have to add the new VIP. This IS a supported configuration and in case that it does not work, Microsoft will assist to troubleshoot.
Also as per Microsoft And at this point in time, this data is not readily available on the portal. While we can pull this from the backend, if you would like to do that same, we will have to take captures to understand the public IP.
Based in this information once we have configured App Service to be accessible via Application Gateway we access App Service via Application Gateway front-end IP. Then we use App Service Web log to find out client IP (the one that App Gateway uses to access the App Service). This will be the IP to use for App Service IP restriction configuration in subsequent steps.
To capture logs configure App Service as below.
Alternatively discover IP address that Application Gateway uses to talk to App Service via Advanced Tools
Sometimes Log Stream gets quirky and does not want to show output logs. For this situations there is a longer but sure way to get at the logs - App Service Advanced Tools.
Navigate in command line or simply click through to LogFiles\http\RawLogs. Then download the Web log file and get the IP address that Application Gateway uses to access App Service from it.
Example of the log file is below
Apply IP restrictions to App Service
First test that App Service is accessible via Application Gateway. You should get something like below.
Then try to bypass Application Gateway by accessing App Service Directly via https://yourservicename.azurewebsites.net. Now you should get error message like below.
We are done. Well... almost.