External Ingress Control for Cloud Run
By: Betsy Varghese
Tags: Cloud Armor, Google Cloud Run, Security, Cloud Load Balancers

How do we do it? Cloud Load Balancing and Cloud Armor! Network-based ingress controls can be implemented with the help of a load balancer that has security policies attached to it, ensuring that only trusted sources can access the load balancer. This can be done in addition to allowing only authenticated invocations of the service. For this tutorial, we’ll be whitelisting our own IP address.

Network diagram

We’ll be going through how we can set this up, step-by-step. Begin by following this Quickstart tutorial provided by Google Cloud to set up our Cloud Run service (pick any language you’re comfortable with). Once you’ve got your container up and running, register a domain name for your service (we will be using this later).

Cloud Load Balancing

Cloud Load Balancing is a service that helps you manage traffic to your resources. We’re going to set up an HTTPS Load Balancer for our service.

Head over to the Load Balancing page in the console. Start the configuration for HTTP(S) Load Balancing. Choose “From internet to my VMs” for the Internet facing or internal only option, and click continue. Choose an appropriate name for your load balancer.

Now you’ll have to configure the load balancer’s host rules and path matchers, backend, and frontend.

Backend

We’re going to create a serverless network endpoint for the backend. A network endpoint group (NEG) specifies a group of backend endpoints for a load balancer. To point to a Cloud Run, App Engine, or Cloud Functions service (all serverless), we use serverless NEGs. Depending on the service, these serverless NEGs can represent a single service or a group of services using URL masking. (Note that serverless NEGs can only be set up with HTTPS Load Balancing!)

Click backend configuration and select Create or select a backend service>Backend services>Create a backend service. Choose a name for the backend service. For Backend type, select Serverless network endpoint group. For the Protocol, select HTTPS. Select Backends>New backends>Create serverless network endpoint group. Choose a name for your serverless NEG. Pick the region your container is running in. Select Serverless network endpoint group type>Cloud Run. Select the helloworld service you’ve created from the Select service name dropdown. Click Create.

Finally, click Done under New backend window and click Create.

Host Rules and Path Matchers

Leave the host rules and path matchers to their default values, meaning that all requests go to the service you choose in the backend.

Frontend

Click Frontend configuration, and enter a Name. Create a free Google-managed SSL certificate for the domain name you registered earlier. This is needed to create an HTTPS Load Balancer. Click Done.

We’ve configured all aspects of the load balancer, and can now click Create. When it is done being created, click on the name of the load balancer and note the IP address associated with it in the Frontend configuration. Point the DNS A record of your domain name to this IP address. This is the URL we will use to access our service.

Load balancer IP

Congratulations! We’re nearly done. All we need to do now is to add IP whitelisting.

Cloud Armor

Cloud Armor is a Google offering that provides a web application firewall to control traffic to your applications. Find out what your IP address is, and head to the Cloud Armor page.

Click Create policy and choose a Name for the policy. Under Default rule action, click Deny. Under Add more rules, click Add Rule. Under Mode, click Basic. Under Match, enter your IP address. Under Action, click Allow. Under Priority, enter 0. This gives maximum priority for this rule. Click Done. Under Apply policy to targets, click Add Targets. Under Type, select Load Balancer backend service Under Target, select the backend service created before Click Done.

Finally, click Create policy. We’ve asked Cloud Armor to deny all traffic to the load balancer, with the exception of our IP address. You can also add a response for denied traffic.

Cloud Armor policy

Deny response configuration

Now’s a good time to find out if our setup works. Access your domain from your device using the required authentication. An easy way to do this is to click “Show information on service URLs” (available next to the service URL on the Cloud Run console) and copy the invocation provided. Replace the service URL with your registered domain name.

Service URL invocation

When I access this using my whitelisted device, I get the following output:

Whitelisted IPs response

What about from other IPs? Try the same invocation from Cloud Shell, which is run on a temporary VM and has an ephemeral IP.

Bad Gateway response

And there we have it! Only whitelisted IPs are able to access the Cloud Run service, providing a layer of security to our resources.

Happy building!

References

Note

Currently, there is an alpha feature of Cloud Run that enables us to set the ingress parameter to “internal-and-cloud-load-balancing”. This ensures that only inbound requests from VPCs in the same project or Google Cloud Load Balancing are allowed to access the service URL. You can sign up to enable this for your project, or wait until it is GA.