Skip to content
This repository has been archived by the owner on Dec 17, 2023. It is now read-only.

Troubleshooting Google Cloud Run

tpAtalas edited this page Mar 6, 2023 · 10 revisions

Table of Contents

Connection issue with MongoDB Atlas (Dedicated Tier) and Google Cloud Run

This only works for Dedicated Tier plans and free tier or shared tier may add 0.0.0.0/0 to the Network Access, but this may pose the security issue and is not the recommended solution.

Issue

Google Cloud Run is unable to connect to MongoDB.

Example of the common Error Message:

MongoNetworkError: connection 1 to 22.199.200.204:27017 closed

Cause

MongoDB Atlas does not allow the Network Access to the database. The CloudRun as serverless service does not have static IP address, but only dynamic IP address unless static IP is assigned through another Load Balancing or VPC Connector.

Solution

VPC peering between Google Cloud Platform and MongoDB Atlas and whitelist IP on MongoDB Atlas

VPC peering in MongoDB Atlas is a feature that allows you to connect Virtual Private Cloud (VPC) within a single Region. This allows you to securely and privately access your MongoDB Atlas cluster from resources within another VPC.

Initiate Peering in MongoDB Atlas

  1. Login to MongoDB Atlas web console.
  2. Navigate to the Security tab and click on the Network Access option on the left panel.
  3. Click Peering tab and click ADD PEERING CONNECTION in the top-left corner.
  4. Click Google Cloud and Next.
  5. Add Project ID, which is found on the Google Cloud Console.
  6. Add VPC Name of Google Cloud Console, which is found on the GCP > VPC network > VPC networks. The default name of VPC Name is default.
  7. The current Atlas CIDR is autofilled, but it is likely 192.168.0.0/16. Then, Click initiate Peering.
  8. You may wait or comeback to copy and save the Atlas GCP Project ID, Atlas VPC Name, and Atlas CIDR for next steps.

Initiate Peering in Google Cloud Platform

  1. Go to Google Cloud Console Network Peering or Google Cloud > VPC network > VPC network peering.
  2. Click CREATE CONNECTION > CONTINUE.
  3. Name the peering connection on Name input, such as mongodb-atlas-peering, on the Name.
  4. Select default on the dropdown of Your VPC network.
  5. Select In another project on Peered VPC network.
  6. Enter Project ID with Atlas GCP Project ID, which you have copied from 'Initial Peering in MongoDB Atlas'.
  7. Enter VPC network name with Atlas VPC Name, which is also copied from previous steps.
  8. Click CREATE and wait.

Whitelist Private IP ranges

GCP networks generated in auto-mode use a CIDR range of 10.128.0.0/9

  1. Go to IP Access List tab and click ADD IP ADDRESS.
  2. Add 10.128.0.0/9 IP Address ranges then Confirm.

Connection issue with MongoDB Atlas (Serverless Tier and Free/Shared Tier) and Google Cloud Run

Note: This method causes the cost besides to the Google Cloud Run

Issue

Google Cloud Run is unable to connect to MongoDB.

Example of the common Error Message:

MongoNetworkError: connection 1 to 22.199.200.204:27017 closed

Cause

The Cause is still same as above that 3 MongoDB Atlas does not allow the network access.

Solution

More Info: Static Outbound IP to CloudRun

As VPC peering only works on Dedicated tier plan on MongoDB Atlas, the static IP must be assigned to CloudRun through VPC connector.

Assign Static IP to CloudRun

  1. Create a sub-network
#gcloud compute networks subnets create SUBNET_NAME \
#--range=RANGE --network=NETWORK_NAME --region=REGION
gcloud compute networks subnets create example-subnet \
--range=10.124.0.0/28 --network=default --region=us-central1
  1. Create a Serverless VPC Access connector
# gcloud compute networks vpc-access connectors create CONNECTOR_NAME \
#   --region=REGION \
#   --subnet-project=PROJECT_ID \
#   --subnet=SUBNET_NAME
gcloud compute networks vpc-access connectors create example-connector \
  --region=us-central1 \
  --subnet-project=example-project-id \
  --subnet=example-subnet
  1. Configuring network address translation (NAT)
  • Create a new Cloud Router
# gcloud compute routers create ROUTER_NAME \
#   --network=NETWORK_NAME \
#   --region=REGION
gcloud compute routers create example-router \
  --network=default \
  --region=us-central1
  • Reserve Static IP
# gcloud compute addresses create ORIGIN_IP_NAME --region=REGION
gcloud compute addresses create example-ip-static --region=us-central1
  • Create Cloud NAT gateway configs
# gcloud compute routers nats create NAT_NAME \
#   --router=ROUTER_NAME \
#   --region=REGION \
#   --nat-custom-subnet-ip-ranges=SUBNET_NAME \
#   --nat-external-ip-pool=ORIGIN_IP_NAME
gcloud compute routers nats create example-nat \
  --router=example-router \
  --region=us-central1 \
  --nat-custom-subnet-ip-ranges=example-subnet \
  --nat-external-ip-pool=example-ip-static
  1. Routing Cloud Run traffic through VPC network

IMAGE_URL can be found on the Google Cloud Platform > Cloud Run click service-name > REVISIONS tab under CONTAINERS as image URL

# gcloud run deploy SERVICE_NAME \ # service name you have deployed with
#    --image=IMAGE_URL \
#    --vpc-connector=CONNECTOR_NAME \
# --vpc-egress=all-traffic
gcloud run deploy example-service-name \
   --image=docker.pkg.dev/cloudrun/container/example-app:lastest \
   --vpc-connector=example-connector \
   --region=us-central1 \
   --vpc-egress=all-traffic

Assign IP address to MongoDB Atlas

  1. Go to MongoDB Atlas.
  2. Go to Network Access > IP Access List > Click ADD IP ADDRESS.
  3. Add IP address you have assigned from Google Cloud Platform, which can be found under VPC network > IP addresses, and then click Confirm.

Environment Variables defined within Google Cloud Run are not available

Issue

After deploying to Google Cloud Run, the environment variables that must be publicly available, or accessible within client, are returning undefined.

Cause

Environment variables defined within Google Cloud Run are only available during the runtime, but not build time. Next.js may require some values from environment variables during the build process. If it does, this may cause the undefined environment variables after deploying to Google Cloud Run because the value cannot be accessed during the build time.

Solution

This issue can be resolved by implementing build time substitution of environment variables.

  1. Go to Dockerfile.
  2. Add the substitution.

Build time substitution environment variable holds the value during the build time then insert the actual environment variable values defined within Google Cloud Run during the deployment phase.

...
# Build time substitution
# add prefix BUILD_
ARG BUILD_IMAGE_DOMAIN

# IMAGE_DOMAIN is the actual environment variable that is required during the
# the build time
ENV IMAGE_DOMAIN $BUILD_IMAGE_DOMAIN
...
  1. Add the build flag on the docker build command.
# IMAGE_DOMAIN is the environment variable defined within Google Cloud Run
docker build --build-arg BUILD_IMAGE_DOMAIN=$IMAGE_DOMAIN -t example-project:latest
  1. [Optional] Semi-automate the process.

This process is automated with deploy.sh as long as GCR_ prefix is added.

Although It is still manual to define the build time environment variable within Dockerfile, deploy.sh will automatically pick up the environment variables with prefix GCR_ and add them into Google Cloud Run's environment variable, but also make them available during the build time

# ARG BUILD_IMAGE_DOMAIN
# ENV IMAGE_DOMAIN $BUILD_IMAGE_DOMAIN
ARG BUILD_IMAGE_DOMAIN
ENV GCR_IMAGE_DOMAIN $BUILD_IMAGE_DOMAIN