MongoDB复制集是将数据同步在多个服务器的过程。以此来实现服务的高可用。
主要提供了两个主要功能:
- 数据写入主节点(Primary)时将数据复制到另一个副节(Secondary)点上
- 主节点发生故障时自动选举出一个新的替代节点
一个典型的复制集由三个或三个以上具有投票权的节点组成,其中一个主节点(Primary):接 收写入操作,读操作和选举时投票,两个或多个从节点(Secondary):复制主节点上的新数据和 选举时投票。
主要架构图如下:
复制流程:
当一个修改操作,无论是插入,更新或删除,到达主节点时,它对数据的操作将被记录下来,这些记录称为oplog,从节点通过从主节点上不断获取新进入主节点的oplog,并在自己的数据上回放,以此保持跟主节点的数据一致。
选举流程:
选举基于RAFT一致性算法实现,选举成功的必要条件是大多数投票节点存活。
被选举为主节点的节点必须
1.能够与多数节点建立连接
2.具有较新的oplog
3.具有较高的优先级(如果有配置)
搭建复制集
实验环境:一台CentOS 7 64bit主机进行一主两从架构
- 下载安装MongoDB
从官网获取下载链接(https://www.mongodb.com/try/download/community):
进入Linux主机进行下载
wget https://fastdl.mongodb.org/linux/mongodb-linux-x86_64-rhel70-4.4.4.tgz
进行解压
tar ‐xvzf mongodb-linux-x86_64-rhel70-4.4.4.tgz
将MongoDB的bin目录添加到PATH路径下,</usr/local/mongodb4>为安装目录
export PATH=/usr/local/mongodb4/bin:$PATH
- 搭建复制集
创建数据目录文件
sudo mkdir -p /data/db1
sudo mkdir -p /data/db2
sudo mkdir -p /data/db3
启动mongoDB
First member:
mongod --replSet rs0 --port 27017 --bind_ip 0.0.0.0 --dbpath /data/db1 --oplogSize 128
Second member:
mongod --replSet rs0 --port 27018 --bind_ip 0.0.0.0 --dbpath /data/db2 --oplogSize 128
Third member:
mongod --replSet rs0 --port 27019 --bind_ip 0.0.0.0> --dbpath /data/db3 --oplogSize 128
连接MongoDB
mongo --port 27017
在MongoDB shell中通过rs.initiate()启动副本集
rsconf = {
_id: "rs0",
members: [
{
_id: 0,
host: "localhost:27017"
},
{
_id: 1,
host: "localhost:27018"
},
{
_id: 2,
host: "localhost:27019"
}
]
}
rs.initiate( rsconf )
查看配置
rs.conf()
显示如下
{
"_id" : "rs0",
"version" : 1,
"term" : 1,
"protocolVersion" : NumberLong(1),
"writeConcernMajorityJournalDefault" : true,
"members" : [
{
"_id" : 0,
"host" : "localhost:28017",
"arbiterOnly" : false,
"buildIndexes" : true,
"hidden" : false,
"priority" : 1,
"tags" : {
},
"slaveDelay" : NumberLong(0),
"votes" : 1
},
{
"_id" : 1,
"host" : "localhost:28018",
"arbiterOnly" : false,
"buildIndexes" : true,
"hidden" : false,
"priority" : 1,
"tags" : {
},
"slaveDelay" : NumberLong(0),
"votes" : 1
},
{
"_id" : 2,
"host" : "localhost:28019",
"arbiterOnly" : false,
"buildIndexes" : true,
"hidden" : false,
"priority" : 1,
"tags" : {
},
"slaveDelay" : NumberLong(0),
"votes" : 1
}
],
"settings" : {
"chainingAllowed" : true,
"heartbeatIntervalMillis" : 2000,
"heartbeatTimeoutSecs" : 10,
"electionTimeoutMillis" : 10000,
"catchUpTimeoutMillis" : -1,
"catchUpTakeoverDelayMillis" : 30000,
"getLastErrorModes" : {
},
"getLastErrorDefaults" : {
"w" : 1,
"wtimeout" : 0
},
"replicaSetId" : ObjectId("6030a7c25871a56b5e12fd49")
}
}
查看副本集的状态
rs.status()
缺点:
- 复制集的数据量都存储在主节点上,因此如果数据量太大,在进行恢复数据的时候会比较麻烦。//或许可以多建几个副本集来存储不同的数据
- 只有主节点对外提供写操作,因此不能支持高并发。
MongoDB的复制集相当于Redis的哨兵模式,能进行备份,在主节点挂掉之后能自动选出主节点,进行故障转移。
MongoDB还有分片集群,类似于redis的集群模式。。。