I have a mongo 3.6 replicaset setup on machine with IP 192.168.1.175
with below command,
$ sudo mongod --port 27017 --replSet "rs0" --bind_ip_all --dbpath ~/data/db/rs1 &
$ sudo mongod --port 27018 --replSet "rs0" --bind_ip_all --dbpath ~/data/db/rs2 &
$ sudo mongod --port 27019 --replSet "rs0" --bind_ip_all --dbpath ~/data/db/rs3
$ rs.initiate( {
_id : "rs0",
members: [
{ _id: 0, host: "localhost:27017" },
{ _id: 1, host: "localhost:27017" },
{ _id: 2, host: "localhost:27017" }
]
})
So I am assuming that since I am using --bind_ip_all
, I am able to connect this replica from the remote machine as well.
Now I am trying to access 192.168.1.175
from the machine with IP 192.168.1.160
, below are the outputs
emgda@ubuntu:~$ mongo 'mongodb://mongomachine:27017,mongomachine:27018,mongomachine:27019/?replicaSet=rs0' --quiet
rs0:PRIMARY> ^C
Below is the small Node.js code to connect to the same mongo URL, but I am getting error.
const MongoClient = require("mongodb").MongoClient;
MongoClient.connect('mongodb://192.168.1.175:27018,192.168.1.175:27017,192.168.1.175:27019/emgda?replicaSet=rs0', { useUnifiedTopology: true })
.then(client => {
console.log("Connected correctly to server");
// specify db and collections
const db = client.db("emgda");
const collection = db.collection("aggregatehourly");
})
.catch(err => {
console.error(err);
});
Below is the output,
{ MongoServerSelectionError: connect ECONNREFUSED 127.0.0.1:27017
at Timeout.waitQueueMember.timer.setTimeout [as _onTimeout] (/home/emgda/Documents/mongo-connection/node_modules/mongodb/lib/core/sdam/topology.js:448:30)
at ontimeout (timers.js:436:11)
at tryOnTimeout (timers.js:300:5)
at listOnTimeout (timers.js:263:5)
at Timer.processTimers (timers.js:223:10)
name: 'MongoServerSelectionError',
reason:
TopologyDescription {
type: 'ReplicaSetNoPrimary',
setName: 'rs0',
maxSetVersion: 1,
maxElectionId: null,
servers:
Map {
'localhost:27017' => [ServerDescription],
'localhost:27018' => [ServerDescription],
'localhost:27019' => [ServerDescription] },
stale: false,
compatible: true,
compatibilityError: null,
logicalSessionTimeoutMinutes: null,
heartbeatFrequencyMS: 10000,
localThresholdMS: 15,
commonWireVersion: 6 },
[Symbol(mongoErrorContextSymbol)]: {} }
When run a command on mongo shell on local machine, I get this as output,
rs0:PRIMARY> rs.status()
{
"set" : "rs0",
"date" : ISODate("2020-01-24T06:15:26.540Z"),
"myState" : 1,
"term" : NumberLong(10),
"heartbeatIntervalMillis" : NumberLong(2000),
"optimes" : {
"lastCommittedOpTime" : {
"ts" : Timestamp(1579846526, 1),
"t" : NumberLong(10)
},
"readConcernMajorityOpTime" : {
"ts" : Timestamp(1579846526, 1),
"t" : NumberLong(10)
},
"appliedOpTime" : {
"ts" : Timestamp(1579846526, 1),
"t" : NumberLong(10)
},
"durableOpTime" : {
"ts" : Timestamp(1579846526, 1),
"t" : NumberLong(10)
}
},
"members" : [
{
"_id" : 0,
"name" : "localhost:27017",
"health" : 1,
"state" : 1,
"stateStr" : "PRIMARY",
"uptime" : 294,
"optime" : {
"ts" : Timestamp(1579846526, 1),
"t" : NumberLong(10)
},
"optimeDate" : ISODate("2020-01-24T06:15:26Z"),
"electionTime" : Timestamp(1579846244, 1),
"electionDate" : ISODate("2020-01-24T06:10:44Z"),
"configVersion" : 1,
"self" : true
},
{
"_id" : 1,
"name" : "localhost:27018",
"health" : 1,
"state" : 2,
"stateStr" : "SECONDARY",
"uptime" : 282,
"optime" : {
"ts" : Timestamp(1579846516, 1),
"t" : NumberLong(10)
},
"optimeDurable" : {
"ts" : Timestamp(1579846516, 1),
"t" : NumberLong(10)
},
"optimeDate" : ISODate("2020-01-24T06:15:16Z"),
"optimeDurableDate" : ISODate("2020-01-24T06:15:16Z"),
"lastHeartbeat" : ISODate("2020-01-24T06:15:24.871Z"),
"lastHeartbeatRecv" : ISODate("2020-01-24T06:15:25.718Z"),
"pingMs" : NumberLong(0),
"syncingTo" : "localhost:27017",
"configVersion" : 1
},
{
"_id" : 2,
"name" : "localhost:27019",
"health" : 1,
"state" : 2,
"stateStr" : "SECONDARY",
"uptime" : 273,
"optime" : {
"ts" : Timestamp(1579846516, 1),
"t" : NumberLong(10)
},
"optimeDurable" : {
"ts" : Timestamp(1579846516, 1),
"t" : NumberLong(10)
},
"optimeDate" : ISODate("2020-01-24T06:15:16Z"),
"optimeDurableDate" : ISODate("2020-01-24T06:15:16Z"),
"lastHeartbeat" : ISODate("2020-01-24T06:15:24.894Z"),
"lastHeartbeatRecv" : ISODate("2020-01-24T06:15:24.702Z"),
"pingMs" : NumberLong(0),
"syncingTo" : "localhost:27018",
"configVersion" : 1
}
],
"ok" : 1,
"operationTime" : Timestamp(1579846526, 1),
"$clusterTime" : {
"clusterTime" : Timestamp(1579846526, 1),
"signature" : {
"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
"keyId" : NumberLong(0)
}
}
}
Question:
Any guidance would be deeply appreciated.
Finally, I got a resolution for the issue,
While we initiate a replica set, we need to make sure that we do not have to mention the localhost
in the member's configuration (see below configuration). If done so then other remote servers won't be able to access the database even if you start Mongo server with the command --bind_ip 0.0.0.0,::
OR --bind_ip_all
.
Below are the correct and incorrect configurations.
INCORRECT
rs.initiate( {
_id : "rs0",
members: [
{ _id: 0, host: "localhost:27017" },
{ _id: 1, host: "localhost:27017" },
{ _id: 2, host: "localhost:27017" }
]
})
CORRECT [all replicas on the same machine]
rs.initiate( {
_id : "rs0",
members: [
{ _id: 0, host: "192.168.1.175:27017" },
{ _id: 1, host: "192.168.1.175:27018" },
{ _id: 2, host: "192.168.1.175:27019" }
]
})
CORRECT [all replicas on different machines]
rs.initiate( {
_id : "rs0",
members: [
{ _id: 0, host: "192.168.1.175:27017" },
{ _id: 1, host: "192.168.1.176:27018" },
{ _id: 2, host: "192.168.1.177:27019" }
]
})