mongodb复制集是原生提供这种方式 ,复制集的主要意义在于实现服务的高可用,它的依赖于两个方面的功能
- 输入写入时将数据快速复制到另外一个独立节点上
- 在接受写入的节点发生故障时自动选举一个新的替代节点
在实现高可用的同时,复制集实现了其他几个附加的作用
- 数据分发: 将数据 从一个区域复制到另一个 区域,减少另一个区域的读延迟
- 读写分离:不同类型的压力分别在不同的节点上执行
- 异地容灾:在数据中心故障的时候快速的切换到异地
一个典型的复制集由三个以上的具有投票权的节点组成,包括:
- 一个主节点 (PRIMARY): 接受写入 操作和选举时投票
- 两个或多个从节点 (SECONDARY) : 复制主节点上的新数据 和选举时投票
- 不推荐使用Arbiter(投票节点)
数据是如何复制的?
- 当一个修改操作 ,无论是插入更新或者删除,到达主节点时,他对数据的操作被记录下来,经过一些 必要的转换,这些记录 称为oplog
- 从节点通过在主节点上打开一个 tailable游标不断获取新进入的主节点的oplog,并在自己的数据上回放,以此保持跟主节点的数据一致
通过选举完成的故障恢复
- 具有投票 圈的节点两两互信发送心跳
- 当5次心跳未收到时判断为节点失联
- 如果失联的是主节点,从节点发起选举,选出新的主节点
- 如果失联的是从节点则不会产生新 的选举
- 选举基于RAFT一致性算法实现,选举成功的必要条件是大多数投票节点存活
- 复制集中最多可以有50个节点,但具有投票权的节点最多 7个
影响选举的因素
整个集群必须有大多数节点存货
被选举为主节点的节点必须满足以下条件:
- 能够与多数节点建立连接
- 具有较新 的oplog
- 具有较高的优先级(如果配置了的话)
复制集节点有一下常见的选配项目 :
- 是否具有投票权(v): 有就参与投票
- 优先级(priority):优先级越高的节点优先称为主节点,优先级为0的节点无法称为主节点
- 隐藏(hidden):复制 数据,但对应用不可见。隐藏节点可以 具有投票权,但优先级必须 为0
- 延迟(slaveDelay):复制n秒之前的数据,保持与主节点的 时间差(通常用来作为一个规避误操作的备份节点)
复制集的注意事项
- 所有的节点都有可能称为主节点,配置应该一致
- 复制集版本一致
- 在写频繁的情况下,增加节点不会增加系统的写性能。除非是读多写少的情况
其他配置
ssh-keygen -t rsa
ssh-copy-id 172.16.100.92
ssh-copy-id 172.16.100.93
配置ulimit
[root@Node-172_16_100_91 ~]# ulimit -n
1000000
安装脚本
if ! grep ntp.aliyun.com /var/spool/cron/root >/dev/null 2>&1;then (crontab -l; echo -e "10 * * * * ntpdate ntp.aliyun.com") | crontab -;fi
timedatectl set-timezone Asia/Shanghai
hostnamectl set-hostname mongodb1
wget https://fastdl.mongodb.org/linux/mongodb-linux-x86_64-rhel70-4.4.8.tgz
tar xf mongodb-linux-x86_64-rhel70-4.4.8.tgz -C /usr/local
cd /usr/local/
ln -s mongodb-linux-x86_64-rhel70-4.4.8 mongodb
## ulimit
echo "never" > /sys/kernel/mm/transparent_hugepage/defrag
echo "never" > /sys/kernel/mm/transparent_hugepage/enabled
groupadd -r -g 490 mongodb
useradd -u 490 -s /sbin/nologin -c 'mongodb server' -g mongodb mongodb -M
mkdir /u01/data/mongodb/{data,logs,pid,conf} -p
chown -R mongodb.mongodb /u01/data/mongodb
ln -s /usr/local/mongodb/bin/mongo /usr/local/bin/
#cp /etc/firewalld/zones/public.xml /etc/firewalld/zones/public.xml.oldone
#cat > /etc/firewalld/zones/public.xml /etc/systemd/system/mongodb.service > /etc/hosts
echo "172.16.100.92 mogodb_instance2 mongo3.linuxea.com mongo4.linuxea.com" >> /etc/hosts
echo "172.16.100.93 mogodb_instance3 mongo5.linuxea.com mongo6.linuxea.com" >> /etc/hosts
修改每个节点的主机名
for i in static pretty transient; do hostnamectl set-hostname mogodb_instance1 --$i; done
节点1
cat > /u01/data/mongodb/conf/mongodb.conf /u01/data/mongodb/conf/mongodb.conf /u01/data/mongodb/conf/mongodb.conf rs.initiate({
... _id: "rs02",
... "members" : [
... {
... "_id": 0,
... "host" : "mongo1.linuxea.com:27020"
... },
... {
... "_id": 1,
... "host" : "mongo3.linuxea.com:27020"
... },
... {
... "_id": 2,
... "host" : "mongo5.linuxea.com:27020"
... }
... ]
... });
{ "ok" : 1 }
稍等片刻等待状态:SECONDARY变为PRIMARY
rs02:SECONDARY>
rs02:PRIMARY>
rs02:PRIMARY>
rs02:PRIMARY>
rs02:PRIMARY> sh.status()
printShardingStatus: this db does not have sharding enabled. be sure you are connecting to a mongos from the shell and not to a mongod.
rs02:PRIMARY> rs.status()
{
.............
"members" : [
{
"_id" : 0,
"name" : "mongo1.linuxea.com:27020",
"health" : 1,
"state" : 1,
"stateStr" : "PRIMARY",
"uptime" : 66,
.........
"_id" : 1,
"name" : "mongo3.linuxea.com:27020",
"health" : 1,
"state" : 2,
"stateStr" : "SECONDARY",
"uptime" : 20,
...........
"_id" : 2,
"name" : "mongo5.linuxea.com:27020",
"health" : 1,
"state" : 2,
"stateStr" : "SECONDARY",
"uptime" : 20,
..........
rs02:PRIMARY>
开启集群认证和用户认证
mongodb默认没有一个超级用户的,默认任何人都可以登录。当开启用户认证后仍然可以不使用密码登录,但是不使用密码登录,不能访问里面的资源 ,且只能创建用户
创建用户
创建超级用户
db.createUser({
user: 'superadmin',
pwd: 'password',
roles: [{role: 'root', db: 'admin'}]
}
)
执行
rs02:PRIMARY> use admin
switched to db admin
rs02:PRIMARY> db.createUser({
... user: 'superadmin',
... pwd: 'password',
... roles: [{role: 'root', db: 'admin'}]
... }
... )
Successfully added user: {
"user" : "superadmin",
"roles" : [
{
"role" : "root",
"db" : "admin"
}
]
}
而后就使用创建的账户登录
mongo --host mongo3.linuxea.com:27020 -u superadmin -p password --authenticationDatabase admin
而后创建mark库的读写用户
当创建了amdin用户后,开启认证后,只能登录admin授权其他用户
db.createUser({
user: 'writer',
pwd: 'password',
roles: [{role: 'readWrite', db: 'mark'}]
}
)
db.createUser({
user: 'reader',
pwd: 'password',
roles: [{role: 'read', db: 'mark'}]
}
)
创建mark库的读写超级用户
db.createUser({
user: 'mark',
pwd: 'TdmMzIyNjRmMjViOTc1MGIwZGU',
roles: [{role: 'dbAdmin', db: 'mark'}]
}
)
一旦这样授权,在登录的时候就需要指定库--authenticationDatabase mark
mongo --host mongo3.linuxea.com:27020 -u mark -p TdmMzIyNjRmMjViOTc1MGIwZGU --authenticationDatabase mark
创建集群认证文件
用户创建完成后,还需要创建集群内认证文件
cd /u01/data/mongodb/conf/
openssl rand -base64 756 > keyfile
chmod 400 keyfile
chown mongodb.mongodb keyfile
复制到92和93
scp keyfile 172.16.100.92:/u01/data/mongodb/conf/
scp keyfile 172.16.100.93:/u01/data/mongodb/conf/
ssh 172.16.100.92 "chown mongodb.mongodb /u01/data/mongodb/conf/keyfile"
ssh 172.16.100.93 "chown mongodb.mongodb /u01/data/mongodb/conf/keyfile"
ssh 172.16.100.93 "chmod 400 /u01/data/mongodb/conf/keyfile"
ssh 172.16.100.92 "chmod 400 /u01/data/mongodb/conf/keyfile"
开启security
security:
keyFile: /u01/data/mongodb/conf/keyfile
authorization: enabled
而后重启集群并观察日志
systemctl restart mongodb
tail -f /u01/data/mongodb/logs/mongod.log
尝试登录
超级管理登录
[root@Node-172_16_100_91 ~]# mongo --host mongo1.linuxea.com:27020 -u superadmin -p password --authenticationDatabase admin
MongoDB shell version v4.4.8
connecting to: mongodb://mongo1.linuxea.com:27020/?authSource=admin&compressors=disabled&gssapiServiceName=mongodb
Implicit session: session { "id" : UUID("4f20880e-2ab3-44b6-8ce9-825640ef13d4") }
MongoDB server version: 4.4.8
---
Enable MongoDB's free cloud-based monitoring service, which will then receive and display
metrics about your deployment (disk utilization, CPU, operation statistics, etc).
The monitoring data will be available on a MongoDB website with a unique URL accessible to you
and anyone you share the URL with. MongoDB may use this information to make product
improvements and to suggest MongoDB products and deployment options to you.
To enable free monitoring, run the following command: db.enableFreeMonitoring()
To permanently disable this reminder, run the following command: db.disableFreeMonitoring()
---
rs02:PRIMARY> show dbs
admin 0.000GB
config 0.000GB
local 0.027GB
mark 0.007GB
mark用户登录
[root@Node-172_16_100_91 ~]# mongo --host mongo3.linuxea.com:27020 -u mark -p TdmMzIyNjRmMjViOTc1MGIwZGU --authenticationDatabase mark
MongoDB shell version v4.4.8
connecting to: mongodb://mongo3.linuxea.com:27020/?authSource=mark&compressors=disabled&gssapiServiceName=mongodb
Implicit session: session { "id" : UUID("b6204420-bf30-452f-9cef-e7bb84c73a4d") }
MongoDB server version: 4.4.8
rs02:SECONDARY>
登录PRIMARY
[root@Node-172_16_100_91 ~]# mongo --host mongo1.linuxea.com:27020 -u mark -p TdmMzIyNjRmMjViOTc1MGIwZGU --authenticationDatabase mark
MongoDB shell version v4.4.8
connecting to: mongodb://mongo1.linuxea.com:27020/?authSource=mark&compressors=disabled&gssapiServiceName=mongodb
Implicit session: session { "id" : UUID("9d19034d-e7b9-4ccb-b657-bc84122d0468") }
MongoDB server version: 4.4.8
rs02:PRIMARY> show dbs
mark 0.007GB
rs02:PRIMARY>
开启从节点读
slaveOk()
添加节点
rs.add("hostname And ip:port")
Compose
下载compass进行配置
选择Fill in connection fields individually