How to connect to mongoDB Atlas form a deployed application in google cloud

I have created an express server that adds users to mongoDB. On local host it works fine. However when I deployed it to google cloud it doesn’t add anything to the database. So I believe that I need to configure my connection.js differently. Here is the code that I am using:

connection.js:

const mongoose = require('mongoose');
require('dotenv').config({ path: __dirname + '/../../../.env' });

const dbURI = 'mongodb+srv://' + process.env.DBUSER + ':' + process.env.DBPASSWD + process.env.CLUSTER + '.mongodb.net/' +
    process.env.DB + '?retryWrites=true&w=majority';

const dbOptions = {
    useNewUrlParser: true,
    useUnifiedTopology: true
}

const connectToDatabase = async () => {
    mongoose.connect(dbURI, dbOptions)
        .then(result => console.log("Database connected"))
        .catch(error => console.log(error));
};

module.exports = connectToDatabase;

index.js:

const express = require('express');
const exphbs = require('express-handlebars');
const mongoose = require('mongoose');
const handlebars = require("handlebars");
const connectToDatabase = require('./Connection/dbConnection.js');
require('dotenv').config({ path: __dirname + '/./../../.env' })

connectToDatabase();

const app = express();

// Middlewares
app.use(express.json());
app.use(express.urlencoded({ extended: false }));
app.use(express.static('public'));

app.use('', require('./routes/routes.js'));

app.engine('handlebars', exphbs.engine({
    defaultLayout: 'main'
}));
app.set("view engine", "handlebars");

const PORT = process.env.PORT || 3000;
app.listen(PORT, () => console.log(`App listening port ${PORT}`));

And here is what I tried to do to make the deployed app work:

  1. I created a env_variables.yaml and I added the needed connection variables in it as follow:
env_variables:
  KEY = 'random-String-here'
  DBUSER = 'mondodb-atlas-username'
  DBPASSWD = 'mondodb-atlas-password'
  DB = 'database name'
  CLUSTER = '@cluster123.example'
  1. in the app.yaml I have :
includes:
  - env_variables.yaml

runtime: nodejs20
  1. and then I modified the connection.js as:
const mongoose = require('mongoose');
const fs = require('fs');

// Check if the app is deployed by looking for a deployment-specific environment variable
const isDeployed = process.env.DEPLOYED === 'true';

// Function to load environment variables
const loadEnvVariables = () => {
  if (isDeployed) {
    // Use env_variables.yaml when deployed
    const yaml = require('js-yaml');
    const envVarsYaml = fs.readFileSync('env_variables.yaml', 'utf8');
    const envVars = yaml.safeLoad(envVarsYaml);
    return envVars;
  } else {
    // Use .env when running locally
    require('dotenv').config({ path: __dirname + '/../../../.env' });
    return process.env;
  }
};

const env = loadEnvVariables();

const dbURI = 'mongodb+srv://' + env.DBUSER + ':' + env.DBPASSWD + env.CLUSTER + '.mongodb.net/' +
    env.DB + '?retryWrites=true&w=majority';

const dbOptions = {
  useNewUrlParser: true,
  useUnifiedTopology: true
};

const connectToDatabase = async () => {
  mongoose.connect(dbURI, dbOptions)
    .then(result => console.log("Database connected"))
    .catch(error => console.log(error));
};

module.exports = connectToDatabase;

Of course this solution didn’t work. Every time I try to add a user I get Server side error creating a user Even if I am explicitly using the environment variables values in the dbURI. So I am wondering what is the approach that I need to do so that If I am working in development the code uses the dotevn file and if the app is deployed it uses the env_variable file to connect to the database. But maybe the the verification for production and development isn’t needed since mongoDB Atlas is hosted online?

First time deploying an app and first time using Google Cloud. Any help would be much apprecitaed!

Let’s try to simplify this:

const mongoose = require('mongoose');

// Use the MONGODB_URI environment variable directly
const dbURI = process.env.MONGODB_URI;

const dbOptions = {
    useNewUrlParser: true,
    useUnifiedTopology: true
}

const connectToDatabase = async () => {
    mongoose.connect(dbURI, dbOptions)
        .then(result => console.log("Database connected"))
        .catch(error => console.log(error));
};

module.exports = connectToDatabase;

What I wrote this to do in relation to your stuff above, is it’s meant to set your connection to the mongoldb URI unconditionally.

You need to modify a bit better for your environment of course, but something like this is what you probably are more so looking for so that you just focus on the URI being defacto in your deployment.

If you have any questions hit me up, and we can even setup a one on one via discord or google meets if you really need. But this is overall the easiest way to do what what you’re wanting by making google just use the MONGODB_URI.

In your APP.YAML do something like this, of course not exactly but something like it that will put the URI to your YAML env.

env_variables:
  MONGODB_URI: 'mongodb+srv://your-username:your-password@cluster.mongodb.net/your-database?retryWrites=true&w=majority'