连接Mongo集群,应用层面可以直接区分读写状态,无需其他应用做读写分离,架构设计如图所示:
1. 获取MongoDB
https://www.mongodb.com/try/download/community
2. 上传解压
cd /mongodb/
rz
rz waiting to receive.
Starting zmodem transfer. Press Ctrl+C to cancel.
Transferring mongodb-linux-x86_64-rhel70-4.2.8.tgz...
100% 129656 KB 32414 KB/sec 00:00:04 0 Errors
tar xf mongodb-linux-x86_64-rhel70-4.2.8.tgz
3. 关闭THP
修改 /etc/default/grub
GRUB_CMDLINE_LINUX="crashkernel=auto ipv6.disable=1 rd.lvm.lv=rhel/root rd.lvm.lv=rhel/swap rhgb quiet transparent_hugepage=never"
执行如下命令生效,有些系统不生效是因为没有选对相应的命令
grub2-mkconfig -o /boot/efi/EFI/redhat/grub.cfg
grub2-mkconfig -o /boot/grub2/grub.cfg
修改完成重启机器
4. 环境准备
-
创建所需用户和组 useradd mongod
passwd mongod
-
创建mongodb所需目录结构 mkdir -p /mongodb/conf
mkdir -p /mongodb/log
mkdir -p /mongodb/data
-
修改权限 chown -R mongod:mongod /mongodb
-
切换用户并设置环境变量 su - mongod
vi .bash_profile
export PATH=/mongodb/app/bin:$PATH
source .bash_profile
5. 创建配置文件
bindIp以所在服务器为准
$ cat >> /mongodb/mongodb.yaml <<EOF
systemLog:
destination: file
path: /mongodb/log/mongod.log
logAppend: true
processManagement:
fork: true
pidFilePath: /mongodb/mongodb.pid
storage:
dbPath: /mongodb/data
journal:
enabled: true
net:
bindIp: localhost,192.168.1.11
port: 27017
security:
keyFile: /mongodb/secret
authorization: enabled
replication:
replSetName: MongoRepl
EOF
6. 创建密码文件
三个节点需要配置相同的keyfile,否则复发互相通信,此处仅需生成一次,拷贝至其他服务器即可
$ openssl rand -base64 666 > /mongodb/secret
$ chmod 400 /mongodb/secret
$ scp /mongodb/secret mongo@192.168.62.22:/mongodb/secret
$ scp /mongodb/secret mongo@192.168.62.23:/mongodb/secret
7. 三个节点启动mongod进程
$ mongod -f /mongodb/mongodb.yaml
$ ps -ef | grep mongod
8. 初始化副本集
$ mongo
> rs.initiate()
{
"info2" : "no configuration specified. Using a default configuration for the set",
"me" : "192.168.1.11:27017",
"ok" : 1,
"operationTime" : Timestamp(1605262167, 1),
"$clusterTime" : {
"clusterTime" : Timestamp(1605262167, 1),
"signature" : {
"hash" : BinData(0,"AAAAAAAAAAAAAAAAAAAAAAAAAAA="),
"keyId" : NumberLong(0)
}
}
}
如下设置方式设置了权重
rs.initiate({_id:"MongoRepl",
version:1,
members:[{ _id:0, host:"192.168.1.11:27017",priority:2},
{ _id:1, host:"192.168.1.12:27017",priority:1},
{ _id:2, host:"192.168.1.13:27017",priority:1}
]}
)
9. 添加数据库管理用户
$ mongo
MongoRepl:PRIMARY> use admin
MongoRepl:PRIMARY> db.createUser({user: "admin",pwd: "admin1234",roles:[{role: "root",db:"admin"}]})
Successfully added user: {
"user" : "admin",
"roles" : [
{
"role" : "root",
"db" : "admin"
}
]
}
10. 建立业务数据库及用户
mongo用户创建比较特殊,要想用户能直接登录对应的数据库,需要在创建用户前use数据库
$ mongo
MongoRepl:PRIMARY> use admin
MongoRepl:PRIMARY> db.auth("admin","admin1234")
MongoRepl:PRIMARY> use testdb
MongoRepl:PRIMARY> db.createUser({user: "test",pwd: "test1234",roles:[{role: "readWrite",db:"testdb"}]})
Successfully added user: {
"user" : "test",
"roles" : [
{
"role" : "readWrite",
"db" : "testdb"
}
]
}
11. 副本集验证
-
验证同步
登录主节点新增数据
$ mongo
MongoRepl:PRIMARY> use testdb
MongoRepl:PRIMARY> db.auth("test","test1234")
MongoRepl:PRIMARY> db.test.insert({"name":"test"})
WriteResult({ "nInserted" : 1 })
MongoRepl:PRIMARY> db.test.find()
{ "_id" : ObjectId("5ac9f5e06e02cf1ec5d82ae7"), "name" : "test" }
登录从节点192.168.1.12查询数据
$ mongo
MongoRepl:SECONDARY> use testdb
MongoRepl:SECONDARY> db.auth("test","test1234")
MongoRepl:SECONDARY> rs.slaveOk()
MongoRepl:SECONDARY> db.test.find()
{ "_id" : ObjectId("5ac9f5e06e02cf1ec5d82ae7"), "name" : "test" }
-
验证故障转移
关闭主节点
$ mongo
MongoRepl:PRIMARY> use admin
MongoRepl:PRIMARY> db.auth("admin","admin1234")
MongoRepl:PRIMARY> db.shutdownServer()
server should be down...
2018-04-09T09:50:30.195+0800 I NETWORK [thread1] trying reconnect to 127.0.0.1:27017 (127.0.0.1) failed
2018-04-09T09:50:30.195+0800 W NETWORK [thread1] Failed to connect to 127.0.0.1:27017, in(checking socket for error after poll), reason: Connection refused
确认主节点mongod进程已关闭
$ ps -ef|grep mongod
mongo 3799 1581 0 09:54 pts/0 00:00:00 grep mongod
登录从节点查看集群状态
$ mongo
MongoRepl:PRIMARY> db.auth("admin","admin1234")
1
MongoRepl:PRIMARY> rs.status()
{
"set" : "MongoRepl",
"date" : ISODate("2020-11-13T10:47:45.141Z"),
"myState" : 1,
"term" : NumberLong(2),
"heartbeatIntervalMillis" : NumberLong(2000),
"optimes" : {
"lastCommittedOpTime" : {
"ts" : Timestamp(1605264400, 1),
"t" : NumberLong(1)
},
"readConcernMajorityOpTime" : {
"ts" : Timestamp(1605264400, 1),
"t" : NumberLong(1)
},
"appliedOpTime" : {
"ts" : Timestamp(1605264456, 1),
"t" : NumberLong(2)
},
"durableOpTime" : {
"ts" : Timestamp(1605264456, 1),
"t" : NumberLong(2)
}
},
"members" : [
{
"_id" : 0,
"name" : "192.168.1.11:27017",
"health" : 0,
"state" : 8,
"stateStr" : "(not reachable/healthy)",
"uptime" : 0,
"optime" : {
"ts" : Timestamp(0, 0),
"t" : NumberLong(-1)
},
"optimeDurable" : {
"ts" : Timestamp(0, 0),
"t" : NumberLong(-1)
},
"optimeDate" : ISODate("1970-01-01T00:00:00Z"),
"optimeDurableDate" : ISODate("1970-01-01T00:00:00Z"),
"lastHeartbeat" : ISODate("2020-11-13T10:47:43.243Z"),
"lastHeartbeatRecv" : ISODate("2020-11-13T10:46:45.196Z"),
"pingMs" : NumberLong(0),
"lastHeartbeatMessage" : "Connection refused",
"configVersion" : -1
},
{
"_id" : 1,
"name" : "192.168.1.12:27017",
"health" : 1,
"state" : 1,
"stateStr" : "PRIMARY",
"uptime" : 7748,
"optime" : {
"ts" : Timestamp(1605264456, 1),
"t" : NumberLong(2)
},
"optimeDate" : ISODate("2020-11-13T10:47:36Z"),
"infoMessage" : "could not find member to sync from",
"electionTime" : Timestamp(1605264415, 1),
"electionDate" : ISODate("2020-11-13T10:46:55Z"),
"configVersion" : 3,
"self" : true
},
{
"_id" : 2,
"name" : "192.168.1.13:27017",
"health" : 1,
"state" : 7,
"stateStr" : "ARBITER",
"uptime" : 1241,
"lastHeartbeat" : ISODate("2020-11-13T10:47:43.186Z"),
"lastHeartbeatRecv" : ISODate("2020-11-13T10:47:44.331Z"),
"pingMs" : NumberLong(0),
"configVersion" : 3
}
],
"ok" : 1,
"operationTime" : Timestamp(1605264456, 1),
"$clusterTime" : {
"clusterTime" : Timestamp(1605264456, 1),
"signature" : {
"hash" : BinData(0,"j7wJlWUpy/znoe6RSdnRL/yfVz0="),
"keyId" : NumberLong("6894548517361025025")
}
}
}
|