MongoDB Replica Set with Master-Slave Replication and Automated Failover

19

A replica set is a term used for defining a database cluster of multiple nodes with master-slave replication and automated failover configured between them. Such a structure usually requires an odd number of nodes, either with an arbiter node or not, to ensure the correct PRIMARY (master) database election. This selected database node will process all the incoming write operations, storing the information about them within its oplog, where they can be accessed and replicated by every secondary (slave) replica node for being applied to their data sets. In such a way, all database servers will represent the same content and ensure its availability.

4217-1-mongodb-replica-set

In case an unexpected issue occurs, causing downtime of the PRIMARY database (e.g., due to hardware failure or connection interruption), a new election process will be initiated automatically, helping to restore the normal application functioning with no manual intervention required. In such way, a replica set inherits the benefits of the usual replication (like failover redundancy, increased data availability and read capacity, disaster recovery, etc.) and simultaneously eliminates the complexity of managing numerous databases separately.

Here is a simple instruction that will show you how to create and configure a MongoDB replica set with three nodes – such a complexion is considered to ensure enough margin of information safety and sufficient out-turn to handle the required amount of I/O operations for most of the commonly used applications. Below we will discover how to prepare the appropriate environment, set authentication between database nodes, configure the replication itself and make sure everything is tuned properly.

Create MongoDB Environment

To start with, you need at least three MongoDB nodes in order to configure a replica set, so let’s create such an environment. In this example, we will allocate three MongoDB instances of version 4.0.10 within a single environment.

4217-1-mongodb-replica-set-create-environment

If required, change the Environment Name and the destination Region. Once the installation is completed you have to take care about the security of the nodes communication with the help of an authentication key file.

Add MongoDB Authentication Key File

Authentication is an important security assurance process that forces each node of the replica set to identify itself during the inner communication by means of a special unique authentication key file. So let’s generate your own in order to protect the data inside your databases from illegal access:

1. Log into one of database nodes via Web SSH.

4217-1-mongodb-replica-set-ssh-acces

2. Use your own key file or generate one with openssl (key size in bytes (e.g., 741) and file name (e.g., my.key) with the following command:

openssl rand -base64 741 > my.key

3. Now you have to distribute the created key file across all MongoDB instances:

  • Click on the Config button next to your database nodes in order to access the File Manager.
    4217-1-mongodb-replica-set-config-file-manager
  • In the opened configuration tab, find the my.key file under the path: /home/jelastic/my.key and open it. Then copy its content into the clipboard.
    4217-1-mongodb-replica-set-locate-key-file
  • In the keys directory (the full path is /var/lib/jelastic/keys), create a file that the MongoDB instances will be using to authenticate each other (e.g., mongo-set.key).
    4217-1-mongodb-replica-set-create-key-file
  • Paste the clipboard content into it and apply changes by Save for all instances. The mongo-set.key file will be distributed to all MongoDB nodes.
    4217-1-mongodb-replica-set-save-and-distribute-key-file

Configure MongoDB Replication

Since security – as one of the main data management principles – is ensured, you can finally proceed to the replica set configuration itself.

1. Switch to the mongod.conf file inside the etc folder within the same configuration tab for the MongoDB nodes. Scroll down to the replication section, then uncomment it and add the following string specifying the unique name for your replica set (e.g., db-replication):

replSetName: db-replication

2. Add parameter keyFile in section security where you should specify the path to your key file (in this case: /var/lib/jelastic/keys/mongo-set.key).

4217-1-mongodb-replica-set-security-configuration

3. Save the changes for all instances using the appropriate button in the editor window.

4. Restart your database nodes for the new configuration parameters to be applied.

4217-1-mongodb-replica-set-restart-node-container

Note: Keep in mind that once you have finished the replica set configuration, a new PRIMARY database election process will be invoked during all nodes restart or PRIMARY node restart (e.g., PRIMARY database downtime).

5. Next, access the MongoDB server you consider to use as PRIMARY via the SSH protocol.

4217-1-mongodb-replica-set-restart-node

Note: After the PRIMARY database is elected, other replica set nodes will become inaccessible for direct write operations, which means that any changes, configurations, etc. (including access to the web admin panel) can be performed for the current PRIMARY node only. So, you will have to change a connection string in your application to the new PRIMARY node, unless you have arranged priorities for all replica set nodes specifying one node as the preferred PRIMARY.

6. Access the database, which should be replicated, with the following command and appropriate admin user credentials:

mongo -u {user} -p {password} {DB_name}

4217-1-mongodb-replica-set-access-database

  • {user} – administrator username (sent to your email, usually admin by default);
  • {password} – password for the corresponding database user (password can be found within the same email);
  • {DB_name} – name of the database you would like to replicate within this replica set (in this case the default: admin).
Note: In case a new election has occurred, the admin user credentials to log into a new PRIMARY database will be the same as you have used for the old one.

7. Once the connection is established, execute the following commands in order to define parameters for the current MongoDB node and initiate your replica set:

config = {_id : “{replica_set}“, members : [{_id : 0, host:“{current_db_ip}:27017“},]}

rs.initiate()

Obviously, the values in brackets should be substituted with the appropriate data:

  • {replica_set} – name of the replicating database group, specified at the beginning of this section (db-replication in this case);
  • {current_db_ip} – IP address of the chosen database container.
    4217-1-mongodb-replica-set-define-parameters

In this example:

config = {_id : “db-replication“, members : [{_id : 0, host:“172.25.2.119:27017“},]}

4217-1-mongodb-replica-set-enable-configuration

rs.initiate()

4217-1-mongodb-replica-set-initiate-configuration

8. Execute the following command for the remaining database nodes where {db_ip} is IP address of each database node:

rs.add(“{db_ip}:27017“)

4217-1-mongodb-replica-set-add-node

9. After you have added all replication members, you will get a fully functional replica set. In case you would like to ensure everything is configured properly, execute the rs.status() command to get full information about your replica set.

4217-1-mongodb-replica-set-status

MongoDB Replica Set Arbiter

Replication is more reliable if it has an odd number of members in replica set. In case you have created an even number of members (nodes), it would be better to add an arbiter node which maintains a quorum by responding to heartbeat and election requests from other replica set participants:

  • Arbiter doesn’t not store data in it, and it just have to vote in elections when any node fails;
  • Arbiter is a lightweight process, it does not consume a lot of resources;
  • Arbiter simply exchanges user credentials between a set of replicas that are encrypted;
  • It is recommended to run the arbiter on a separate node to achieve high availability.

Let’s add an extra arbiter node to the replica set:

1. Scale out the database cluster horizontally with one extra node:

4217-1-mongodb-replica-set-add-arbiter

4217-1-mongodb-replica-set-arbiter-node

2. In the keys directory create a key file mongo-set.key and paste the content of the similar file from any other previously configured database node.

3. Change mongod.conf:

  • Uncomment the replication section and add replSetName (e.g., replSetName: db-replication);
  • Add the keyFile parameter to the security section (/var/lib/jelastic/keys/mongo-set.key in this case).

4. Restart newly added node to apply the configuration parameters.

4217-1-mongodb-replica-set-restart-arbiter

Note: Do not restart all nodes since it will cause a new PRIMARY election unless you have specified priorities to force a specific node to be elected as PRIMARY database node.

5. The arbiter node is ready to be added to the replica set. At the PRIMARY node issue the following command to add the arbiter to the cluster:

rs.addArb(“{db_ip}:27017“)

Where {db_ip} is the IP address of the newly created arbiter node.

4217-1-mongodb-replica-set-arbiter-added

6. Finally let’s check whether the added node became an arbiter or not. To do this, log into the new node via SSH and connect to the MongoDB instance with the credentials from the respective email you have received upon node creation.

4217-1-mongodb-replica-set-check-arbiter-added

As you can see, the newly added node acts as the arbiter of db-replication ensuring a quorum in any situation.

MongoDB Cluster Availability Testing

The configured advanced MongoDB cluster allows you to connect and perform different operations with it remotely. As an example, let’s get its actual state by connecting and executing a few checkup commands by means of a simple PHP applet.

Obviously, you need an PHP application server for that (e.g., Apache), so either add one to the MongoDB environment (as in this case) or just create it within a separate environment.

1. Press the Change Environment Topology button and add the application server.

4217-1-mongodb-replica-set-change-topology

4217-1-mongodb-replica-set-add-application-server

2. Open the Configuration Manager tab for the added Apache server by selecting the Config icon next to it.

4217-1-mongodb-replica-set-application-server-configuration-manager

3. Navigate to the /var/www/webroot/ROOT directory, open the index.php file and paste the following code instead of its default content:

<?php
    try {
        $mongodbConnectionURI= "mongodb://{db_username}:{db_password}@node{NodeID}-{environment_domain}:27017,node{NodeID}-{environment_domain}:27017,node{NodeID}-{environment_domain}:27017,node{NodeID}-{environment_domain}:27017/?replicaSet={replica_set_name}&readPreference=primary";
    $manager = new MongoDB\Driver\Manager($mongodbConnectionURI);
 
    $command = new MongoDB\Driver\Command(['ping' => 1]);
    $cursor = $manager->executeCommand('db', $command);
    $response = $cursor->toArray()[0];
    var_dump($response);
    echo'<br><br>';
    var_dump($manager->getServers());
    } catch (Exception $e){
        echo $e->getMessage();
        }
?>

Where the following values should be substituted with the corresponding data:

  • {replica_set_name} – replica set name;
  • {db_username} – admin user of the chosen primary database (admin by default);
  • {db_password} – password of the admin user;
  • {NodeID} – identification number of the corresponding node (can be found at the Jelastic PaaS dashboard);
  • {environment_domain} – environment domain (can be found at the Jelastic PaaS dashboard).

4217-1-mongodb-replica-set-node-id-and-environment-domain

Note: You need to specify the ID of every node included to the replica set, within the appropriate mongodbConnectionURI section.

As a result, you will get a similar set of strings:

4217-1-mongodb-replica-set-check-source-code

Don’t forget to Save this file.

4. Apache requires a special module for being able to interact with the MongoDB server, so you need to add it within the PHP configuration.

Go to the etc folder and open the php.ini file. Find the [mongodb] section and remove the semicolon before the extension=mongodb.so line to enable this extension.

4217-1-mongodb-replica-set-php-extension

5. In order to apply the new configuration, click Save within the editor window and hit the Restart Nodes button next to your application server.

4217-1-mongodb-replica-set-restart-application-server

6. Finally, click the Open in Browser icon.

4217-1-mongodb-replica-set-check-open-in-browser

As a result, within a new browser tab, you will see information about your replica set members (nodes) and their accessibility.

4217-1-mongodb-replica-set-check-result

The first line displays the result of the availability check of the replica set, which is performed by the command “ping” (line 6 of index.php):

object(stdClass)#11 (3) { [“ok“]=> float(1) }

Which means that the replica set was successfully tested.

In the next block of the output, full information about the replica set nodes is displayed, which is obtained by means of the getServers function (line 11 of the index.php). For example, you can check some values assigned during the process of creating this replica set:

  • host – IP address of a particular database node;
  • port – current replication node port;
  • [“is_primary”] and [“is_secondary”] – parameters indicating the status of the database server (correspondent values for the chosen primary MongoDB server are true, false and for two other MongoDB servers – false, true respectively).

In addition, you can start and stop any of your database nodes and refresh this page to track changes. In such a way, you can make sure that your MongoDB cluster is available and works as intended, and thus can be applied for any real use case right now!

Get your own high available MongoDB replica set with Jelastic PaaS, simply sign up for a free trial at our Jelastic PaaS platform and follow the instructions.