MongoDB简介
MongoDB由C++开发,是NoSQL中比较接近关系型数据库的一种。MongoDB中的数据以类似于json的格式存储,性能非常优越,且支持大量的数据存储。但是MongoDB不支持事务性的操作,使得其适用场景受到限制。
MongoDB副本集
MongoDB的数据复制有两种类型:
? ? 1)master/slave
? ? 2)replica set
第一种为类似于MySQL的主从复制模型,第二种为副本集复制方式。现在主要应用的为副本集复制模型。结构图如下:

一个副本集即为服务于同一数据集的多个MongoDB实例,其中一个为主节点,其余的都为从节点。主节点上能够完成读写操作,从节点仅能用于读操作。主节点需要记录所有改变数据库状态的操作,这些记录保存在oplog中,这个文件存储在local数据库,各个从节点通过此oplog来复制数据并应用于本地,保持本地的数据与主节点的一致。oplog具有幂等性,即无论执行几次其结果一致,这个比mysql的二进制日志更好用。
集群中的各节点还会通过传递心跳信息来检测各自的健康状况。当主节点故障时,多个从节点会触发一次新的选举操作,并选举其中的一个成为新的主节点(通常谁的优先级更高,谁就是新的主节点),心跳信息默认每2秒传递一次。

实现过程
副本集的实现至少需要三个节点,且应该为奇数个节点,可以使用arbiter(仲裁节点)来参与选举。
实验环境:
主节点:192.168.1.132
从节点:192.168.1.139,192.168.1.140
1)安装配置MongoDB
1 [root@mongo1 mongodb-2.6.5]# yum install -y mongodb-org-server-2.6.5-1.x86_64.rpm mongodb-org-tools-2.6.5-1.x86_64.rpm mongodb-org-shell-2.6.5-1.x86_64.rpm
配置文件信息:
[root@mongo1 ~]# vim /etc/mongod.conf
logpath=/var/log/mongodb/mongod.log
logappend=true
fork=true
dbpath=/mongodb/data
pidfilepath=/var/run/mongodb/mongod.pid
bind_ip=0.0.0.0
httpinterface=true
rest=true
replSet=rs0
replIndexPrefetch = _id_only
replSet指定副本集的名称,这个至关重要,这个决定了对应的每一个节点加入的是哪一个副本集的集群。
replIndexPrefetch指定副本集的索引预取,如果有预取功能可以让复制过程更为高效,有3个值none,_id_only,all。none:不预取任何索引,_id_only:预取ID索引,all:预取所有索引。这个预取操作只能定义在从节点上。
在各节点上创建数据存放目录,然后启动服务:
[root@mongo1 ~]# mkdir -pv /mongodb/data
mkdir: created directory `/mongodb'
mkdir: created directory `/mongodb/data'
[root@mongo1 ~]# chown -R mongod.mongod /mongodb
?
[root@mongo1 ~]# service mongod start
Starting mongod:? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? [? OK? ]
2)配置集群的成员
查看集群信息(此时没有任何节点)
[root@mongo1 ~]# mongo --host 192.168.1.132
MongoDB shell version: 2.6.5
connecting to: 192.168.1.132:27017/test
> rs.status()
{
? ? "startupStatus" : 3,
? ? "info" : "run rs.initiate(...) if not yet done for the set",
? ? "ok" : 0,
? ? "errmsg" : "can't get local.system.replset config from self or any seed (EMPTYCONFIG)"
}
添加集群成员,首先配置cfg定义集群信息,然后执行rs.initiate(cfg)完成节点的添加。在定义集群时,需要指定每一个节点的属性信息,例如_id,host。还有很多属性字段,常见的有priority,votes,arbiterOnly.....? 具体的信息可以参考官方网站http://docs.mongodb.org/manual/reference/command/replSetGetConfig/#replsetgetconfig-output。
> cfg={_id:'rs0',members:[?
... ... {_id:0,host:'192.168.1.132:27017'},?
... ... {_id:1,host:'192.168.1.139:27017'},
... ... {_id:2,host:'192.168.1.140:27017'}]?
... ... }
{
? ? "_id" : "rs0",
? ? "members" : [
? ? ? ? {
? ? ? ? ? ? "_id" : 0,
? ? ? ? ? ? "host" : "192.168.1.132:27017"
? ? ? ? },
? ? ? ? {
? ? ? ? ? ? "_id" : 1,
? ? ? ? ? ? "host" : "192.168.1.139:27017"
? ? ? ? },
? ? ? ? {
? ? ? ? ? ? "_id" : 2,
? ? ? ? ? ? "host" : "192.168.1.140:27017"
? ? ? ? }
? ? ]
}
#################################
> rs.initiate(cfg)
{
? ? "info" : "Config now saved locally.? Should come online in about a minute.",
? ? "ok" : 1
}
查看各节点的状态信息:
> rs.status()
{
? ? "set" : "rs0",
? ? "date" : ISODate("2015-09-04T23:02:13Z"),
? ? "myState" : 1,
? ? "members" : [? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? #显示副本集的所有成员信息
? ? ? ? {
? ? ? ? ? ? "_id" : 0,? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? #节点的标识符
? ? ? ? ? ? "name" : "192.168.1.132:27017",? ? ? ? ? ? ? ? ? ? #节点名称? ?
? ? ? ? ? ? "health" : 1,? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? #节点的健康状态? ? ? ? ? ?
? ? ? ? ? ? "state" : 1,? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?
? ? ? ? ? ? "stateStr" : "PRIMARY",? ? ? ? ? ? ? ? ? ? ? ? ? ? #该节点为主节点? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?
? ? ? ? ? ? "uptime" : 1750,? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? #运行时长? ? ? ? ? ? ? ? ?
? ? ? ? ? ? "optime" : Timestamp(1441407002, 1),? ? ? ? ? ? ? ? #oplo