mongodb在线增加分片节点
(2014-08-25 16:19:42)
标签:
mongodb |
分类: 数据库 |
本文章没有任何权威性,纯属自己测试发现的结果
如果shard里只有2台机器,需要一个仲裁节点。否则主挂了从不会提升成主,从表象上看需要超过半数的机器投票才能生效,下面做出解释:
primary 负责client的读写。
secondary作为热备节点,应用Primary的oplog读取的操作日志,和primary保持一致,不提供读写操作!
secondary有两种类型:
1)normal secondary
随时和Primay保持同步,
2)delayed secondary
延时指定时间和primary保持同步,防止误操作.
3)arbiter.它不负责任何读写,只作为一个仲裁者,负责primary down的时候剩余节点的选举操作. 在Replica Set 如果主库down了,要进行故障切换,集群的选举策略:
当primary当了之后,剩下的节点会选择一个primary节点,仲裁节点也会参与投票,避免僵局出现(如果没有仲裁节点,对于两节点的replica set 从节点down,主节点会变为secondary,导致整个replica set 不可用)选择依据为:优先级最高的且数据新鲜度最新的!
primary
节点使用心跳来跟踪集群中有多少节点对其可见。如果达不到1/2,活跃节点会自动降级为secondary。这样就能够防止上面说的僵局状态或者当网络切割后primary已经与集群隔离的时候!
下面是测试过程
三台机器做mongos,config和仲裁节点 30000/27000/30001
192.168.10.202
192.168.10.203
192.168.10.204
两台机器做shard1 27020
192.168.10.202
192.168.10.203
两台台机器做shard2 27021
192.168.10.203
192.168.10.204
两台台机器做shard3 27022
192.168.10.202
192.168.10.204
1,在202/203/204机器上分别启动相关进程,仲裁节点不能是自己,并且仲裁节点需要和数据节点是一个shard
192.168.10.202
mkdir -p /data/27020 /data/27022 /data/arbiter
/usr/local/mongodb/bin/mongod --replSet shard1 --shardsvr --dbpath /data/27020 --port 27020 &
/usr/local/mongodb/bin/mongod --replSet shard3 --shardsvr --dbpath /data/27022 --port 27022 &
/usr/local/mongodb/bin/mongod --replSet shard2 --shardsvr --dbpath /data/arbiter --port 30001 &
192.168.10.203
mkdir -p /data/27020 /data/27021 /data/arbiter
/usr/local/mongodb/bin/mongod --replSet shard2 --shardsvr --dbpath /data/27021 --port 27021 &
/usr/local/mongodb/bin/mongod --replSet shard1 --shardsvr --dbpath /data/27020 --port 27020 &
/usr/local/mongodb/bin/mongod --replSet shard3 --shardsvr --dbpath /data/arbiter --port 30001 &
192.168.10.204
mkdir -p /data/27021 /data/27022 /data/arbiter
/usr/local/mongodb/bin/mongod --replSet shard1 --shardsvr --dbpath /data/arbiter --port 30001 &
/usr/local/mongodb/bin/mongod --replSet shard3 --shardsvr --dbpath /data/27022 --port 27022 &
/usr/local/mongodb/bin/mongod --replSet shard2 --shardsvr --dbpath /data/27021 --port 27021 &
2.在shard1 192.168.10.202上
初始化replica set
用mongo连接shard1的mongod,
/usr/local/mongodb/bin/mongo --port 27020
执行: #id要和启动时--replSet shard1的shard1匹配
config = {_id: 'shard1', members: [{_id:0, host: '192.168.10.202:27020'},{_id:1, host: '192.168.10.203:27020'},{_id:2, host: '192.168.10.204:30001', arbiterOnly:true}]}
rs.initiate(config);
在shard2 192.168.10.203上
用mongo连接shard2的mongod,
/usr/local/mongodb/bin/mongo --port 27021
执行:
config = {_id: 'shard2', members: [{_id: 0, host: '192.168.10.203:27021'},{_id:1, host: '192.168.10.204:27021'},{_id: 2, host: '192.168.10.202:30001', arbiterOnly:true}]}
rs.initiate(config);
在shard3 192.168.10.204上
/usr/local/mongodb/bin/mongo --port 27022
执行:
config = {_id: 'shard3', members: [{_id: 0, host: '192.168.10.202:27022'},{_id:1, host: '192.168.10.204:27022'},{_id: 2, host: '192.168.10.203:30001', arbiterOnly:true}]}
rs.initiate(config);
3.配置3台config server
在192.168.10.202/203/204上:
mkdir -p /data/27000
/usr/local/mongodb/bin/mongod --configsvr --dbpath /data/27000 --port 27000 &
4.配置mongs
在192.168.10.202/203/204上分别执行:
/usr/local/mongodb/bin/mongos --configdb
192.168.10.202:27000,192.168.10.203:27000,192.168.10.204:27000
--port 30000 --logpath /data/mongos.log --logappend --fork
#mongs不需要dbpath
5.Configuring the Shard Cluster
连接到其中一个mongos进程,并切换到admin数据库做以下配置
a. 连接到mongs,并切换到admin
>use admin
>db
Admin
b. 加入shards
如果shard是replica sets,用replicaSetName/[:port] [,serverhostname2[:port],…]这样的格式表示,例如本例执行:
db.runCommand( { addshard : "shard1/192.168.10.202:27020,192.168.10.203:27020,192.168.10.204:30001"} );
db.runCommand( { addshard : "shard2/192.168.10.203:27021,192.168.10.204:27021,192.168.10.202:30001"} );
db.runCommand( { addshard : "shard3/192.168.10.202:27022,192.168.10.204:27022,192.168.10.203:30001"} );
c. Listing shards
>db.runCommand( { listshards : 1 } )
如果列出了以上二个你加的shards,表示shards已经配置成功
6.对库进行分片,必须为分片enable一个数据库
db.runCommand({enablesharding:"uam"})
db.printShardingStatus();
7.对需要分片的collections进行分片,用shardcollection 命令分隔数据集,key自动生成
db.runCommand({shardcollection : "uam.MONITOR_INFO","key":{"_id":"hashed"}})
先插入20W条数据:
mongos> for(i=1;i<200000;i++){
db.MONITOR_INFO.insert({uid:i,username:"Falcon +i",sex:"m",age:25 +i});
}
以下省略不重要部分
mongos> db.MONITOR_INFO.stats()
{
"sharded" : true,
"ns" : "uam.MONITOR_INFO",
"count" : 199999,
"shards" : {
"shard1" : {
"ns" : "uam.MONITOR_INFO",
"count" : 66571,
"ok" : 1
},
"shard2" : {
"ns" : "uam.MONITOR_INFO",
"count" : 66422,
"ok" : 1
},
如果shard里只有2台机器,需要一个仲裁节点。否则主挂了从不会提升成主,从表象上看需要超过半数的机器投票才能生效,下面做出解释:
primary
secondary作为热备节点,应用Primary的oplog读取的操作日志,和primary保持一致,不提供读写操作!
secondary有两种类型:
1)normal secondary
2)delayed secondary
3)arbiter.它不负责任何读写,只作为一个仲裁者,负责primary down的时候剩余节点的选举操作. 在Replica Set 如果主库down了,要进行故障切换,集群的选举策略:
当primary当了之后,剩下的节点会选择一个primary节点,仲裁节点也会参与投票,避免僵局出现(如果没有仲裁节点,对于两节点的replica set 从节点down,主节点会变为secondary,导致整个replica set 不可用)选择依据为:优先级最高的且数据新鲜度最新的!
下面是测试过程
三台机器做mongos,config和仲裁节点
192.168.10.202
192.168.10.203
192.168.10.204
两台机器做shard1 27020
192.168.10.202
192.168.10.203
两台台机器做shard2 27021
192.168.10.203
192.168.10.204
两台台机器做shard3
192.168.10.202
192.168.10.204
1,在202/203/204机器上分别启动相关进程,仲裁节点不能是自己,并且仲裁节点需要和数据节点是一个shard
192.168.10.202
mkdir -p /data/27020 /data/27022 /data/arbiter
/usr/local/mongodb/bin/mongod --replSet shard1 --shardsvr --dbpath /data/27020 --port 27020 &
/usr/local/mongodb/bin/mongod --replSet shard3 --shardsvr --dbpath /data/27022 --port 27022 &
/usr/local/mongodb/bin/mongod --replSet shard2 --shardsvr --dbpath /data/arbiter --port 30001 &
192.168.10.203
mkdir -p /data/27020 /data/27021 /data/arbiter
/usr/local/mongodb/bin/mongod --replSet shard2 --shardsvr --dbpath /data/27021 --port 27021 &
/usr/local/mongodb/bin/mongod --replSet shard1 --shardsvr --dbpath /data/27020 --port 27020 &
/usr/local/mongodb/bin/mongod --replSet shard3 --shardsvr --dbpath /data/arbiter --port 30001 &
192.168.10.204
mkdir -p /data/27021 /data/27022 /data/arbiter
/usr/local/mongodb/bin/mongod --replSet shard1 --shardsvr --dbpath /data/arbiter --port 30001 &
/usr/local/mongodb/bin/mongod --replSet shard3 --shardsvr --dbpath /data/27022 --port 27022 &
/usr/local/mongodb/bin/mongod --replSet shard2 --shardsvr --dbpath /data/27021 --port 27021 &
2.在shard1 192.168.10.202上
初始化replica set
用mongo连接shard1的mongod,
/usr/local/mongodb/bin/mongo --port 27020
执行: #id要和启动时--replSet shard1的shard1匹配
config = {_id: 'shard1', members: [{_id:0, host: '192.168.10.202:27020'},{_id:1, host: '192.168.10.203:27020'},{_id:2, host: '192.168.10.204:30001', arbiterOnly:true}]}
rs.initiate(config);
在shard2 192.168.10.203上
用mongo连接shard2的mongod,
/usr/local/mongodb/bin/mongo --port 27021
执行:
config = {_id: 'shard2', members: [{_id: 0, host: '192.168.10.203:27021'},{_id:1, host: '192.168.10.204:27021'},{_id: 2, host: '192.168.10.202:30001', arbiterOnly:true}]}
rs.initiate(config);
在shard3 192.168.10.204上
/usr/local/mongodb/bin/mongo --port 27022
执行:
config = {_id: 'shard3', members: [{_id: 0, host: '192.168.10.202:27022'},{_id:1, host: '192.168.10.204:27022'},{_id: 2, host: '192.168.10.203:30001', arbiterOnly:true}]}
rs.initiate(config);
3.配置3台config server
在192.168.10.202/203/204上:
mkdir -p /data/27000
/usr/local/mongodb/bin/mongod --configsvr --dbpath /data/27000 --port 27000 &
4.配置mongs
在192.168.10.202/203/204上分别执行:
/usr/local/mongodb/bin/mongos --configdb
#mongs不需要dbpath
5.Configuring the Shard Cluster
连接到其中一个mongos进程,并切换到admin数据库做以下配置
a. 连接到mongs,并切换到admin
>use admin
>db
Admin
b. 加入shards
如果shard是replica sets,用replicaSetName/[:port] [,serverhostname2[:port],…]这样的格式表示,例如本例执行:
db.runCommand( { addshard : "shard1/192.168.10.202:27020,192.168.10.203:27020,192.168.10.204:30001"} );
db.runCommand( { addshard : "shard2/192.168.10.203:27021,192.168.10.204:27021,192.168.10.202:30001"} );
db.runCommand( { addshard : "shard3/192.168.10.202:27022,192.168.10.204:27022,192.168.10.203:30001"} );
c. Listing shards
>db.runCommand( { listshards : 1 } )
如果列出了以上二个你加的shards,表示shards已经配置成功
6.对库进行分片,必须为分片enable一个数据库
db.runCommand({enablesharding:"uam"})
db.printShardingStatus();
7.对需要分片的collections进行分片,用shardcollection 命令分隔数据集,key自动生成
db.runCommand({shardcollection : "uam.MONITOR_INFO","key":{"_id":"hashed"}})
先插入20W条数据:
mongos> for(i=1;i<200000;i++){
db.MONITOR_INFO.insert({uid:i,username:"Falcon +i",sex:"m",age:25 +i});
}
以下省略不重要部分
mongos> db.MONITOR_INFO.stats()
{