mongo--修改主节点oplog步骤
4.1 rs.status()命令解释
4.2 db.getReplicationInfo()命令解释
3.1关闭主节点mongo服务
3.2.将主节点改为单机模式运行
3.3.启动主节点mongo服务
3.4.恢复主节点的配置信息
3.5.重新启动主节点mongo服务,并观察集群状态
2.1关闭仲裁节点mongo服务
2.2 关闭主节点mongo服务
2.3.将主节点改为单机模式运行
2.4.启动主节点mongo服务修改oplog
2.5.恢复主节点的配置信息
2.6.重新启动主节点和仲裁节点mongo服务,并观察集群状态
1.1 背景
1.2 mongo复制原理
一、前言
二、集群只有主节点和仲裁节点---修改主节点oplog步骤
三、集群中有主节点、从节点和仲裁节点---修改主节点oplog步骤
四、附录
mongo--修改主节点oplog步骤
一、前言
1.1 背景
现有一个 mongo3.4 版本副本集群,架构如图:
1.2 mongo复制原理
Mongo的复制集原理是:开启复制功能后,主节点的local库下生成一个集合叫oplog.rs,这是一个有限集合,也就是大小是固定的。其中记录的是整个mongod实例一段时间内数据库的所有变更(插入/更新/删除)操作,当空间用完时新记录自动覆盖最老的记录。
复制集中的从节点是通过读取主节点oplog的来实现数据同步的,MongoDB的oplog(操作日志)是一种特殊的封顶集合,滚动覆盖写入,固定大小。另外oplog的滚动覆盖写入方式有两种:一种是达到设定大小就开始覆盖写入;二是设定文档数,达到文档数就开始覆盖写入(官方不推荐使用)。
如果oplog被覆盖而从库没有同步到对应信息,则从库无法继续和主库同步,需要重新初始化。
目前我们的主节点oplog只有50M,高峰期从节点的同步窗口大约只有10秒钟,10秒钟后主节点的oplog将会覆盖,所以需要升级主节点的oplog。
以下是local库下oplog.rs集合数据例子:
test_mongo_repl:PRIMARY>use local
test_mongo_repl:PRIMARY> db.oplog.rs.findOne()
{
"_id" : ObjectId("5d6f1fb902a37af10280a2e9"),
"ts" : Timestamp(1567563019, 3),
"t" : NumberLong(1),
"h" : NumberLong("6957671099086508662"),
"v" : 2,
"op" : "i",
"ns" : "test.data_error_msg",
"o" : {
"_id" : ObjectId("5d6f1d0bbdf9d3a6d0dc3e2f"),
"ERROR_CODE" : "XSXCD08",
"ERROR_MSG" : "D-04.高负债且近1年贷款或信用卡查询机构数>5次且近1年信用卡和贷款均未发放",
"CREATE_DATE" : ISODate("2018-12-13T08:37:42.633Z"),
"UPDATE_DATE" : ISODate("2018-12-13T08:37:42.633Z"),
"TENANT_ID" : "000"
}
}
test_mongo_repl:PRIMARY>
ts:操作发生时的时间戳,这个时间戳包含两部分内容t和i,t是标准的时间戳(自1970年1月1日 00:00:00 GMT 以来的毫秒数)。而i是一个序号,目的是为了保证t与i组合出的Mongo时间戳ts可以唯一的确定一条操作记录。
h:此操作的独一无二的ID。
v:oplog的版本。
op:操作类型(insert、update、delete、db cmd、null),仅仅代表一个消息信息。
"i":insert
"u":update
"d":delete
"c":db cmd
"db":声明当前数据库 (其中ns 被设置成为=>数据库名称+ '.')
"n": no op,即空操作,其会定期执行以确保时效性
ns:操作所处的命名空间(db_name.coll_name)。
o:操作对应的文档,文档在更新前的状态(“msg” 表示信息)。
o2:仅update操作时有,更新操作的变更条件(只记录更改数据)。
二、集群只有主节点和仲裁节点---修改主节点oplog步骤
注意:在此种状况下,一定要保证修改oplog时mongo没有数据写入,即需要停服操作,否则修改oplog会失败。
2.1关闭仲裁节点mongo服务
登陆仲裁节点服务器的,进入mongo,执行:
use admin
#不需要密码登陆,直接执行:
db.shutdownServer()
如图:
#查看mongo进程是否还在
ps -ef|grep mongo
2.2 关闭主节点mongo服务
登录主节点服务器,登陆mongo,密码验证,关闭主节点mongo服务
use admin
db.auth('root角色用户','密码'));
db.shutdownServer()
如图:
#查看mongo进程是否还在
ps -ef|grep mongo
2.3.将主节点改为单机模式运行
将主节点以单机模式运行,需修改配置文件的下端口号和复制集名称即可
vim opt/soft/mongodb/mongodb.yml
添加:
net:
port: 37017 #端口需要临时改成别的
将复制信息注释
#replication:
# oplogSizeMB: 409600
# replSetName: "prod_core_mongo_repl"
# secondaryIndexPrefetch: "all"
如图:
##启动mongo服务
sudo systemctl start mongo
2.4.启动主节点mongo服务修改oplog
登陆主节点的mongo服务(用户需要对local库有读写权限)
登陆命令:
mongo 127.0.0.1:37017
use admin
db.auth('root角色用户','密码'));
#如果该用户没有local库的读写,则新增该角色:
db.grantRolesToUser( "用户", [{'role':'readWrite','db':'local'}])
命令如下:
mongo>use local
mongo>var cursor=db.oplog.rs.find()
mongo>var cursor = db.oplog.rs.find({"op":"i"})
mongo>var lastInsert = cursor.sort({"$natural":-1}).limit(1).next()
mongo>db.tempLastOp.save(lastInsert)
mongo>db.tempLastOp.findOne() ##验证下确保插入了,非常重要
如图
将原来最后一条操作记录写回新的oplog
注意:主节点的oplog大小没有固定值,一般1个标准:建议oplog大小满足2天的修改,这样可以保证从节点在断了1一天以上还能继续同步主节点信息。否则只能重新初始化。
命令如下:
###删除之前的oplog集合
mongo>db.oplog.rs.drop()
###创建新的oplog集合
mongo>db.createCollection("oplog.rs",{"capped":true,"size": 1073741824})`
###将原来oplog最后一条数据插入到新的oplog中
mongo>var temp=db.tempLastOp.findOne()
mongo>db.oplog.rs.insert(temp)
mongo>db.oplog.rs.findOne() ##验证下确实插入成功,非常重要
如下图:
2.5.恢复主节点的配置信息
恢复主节点mongdb的配置。改回之前的端口,和复制集的名称
a.注释端口
#net:
# port=37017 #端口需要临时改成别的
b.将复制集注释信息释放
replication:
oplogSizeMB: 10240 #该配置最好和上面createoplog大小的数字保持一致
replSetName: "prod_core_mongo_repl"
secondaryIndexPrefetch: "all"
如图:
2.6.重新启动主节点和仲裁节点mongo服务,并观察集群状态
登陆主主节点重启mongo命令
sudo systemctl stop mongo
sudo systemctl start mongo
仲裁节点启动命令
sudo systemctl start mongo
主节点:
仲裁节点:
登陆主节点,rs.status()查看集群和db.getReplicationInfo()查看oplog状态
三、集群中有主节点、从节点和仲裁节点---修改主节点oplog步骤
注意:
集群中必须得有可以做主节点的从节点,即不能从节点不能是隐藏节点。
定要保证主节点的oplog的可以支持5分钟以上的窗口,否则关闭主节点后,集群中所有从节点同步会失败。再起主节点后,将没有从节点,且从节点。
3.1关闭主节点mongo服务
登陆仲裁节点服务器的,登陆mongo,密码验证,让主节点退位,再关闭主节点mongo服务
test_mongo_repl:PRIMARY>use admin
test_mongo_repl:PRIMARY>db.auth('root角色用户','密码');
test_mongo_repl:PRIMARY>rs.stepDown()
####再关闭当前节点mongo服务(保证该节点已经是从几点了)
test_mongo_repl:PRIMARY>db.shutdownServer()
#查看mongo进程是否还在
ps -ef|grep mongo
此时剩余的优先级最高的从节点会变成主节点。
3.2.将主节点改为单机模式运行
将主节点以单机模式运行,需修改配置文件的下端口号和复制集名称即可
vim opt/soft/mongodb/mongodb.yml
添加:
net:
port: 37017 #端口需要临时改成别的
将复制信息注释
#replication:
# oplogSizeMB: 409600
# replSetName: "prod_core_mongo_repl"
# secondaryIndexPrefetch: "all"
如图:
##启动mongo服务
sudo systemctl start mongo
3.3.启动主节点mongo服务
登陆主节点的mongo服务(用户需要对local库有读写权限)
登陆命令:
mongo 127.0.0.1:37017
use admin
db.auth('root角色用户','密码'));
#如果该用户没有local库的读写,则新增该角色:
db.grantRolesToUser( "用户", [{'role':'readWrite','db':'local'}])
命令如下:
mongo>use local
mongo>var cursor=db.oplog.rs.find()
mongo>var cursor = db.oplog.rs.find({"op":"i"})
mongo>var lastInsert = cursor.sort({"$natural":-1}).limit(1).next()
mongo>db.tempLastOp.save(lastInsert)
mongo>db.tempLastOp.findOne() ##验证下确保插入了,非常重要
如图
将原来最后一条操作记录写回新的oplog
注意:主节点的oplog大小没有固定值,一般1个标准:建议oplog大小满足2天的修改,这样可以保证从节点在断了1一天以上还能继续同步主节点信息。否则只能重新初始化。
命令如下:
###删除之前的oplog集合
mongo>db.oplog.rs.drop()
###创建新的oplog集合
mongo>db.createCollection("oplog.rs",{"capped":true,"size": 1073741824})`
###将原来oplog最后一条数据插入到新的oplog中
mongo>var temp=db.tempLastOp.findOne()
mongo>db.oplog.rs.insert(temp)
mongo>db.oplog.rs.findOne() ##验证下确实插入成功,非常重要
如下图:
3.4.恢复主节点的配置信息
恢复主节点mongdb的配置。改回之前的端口,和复制集的名称
a.注释端口
#net:
# port=37017 #端口需要临时改成别的
b.将复制集注释信息释放
replication:
oplogSizeMB: 10240 #该配置最好和上面createoplog大小的数字保持一致
replSetName: "prod_core_mongo_repl"
secondaryIndexPrefetch: "all"
如图:
3.5.重新启动主节点mongo服务,并观察集群状态
登陆主节点重启mongo命令
sudo systemctl stop mongo
sudo systemctl start mongo
主节点:
登陆主节点,rs.status()查看集群和db.getReplicationInfo()查看oplog状态
四、附录
4.1 rs.status()命令解释
字段解释:
self 这个信息出现在执行rs.status()函数的成员信息中
stateStr用户描述服务器状态的字符串。有SECONDARY,PRIMARY,RECOVERING等
uptime 从成员可到达一直到现在经历的时间,单位是秒。
optimeDate 每个成员oplog最后一次操作发生的时间,这个时间是心跳报上来的,因此可能会存在延迟
lastHeartbeat 当前服务器最后一次收到其他成员心跳的时间,如果网络故障等可能这个时间会大于2秒
pinMs 心跳从当前服务器达到某个成员所花费的平均时间
errmsg 成员在心跳请求中返回的状态信息,通过是一些状态信息,不全是错误信息。
state和stateStr是重复的,都表示成员状态,只是state是内部的叫法。
health 为1表示server正常,0表示server宕.
state和stateStr是重复的,都表示成员状态,只是state是内部的叫法。
health 为1表示server正常,0表示server宕.
state 为1表明Primary,2表明secondary,3表示Recovering,7表示Arbiter,8表示Down.
optime与optimeDate表达的信息也是一样的,只是表示的方式不同,一个是用新纪元开始的毫秒数表示的,一个是用一种更容易阅读的方式表示。
syncingTo表示当前服务器从哪个节点在做同步。
由于rs.status()是从执行命令成员本身的角度得出的,由于网路等故障,这份报告可能不准确或者有些过时。
4.2 db.getReplicationInfo()命令解释
字段解释:
logSizeMB:oplog大小,单位是MB
usedMB:已使用的空间,有可能会大于11000。
timeDiff:当前oplog的最大时间和最小时间,单位是秒
timeDiffHours:当前oplog的最大时间和最小时间,单位是小时
tFirst:开始时间
tLast:结束时间
now: 当前时间




