MongoDB sharding: host does not belong to replica set - mongodb

I am a Mongo newbie.
I am trying to sping up a MongoDB cluster with both sharding and replication. Cluster schema which I want to implement is: https://github.com/ansible/ansible-examples/raw/master/mongodb/images/site.png
I am using server IP as replication set name. I.e. I am building replication sets with commands below:
rs.initiate()
rs.add("10.148.28.51:27118")
rs.add("10.148.28.52:27118")
rs.add("10.148.28.53:27118")
Replication is being configured correctly so when I am executing rs.status() on PRIMARY host 10.148.28.51 I am getting "10.148.28.51" as repl.set name: https://gist.github.com/daniilyar/630bc6fe7723ed06f243
But when I am trying to add shards at mongos instance it gives me 2 opposite errors (depending on what addShard() syntax variation I use):
mongos> sh.addShard("10.148.28.51:27118")
{
"ok" : 0,
"errmsg" : "host is part of set 10.148.28.51, use replica set url format <setname>/<server1>,<server2>,...."
}
mongos> sh.addShard("10.148.28.51/10.148.28.51:27118")
{
"ok" : 0,
"errmsg" : "in seed list 10.148.28.51/10.148.28.51:27118, host 10.148.28.51:27118 does not belong to replica set 10.148.28.51"
}
How do I add shard if Mongo tells that "host X is in replica set Y" and that "host X does not belong to replica set Y" in the same time?
Any help would be greatly appreciated

From your description sounds like you need to tweak the way your are using the rs.add(..) command. You state you are using the IP address as the name of the replica set but this is not how rs.add(...) interprets the argument.
The argument you pass is the hostname (or IP) and port of the mongod instance you are looking to add to the replica set notthe replica set name. You set-up this configuration when connected via mongo to the primary. The replSet name is set when the primary is started:
mongod --replSet "rs1"
sets the as name of rs1.
I'd have a read over: http://docs.mongodb.org/manual/tutorial/convert-replica-set-to-replicated-shard-cluster/ as it covers pretty much what you appear to be trying to do.
I'd also consider what you are trying to achieve as it sounds (from your description) like you may end up with a single replicated shard (!!!) when you most probably are looking to create multiple shards each of which have their data replicated.
References:
rs.add command - http://docs.mongodb.org/manual/reference/method/rs.add/
rs.addShard command - http://docs.mongodb.org/manual/reference/method/sh.addShard/
Sharded Cluster -
http://docs.mongodb.org/manual/core/sharded-cluster-components/

Thank you for good explanation, now I understand. If you use in rs.add(IP:port), Mongo adds replica set member with name ip-X-Y-Z-R:. It seems to be Mongo's default behavior. So in my case solution was to use command:
sh.addShard("10.148.28.51/**ip-10-148-28-51**:27118")
instead of:
sh.addShard("10.148.28.51/**10.148.28.51**:27118")

Related

MongoDB : How to perform sharding without replication?

I am trying to accomplish sharding within 2 machines with config server, router, 1 shard in machine A and another shard in machine B. I am finding it hard to do this as I am a beginner and also can't find much documentation/ tutorials online. I have started a two mongod instances one as config server and another as shard, but clueless on how to proceed.
Below is the sharding configuration in two of my mongod (config and shard ) conf files:
Config server:
sharding:
clusterRole: configsvr
Shard:
sharding:
clusterRole : shardsvr
As per the documentation , the next step is to execute the command rs.initiate(), but I don't require replication. I still tried to execute just in case and received below error:
{
"ok" : 0,
"errmsg" : "This node was not started with the replSet option",
"code" : 76,
"codeName" : "NoReplicationEnabled"
}
Is it mandatory to have replication while sharding? How to do sharding without replication within 2 machines?
That's not possible, see sharding Options:
Note
Setting sharding.clusterRole requires the mongod instance to be
running with replication. To deploy the instance as a replica set
member, use the replSetName setting and specify the name of the
replica set.
But you can have a replica set with just one member, that's no problem.
The replica set will have only the primary, should work.

Error in configuration of Mongodb sharded cluster

I have Error in configuration of Mongodb sharded cluster.
I tried all the possibilities of rs.add("127.0.0.1:27002"), rs.add("loclahost:27002") and rs.add("hostname:27002") for sharding
But I am getting error:
{
"ok" : 0,
"errmsg" : "Either all host names in a replica set configuration must be localhost references, or none must be; found 1 out of 2",
"code" : 103
}
I assume that you try to connect to your primary and trying to add the secondary nodes. To start a Mongo instance by typing
mongo localhost:30001
I suppose this is primary, in the mongod shell for this primary. Type in this command
rs.status()
You'll get to know the name of your primary. Same will be the name of your secondary with just the difference of the port number.
Once you get the name, just do rs.add("name:port_number") and you'll be able to add.
rs.add() is used to make ReplicaSet not Sharded cluster.
If you what to add a shard to a sharded cluster, you may use sh.addShard("host:port").

MongoDB how to become master

I am creating a MongoDB database through a linux terminal and I am trying to create a collection for the database.
But when I run the command: db.createCollection("mainCollection") I get the following error message: { "note" : "from execCommand", "ok" : 0, "errmsg" : "not master" }
I'm not exactly sure what this means. How can I make the database master?
Thanks
You have started the mongod with the --replSet option (or equivalent configuratin file option). That puts the mongod into a mode where it will not allow any writes until it receives a replica set configuration.
For an existing replica set this is accomplished by doing a rs.add("<host>:<port>") on the existing primary for the replica set.
Based on the conversation around this question I think you have a single MongoDB instance and do not plan to have a true multi-member replica set. If that is the case you have two options:
Stop trying to run a replica set
Stop the mongod.
Wipe the data directory for the mongod process.
Restart the mongod process without the --replSet option on the command line/config.
Initialize the mongod as a single node replica set.
Run rs.initiate() from the shell (no config is required). You will get disconnected but the shell will automatically reconnect and then you can create collections and do other writes.
Thats expected behaviour "Viratan" if you are querying on the replica set and the shell you are connected with is not the Primary.
You can do either of these two things.
Disconnect from the current shell and connect with the Primary. In mongo shell you would see it written "PRIMARY" or "SECONDARY".
In case you want the same member as the primary then you can increase the priority of that particular member and/or force the formar primary to stepDown. once the primary is step down, the election would occur and because the desired member has higher priority that would become primary.
you can follow the below link to change the priority of a member http://docs.mongodb.org/manual/tutorial/force-member-to-be-primary
Once you are connected with Primary in either ways, you can query the DB and do your stuff.
Happy Mongoing.. :-)
-$
you are trying to create a new collection on secondary.thats why it is giving as error please use primary to create new

Connecting to Mongo in Replica set mode

I have a standalone Mongo instance running a replica set. I can't seem to connect and run any queries in the Mongo shell however. I get the following:
error: { "$err" : "not master and slaveOk=false", "code" : 13435 }
I set SlaveOk like so:
db.getMongo().setSlaveOk()
..but I still get an error:
error: {
"$err" : "not master or secondary; cannot currently read from this replSet member",
"code" : 13436
}
I can't seem to find a straight answer on Google: how do I connect to my replica set using the mongo shell?
I got the same problem and solved it using
rs.initiate()
If you are connecting to a node in a replica set that is not the master, you need to explicitly tell the client that it is ok that your are not connected to a master..
You can do this by calling
rs.slaveOk()
You can then perform your query.
Note that you will only be able to perform queries, not make changes to the repository, when connected to a slave node.
You are connected to a node that is neither in state secondary or primary. This node could be an arbiter or possibly a secondary in recovery mode. For example, if I had a replica set of 3 nodes, (where there is one primary, a secondary and an arbiter) I would get the same error if I had connected to the arbiter and issued a query even after I had set slaveOK true. The shell's command line prompt should indicate what state the node you are connected is in:
foo:ARBITER> db.test.find()
error: {
"$err" : "not master or secondary; cannot currently read from this replSet member",
"code" : 13436
}
have you tried: db.getMongo().setSlaveOk(true)
I also got the error. But when i tried connecting to the secondary node using the machine name instead of 'localhost' or 127.0.0.1 the error went away.
This error is only displayed when you are running an instance that's part of a replica set in standalone mode without completely removing it from the replica set.
e.g. You restart your instance on a different port but don't remove the --repSet option when starting it.
This starts it but neither as a primary nor as a secondary, hence the error
not master or secondary;
Depending on what you intended to do initially, either restart the instance on the correct port and with the correct --repSet option. This adds it to the replica set and gets rid of this error
If you intended to run the instance as standalone for some time (say to create an index), then start it on a different port WITHOUT the --repSet option
I got the same error while running aggregate() on staging server with two replica sets.I think you need to change the read preference to 'secondaryPreferred'.
Just put .read('secondaryPreferred') after the query function.

Setup Shards: Should I install MongoDB on the following servers

Following the Oreily Scaling MongoDB book (i.e. Page 27), I saw the following command:
Once you’re connected, you can add a shard. There are two ways to add
a shard, depending on whether the shard is a single server or a
replica set. Let’s say we have a single server, sf-02, that we’ve been
using for data. We can make it the first shard by running the addShard
command:
> db.runCommand({"addShard" : "sf-02:27017"})
{ "shardAdded" : "shard0000", "ok" : 1 }
Question 1>: What should be done on the servers of sf-02?
Should I also install MongoDB on it? If any, which package?
For example, if we had a replica set creatively named replica set “rs”
with members rs1-a, rs1-b, and rs1-c, we could say:
> db.runCommand({"addShard" : "rs/rs1-a,rs1-c"})
{ "shardAdded" : "rs", "ok" : 1 }
Question 2>: where is "rs" located?
Question 3>: Does rs1-a, rs1-c share the same machine?
reply 1: you should run mongod with the --shardsvr option to start it as a shard server. each shard server has to know that it is will receive a connection from a mongos (the shard router).
reply 2: 'rs' is the name of a replica set, a set is just a group of machine (usually 3). so it is not located on a single machine, it is an abstract entity which represent the group of machine in the set.
reply 3: no. for testing purpose you can run replica set on the same machine, but the purpose of a replica set is failover. in production you should use different machine for every member of the set.