Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

MongoDB replica set preventing queries to secondary

To set up the replica set, I've run in 3 separate terminal tabs:

 $ sudo mongod --replSet rs0 --dbpath /data/mining --port 27017  $ sudo mongod --replSet rs0 --dbpath /data/mining2 --port 27018  $ sudo mongod --replSet rs0 --dbpath /data/mining3 --port 27019 

Then, I configured replication in the Mongo shell and verified that it worked:

 > var rsconf = {      _id: "rs0",      members: [        {          _id: 0,          host: 'localhost:27017'        },        {          _id: 1,          host: 'localhost:27018'        },        {          _id: 2,          host: 'localhost:27019'        }      ]    };  > rs.initiate(rsconf); {   "info": "Config now saved locally.  Should come online in about a minute.",   "ok": 1 } // Some time later...  > rs.status() {   "set": "rs0",   "date": ISODate("2013-06-17T13:23:45-0400"),   "myState": 2,   "syncingTo": "localhost:27017",   "members": [     {       "_id": 0,       "name": "localhost:27017",       "health": 1,       "state": 1,       "stateStr": "PRIMARY",       "uptime": 4582,       "optime": {         "t": 1371489546,         "i": 1       },       "optimeDate": ISODate("2013-06-17T13:19:06-0400"),       "lastHeartbeat": ISODate("2013-06-17T13:23:44-0400"),       "lastHeartbeatRecv": ISODate("2013-06-17T13:23:44-0400"),       "pingMs": 0     },     {       "_id": 1,       "name": "localhost:27018",       "health": 1,       "state": 2,       "stateStr": "SECONDARY",       "uptime": 5034,       "optime": {         "t": 1371489546,         "i": 1       },       "optimeDate": ISODate("2013-06-17T13:19:06-0400"),       "self": true     },     {       "_id": 2,       "name": "localhost:27019",       "health": 1,       "state": 2,       "stateStr": "SECONDARY",       "uptime": 4582,       "optime": {         "t": 1371489546,         "i": 1       },       "optimeDate": ISODate("2013-06-17T13:19:06-0400"),       "lastHeartbeat": ISODate("2013-06-17T13:23:44-0400"),       "lastHeartbeatRecv": ISODate("2013-06-17T13:23:45-0400"),       "pingMs": 0,       "syncingTo": "localhost:27017"     }   ],   "ok": 1 } 

My script runs fine against the primary:

 $ ./runScripts.sh -h localhost -p 27017 MongoDB shell version: 2.4.3 connecting to: localhost:27017/test Successful completion 

However, against either secondary:

 $ ./runScripts.sh -h localhost -p 27018 MongoDB shell version: 2.4.3 connecting to: localhost:27017/test Mon Jun 17 13:30:22.989 JavaScript execution failed: count failed:  { "note" : "from execCommand", "ok" : 0, "errmsg" : "not master" }  at src/mongo/shell/query.js:L180 failed to load: /.../.../myAggregateScript.js 

I've read in multiple places to use rs.slaveOk() or db.getMongo().setSlaveOk(), but neither of these had any effect, whether entered from the shell or called in my script. These statements did not throw errors when called, but they didn't fix the problem, either.

Does anyone know why I can't configure my replset to allow querying of the secondary?

like image 394
Ryan Kennedy Avatar asked Jun 17 '13 18:06

Ryan Kennedy


People also ask

What is the purpose of using replica set in MongoDB?

A replica set in MongoDB is a group of mongod processes that maintain the same data set. Replica sets provide redundancy and high availability, and are the basis for all production deployments. This section introduces replication in MongoDB as well as the components and architecture of replica sets.

What is difference between replica set and sharding in MongoDB?

What is the difference between replication and sharding? Replication: The primary server node copies data onto secondary server nodes. This can help increase data availability and act as a backup, in case if the primary server fails. Sharding: Handles horizontal scaling across servers using a shard key.

How often do the members of a replica set send heartbeats to each other in MongoDB?

Heartbeats. Replica set members send heartbeats (pings) to each other every two seconds. If a heartbeat does not return within 10 seconds, the other members mark the delinquent member as inaccessible.


2 Answers

rs.slaveOk() run in the mongo shell will allow you to read from secondaries. Here is a demonstration using the mongo shell under MongoDB 2.4.3:

$ mongo --port 27017 MongoDB shell version: 2.4.3 connecting to: 127.0.0.1:27017/test replset:PRIMARY> db.foo.save({}) replset:PRIMARY> db.foo.find() { "_id" : ObjectId("51bf5dbd473d5e80fc095b17") } replset:PRIMARY> exit  $ mongo --port 27018 MongoDB shell version: 2.4.3 connecting to: 127.0.0.1:27018/test replset:SECONDARY> db.foo.find() error: { "$err" : "not master and slaveOk=false", "code" : 13435 } replset:SECONDARY> rs.slaveOk() replset:SECONDARY> db.foo.find() { "_id" : ObjectId("51bf5dbd473d5e80fc095b17") } replset:SECONDARY> db.foo.count() 1 
like image 164
James Wahlin Avatar answered Sep 25 '22 17:09

James Wahlin


You have to run the command rs.slaveOk() in the secondary server's shell.

like image 36
Dung Nguyen Avatar answered Sep 25 '22 17:09

Dung Nguyen