Securely Connecting Lambda to MongoDB Atlas through VPC Peering

Published on December 10, 2022

By Hyuntaek Park

Senior full-stack engineer at Twigfarm

MongoDB Atlas has several network security options. One of them is traditional IP whitelisting, which is very convenient when your business logic, which needs access to the MongoDB Atlas, has a static IP address. Or you can set 0.0.0.0/0 to access to the database, which opens your database to the public. It is very dangerous and you should avoid it.

At Twigfarm, we use AWS lambda very often. We had cases where our lambdas needs access to the MongoDB Atlas database. As you might already know, unlike AWS EC2, you cannot set a static IP address for AWS lambda easily. It is possible using an AWS NAT Gateway but requires a bit of work, which is out of scope in this article. I will cover that topic later if I have a chance.

Prerequisites

  • A database is setup on MongoDB Atlas
  • Have your MongoDB Atlas connection string ready

Create a lambda function

Let’s create a lambda function that is trying to access to the MongoDB Atlas database. Obviously, it is not going to work and gets timeout because the MongoDB Atlas database does not allow this connection yet.

Lambda code is as the following; the code snippet is copied from here and modified.

You need MongoDB Nods.js Driver to run the following code. Please refer to the following link: https://www.npmjs.com/package/mongodb

To use the third-party library in a lambda, I prefer to have the libraries in a layer. You can refer to the following link for layers in lambda functions. https://docs.aws.amazon.com/lambda/latest/dg/configuration-layers.html

const { MongoClient } = require("mongodb");

// Connection URI
const uri = process.env.MONGODB_URI;

// Create a new MongoClient
const client = new MongoClient(uri, {
  useUnifiedTopology: true,
});

exports.handler = async (event) => {
  try {
    // Connect the client to the server (optional starting in v4.7)
    await client.connect();
    // Establish and verify connection
    await client.db(YOUR_DB_NAME).command({ ping: 1 });
    console.log("Connected successfully to server");
  } finally {
    // Ensures that the client will close when you finish/error
    await client.close();
  }
};

Then we set the MONGODB_URI to your MongoDB Atlas connection string. image

Then you click the Test button to run the lambda function. If you haven’t created a test case before, just leave everything as it is and name the test case and save it. Then click the Test button again.

You should get a timeout response such as the following because your lambda is not whitelisted in the MongoDB Atlas database.

Response
{
  "errorMessage": "2022-12-10T10:16:28.767Z 8bd39e1c-f688-409c-93f1-eaa13c6b46a6 Task timed out after 3.01 seconds"
}

Create a VPC

Go to AWS VPC. Then click Create VPC button. image

Here I have a couple of public subnets and no private subnets for simplicity.

image

These are the result of the VPC creation and highlighted are strings to be used at the MongoDB Atlas

Create a VPC peering at MongoDB Atlas

Log in to MongoDB Atlas and choose your project to connect to the lambda function. Click Network Access and select Peering tab. I have a few VPC peering connections already but, likely, that you don’t have any. Click ADD PEERING CONNECTION button to create a new connection.

image

Choose AWS. Click Next.

Fill in the Account ID, VPC ID, and VPC CIDR with the above VPC information. Then click Initiate Peering. image

Accept peering connection requests in AWS

Now go back to the AWS VPC and choose Peering connections. Choose the peering connection and then Actions and choose Accept request.

image

You’ll see the Status is changed to Active.

Setting up the route table

This is is the last step of the VPC Peering. Go to the AWS VPC then choose the Route tables. Choose the route table for the VPC and click Edit routes then Add route.

Add the VPC CIDR value we obtained from the MongoDB Atlas Peering Connection. In my case, it is 192.168.248.0/21 for the Destination field. Choose the Peering Connection and the Peering connection ID for the Target field.

image

Configure lambda’s VPC

Now the connection is made. Let’s go back to the lambda and do the VPC configurations.

Go back to the lambda we created and choose Configuration and VPC. Then click Edit button.

image

Then fill in the VPC information and click Save button. image

Final testing

Now the lambda and the MongoDB Atlas database are connected securely. Let’s do the same testing that we did at the beginning of this article. Now you will be able to see the “Connected successfully to server” in your log.

For more information about the VPC Peering Connection, you can refer to the MongoDB Atlas tutorial as well https://www.mongodb.com/docs/atlas/security-vpc-peering.