Guide to connect to multiple databases using Mongoose
People who are used to building apps with Mongo and Nodejs should be familiar with Mongoose which is an ORM for MongoDB. Though there are other competitive ORMs available, it is one of the most popular and efficient ORMs for Mongo connectivity. When I build my applications, my first choice would be to use a Mongo database. The main reason is that I have used it on many apps and find it comfortable to use.
I recently had a requirement to establish connections and work on multiple Mongo databases within my backend application. More like switching between multiple databases based on user requests. There were a few solutions that I came across online and finally fixed with a solution.
- Have multiple connection strings saved in the config file and switch between them or connect to each one of them. This can work if we are working only on a few databases.
- Opening and closing connections for every request.
- Have a single connection to a master database and switch to other databases internally using useDb feature.
I solved my need with the third solution. In my case, I was using models and I wanted them to be common for all the databases. That's why I came up with this solution and it works well. I'm going to walk through the code step by step.
Note: I'm assuming that the readers are familiar with Nodejs and MongoDB. I'm not going to be covering the complete code of the backend application.
Step 1: Creating the db.js file
This file will have basic connection information to the database. I usually keep this file separately and establish the connection only by including this file in my main file. It helps in modularizing the code.
const mongoose = require('mongoose');
const database = 'mongodb://localhost:27017/primary';
mongoose.connect(database, {});
const db = mongoose.connection;
// Check DB Connection
db.once('open', () => {
// eslint-disable-next-line no-console
console.log('Connected to MongoDB');
});
// Check for DB errors
db.on('error', (err) => {
// eslint-disable-next-line no-console
console.log('DB Connection errors', err);
});
module.exports = mongoose;
If you notice I would have primary
as my database. This is the primary database that I would be connecting to. Only from that database, I would be switching to other databases whenever needed.
Step 2: Creating my model file client.js
The next step would be to create my model file that will have the schema of my collection. I wanted to have a single model file created for a collection that I would be using across all the databases.
const mongoose = require('mongoose');
// eslint-disable-next-line prefer-destructuring
const Schema = mongoose.Schema;
const clientSchema = new Schema(
{
clientNumber: {
type: Number,
required: true,
},
clientName: {
type: String,
required: true,
},
},
{ versionKey: false, minimize: false },
);
const client = async (db) => {
const myDB = mongoose.connection.useDb(db);
const Client = myDB.model('Client',clientSchema);
return Client;
};
module.exports = { client };
In the above model file, I have a schema for the Client with two fields in that. If you look at the code, I have a function towards the end of the code that accepts the database as the input parameter and gives the model as the output parameter.
Step 3: My main.js file
In my main.js file, I have the below code to create a new client. I have included both of the above files in this main file. I wanted to test it out by creating a client on multiple databases at the same time.
require('./db');
const { client } = require('./client');
// Saving to primary database
(async () => {
const Client = await client('primary');
const c = new Client();
c.clientNumber = 1234;
c.clientName = 'Test Client';
await c.save();
})();
// Saving to secondary1 database
(async () => {
const Client = await client('secondary1');
const c = new Client();
c.clientNumber = 1234;
c.clientName = 'Test Client';
await c.save();
})();
// Saving to secondary2 database
(async () => {
const Client = await client('secondary2');
const c = new Client();
c.clientNumber = 1234;
c.clientName = 'Test Client';
await c.save();
})();
As we all know Nodejs is asynchronous by default, when we execute the main.js file, it executes all the 3 functions at the same time creating the same entry on 3 different databases. This is an example to show how we can pass the database name as a parameter to the model and perform operations on specific models in each database.
If you like what I'm doing on Hive, you can vote me as a witness with the links below.
|
|
|
|
|
|
This post has been manually curated by @bhattg from Indiaunited community. Join us on our Discord Server.
Do you know that you can earn a passive income by delegating to @indiaunited. We share more than 100 % of the curation rewards with the delegators in the form of IUC tokens. HP delegators and IUC token holders also get upto 20% additional vote weight.
Here are some handy links for delegations: 100HP, 250HP, 500HP, 1000HP.
100% of the rewards from this comment goes to the curator for their manual curation efforts. Please encourage the curator @bhattg by upvoting this comment and support the community by voting the posts made by @indiaunited.
Wow it quite looks a bit complicated for me or probably I have little understanding of how these things actually works though
This seem hard, lol but thanks very much for the lecture
It was a good one
Mongo has seen quite decent adaptation. It fits well with needs of all scale of projects and provides flexibility to work with complex data structures. Good to see blogs on programing, very well explained. keep posting.
Well detailed and thank you for sharing this. It will really help to open a lot of people eyes to see this
Congratulations @balaz! You have completed the following achievement on the Hive blockchain And have been rewarded with New badge(s)
Your next payout target is 2000 HP.
The unit is Hive Power equivalent because post and comment rewards can be split into HP and HBD
You can view your badges on your board and compare yourself to others in the Ranking
If you no longer want to receive notifications, reply to this comment with the word
STOP