MongoDB高可用集群搭建(主从、分片、路由、安全验证)

怎甘沉沦 提交于 2020-05-01 02:14:12

目录

一、环境准备

1、部署图

2、模块介绍

3、服务器准备

二、环境变量

1、准备三台集群

2、安装解压

3、配置环境变量

三、集群搭建

1、新建配置目录

2、修改配置文件

3、分发其他节点

4、批量启动

5、创建配置服务器副本集

四、集群测试

1、启动路由服务器客户端

2、插入数据

3、验证主从

5、web控制台(浏览器访问)

1、登陆路由服务器

2、串联路由和分片副本集

3、查看分片服务器的配置 

4、数据库的分片设置

5、验证分片

七、高可用验证

1、测试集群的高可用性

2、查看sharding status

3、查看数据库配置信息

八、集群安全验证

1、Key生成

2、配置文件修改

3、增加权限实例

4、针对于数据库 siger建用户

九、安全管理

1、查询数据库所有用户

2、查询数据库角色

3、修改权限

MongoDB高可用集群搭建(主从、分片、路由、安全验证)

一、环境准备
1、部署图


集群部署图1

 

集群部署图2

图片来源于网络

2、模块介绍
Shard服务器:使用Replica Sets确保每个数据节点都具有备份、自动容错转移、自动恢复的能力。
配置服务器:使用使用3个配置服务器确保元数据完整性。
路由进程:使用3个路由进程实现平衡,提高客户端接入性能
3 个分片进程:Shard11,Shard12,Shard13 组成一个副本集,提供Sharding 中 shard1 的功能。
3 个分片进程:Shard21,Shard22,Shard23 组成一个副本集,提供Sharding 中 Shard2 的功能。
3 个分片进程:Shard31,Shard32,Shard33 组成一个副本集,提供Sharding 中 Shard3的功能。
3个配置服务器进程和3个路由器进程。
构建一个 mongoDB Sharding Cluster 需要三种角色:shard 服务器(ShardServer)、配置服务器(config Server)、路由进程(Route Process)

Shard 服务器

  shard 服务器即存储实际数据的分片,每个 shard 可以是一个 mongod 实例, 也可以是一组 mongod 实例构成的 Replica Sets.为了实现每个 Shard 内部的故障 自动转换,MongoDB 官方建议每个 shard 为一组 Replica Sets.
配置服务器

  为了将一个特定的 collection 存储在多个 shard 中,需要为该 collection 指定 一个 shard key,决定该条记录属于哪个 chunk,配置服务器可以存储以下信息, 每个shard节点的配置信息,每个chunk的shard key范围,chunk在各shard 的分布情况,集群中所有 DB 和 collection 的 sharding 配置信息。
路由进程

它是一个前段路由,客户端由此接入,首先询问配置服务器需要到哪个 shard 上查询或保存记录,然后连接相应的 shard 执行操作,最后将结果返回给客户端,客 户端只需要将原本发给 mongod 的查询或更新请求原封不动地发给路由进程,而 不必关心所操作的记录存储在哪个 shard 上。

3、服务器准备
按照架构图,理论上是需要 16 台机器的,由于资源有限,用目录来替代物理机(有风险,若其中某台机器宕机,配置在该机器的服务都会 down 掉),下面给出配置表格: 

服务器

Host

服务和端口

1

172.8.10.140

Shard11:22001 Shard21:22002 Shard31: 22003 ConfigSvr:21000 Mongos:20000

2

172.8.10.141

Shard12:22001 Shard22:22002 Shard32: 22003

ConfigSvr: 21000 Mongos: 20000

3

172.8.10.142

Shard13:22001 Shard23:22002 Shard33: 22003

ConfigSvr: 21000 Mongos: 20000

二、环境变量
1、准备三台集群
172.8.10.140 siger-master.siger.com

172.8.10.141 siger-node1.siger.com

172.8.10.142 siger-node2.siger.com

2、安装解压
#建立mongodb文件夹并进入,将安装包放进文件夹并解压

#将jar放入cd /usr/local/目录下

tar -zxvf mongodb-linux-x86_64-rhel70-3.6.5.tgz

#名称更改为mongodb

mv mongodb-linux-x86_64-rhel70-3.6.5 mongodb

3、配置环境变量
#输入vi /etc/profile编辑

MONGODB_HOME=/usr/local/mongodb

:$MONGODB_HOME/bin

 

#编译环境变量,使其生效

. /etc/profile

三、集群搭建
1、新建配置目录
#进入/usr/local/mongodb,新建目录

mkdir key

 

mkdir route

mkdir route/data

mkdir route/log

mkdir route/pid

 

mkdir config

mkdir config/data

mkdir config/log

mkdir config/pid

 

mkdir shard1

mkdir shard1/data

mkdir shard1/log

mkdir shard1/pid

 

mkdir shard2

mkdir shard2/data

mkdir shard2/log

mkdir shard3/pid

 

mkdir shard3

mkdir shard3/data

mkdir shard3/log

mkdir shard3/pid

 

2、修改配置文件
配置服务器:config.conf 

路由服务器配置:route.conf 

shard服务器配置:shard1.conf       shard2.conf        shard3.conf

vi /usr/local/mongodb/config/config.conf
#指定数据目录,默认是/data/db/。每个mongod进程都需要独立的目录

#启动mongod时就会在数据目录中创建mongod.lock文件,防止其他mongod进程使用该数据目录

dbpath=/usr/local/mongodb/config/data

#日志文件存放目录 

logpath=/usr/local/mongodb/config/logs/config.log

#进程存放目录 

pidfilepath=/usr/local/mongodb/config/pid/config.pid

#一个数据库一个文件夹

directoryperdb=true

#使用追加的方式写日志

logappend=true

#集群名字

#这个是创建副本集的方式,如果master指定了,这个地方不可以再指定了

replSet=config

#指定服务器监听的端口,默认是27017

port=21000

#以守护进程的方式运行MongoDB

fork=true

configsvr=true

#启用日志选项,MongoDB的数据操作将会写入到journal文件夹的文件里

journal=true

#不启动认证

noauth=true

#启动认证

auth=true

vim /usr/local/mongodb/route/route.conf
#设定config server的地址列表,每个server地址之间以“,”分割

configdb=config/172.8.10.140:21000,172.8.10.141:21000,172.8.10.142:21000

#进程存放目录

pidfilepath=/usr/local/mongodb/route/pid/route.pid

#指定服务器监听的端口,默认是27017

port=20000

#sharded集群中每个chunk的大小,单位:MB,默认为64

#chunkSize=1

#日志文件存放目录

logpath=/usr/local/mongodb/route/logs/route.log

#使用追加的方式写日志

logappend=true

#以守护进程的方式运行

fork=true

vim /usr/local/mongodb/shard1/shard1.conf
#指定数据目录,默认是/data/db/。每个mongod进程都需要独立的目录

dbpath=/usr/local/mongodb/shard1/data

#日志文件存放目录

logpath=/usr/local/mongodb/shard1/logs/shard1.log

#进程存放目录

pidfilepath=/usr/local/mongodb/shard1/pid/shard1.pid

#一个数据库一个文件夹

directoryperdb=true

#使用追加的方式写日志

logappend=true

#集群名字

#这个是创建副本集的方式,如果master指定了,这个地方不可以再指定了

replSet=shard1

#指定服务器监听的端口,默认是27017

port=22001

#以守护进程的方式运行MongoDB

fork=true

#启用日志选项,MongoDB的数据操作将会写入到journal文件夹的文件里

journal=true

#此实例为shard(分片),侦听27018端口

shardsvr=true

vim /usr/local/mongodb/shard2/shard2.conf
#指定数据目录,默认是/data/db/。每个mongod进程都需要独立的目录

dbpath=/usr/local/mongodb/shard2/data

#日志文件存放目录

logpath=/usr/local/mongodb/shard2/logs/shard2.log

#进程存放目录

pidfilepath=/usr/local/mongodb/shard2/pid/shard2.pid

#一个数据库一个文件夹

directoryperdb=true

#使用追加的方式写日志

logappend=true

#集群名字

#这个是创建副本集的方式,如果master指定了,这个地方不可以再指定了

replSet=shard2

#指定服务器监听的端口,默认是27017

port=22002

#以守护进程的方式运行MongoDB

fork=true

#启用日志选项,MongoDB的数据操作将会写入到journal文件夹的文件里

journal=true

#此实例为shard(分片),侦听27018端口

shardsvr=true

vim /usr/local/mongodb/shard3/shard3.conf
#指定数据目录,默认是/data/db/。每个mongod进程都需要独立的目录

dbpath=/usr/local/mongodb/shard3/data

#日志文件存放目录

logpath=/usr/local/mongodb/shard3/logs/shard3.log

#进程存放目录

pidfilepath=/usr/local/mongodb/shard3/pid/shard3.pid

#一个数据库一个文件夹

directoryperdb=true

#使用追加的方式写日志

logappend=true

#集群名字

#这个是创建副本集的方式,如果master指定了,这个地方不可以再指定了

replSet=shard3

#指定服务器监听的端口,默认是27017

port=22003

#以守护进程的方式运行MongoDB

fork=true

#启用日志选项,MongoDB的数据操作将会写入到journal文件夹的文件里

journal=true

#此实例为shard(分片),侦听27018端口

shardsvr=true

3、分发其他节点
#将mongodb分发给其他两个节点

cd /usr/local
scp -r mongodb/ root@172.8.10.141:/usr/local/
scp -r mongodb/ root@172.8.10.142:/usr/local/
4、批量启动
启动顺序为 mogodb(shard) ->  config  - > mongos

mongod -f /usr/local/mongodb/shard1/shard1.conf

mongod -f /usr/local/mongodb/shard2/shard2.conf

mongod -f /usr/local/mongodb/shard3/shard3.conf

mongod -f /usr/local/mongodb/config/config.conf

注意:初次登陆时候,先加入数据集和副本集。然后再启动路由服务器

mongos -f /usr/local/mongodb/route/route.conf

 

5、创建配置服务器副本集

#将140,141,142加入 Replic Set

mongo --host 172.8.10.140 --port 21000
use admin
db.runCommand({"replSetInitiate":{"_id":"config","members":[{"_id":0,"host":"172.8.10.140:21000"},{"_id":1,"host":"172.8.10.141:21000"},{"_id":2,"host":"172.8.10.142:21000"}]}});


查看副本集配置

rs.conf()


查看副本集状态

rs.status()
6、创建分片服务器副本集

#将140,141,142加入 Replic Set

#登陆shard1分片服务器,增加分片

 

加入shard1副本集:登陆shard1端口

mongo --host 172.8.10.140 --port 22001
use admin
db.runCommand({"replSetInitiate":{"_id":"shard1","members":[{"_id":0,"host":"172.8.10.140:22001",priority:10},{"_id":1,"host":"172.8.10.141:22001",priority:8},{"_id":2,"host":"172.8.10.142:22001",arbiterOnly:true}]}});
加入shard2副本集:登陆shard2端口

mongo --host 172.8.10.140 --port 22002
use admin
db.runCommand({"replSetInitiate":{"_id":"shard2","members":[{"_id":0,"host":"172.8.10.140:22002",priority:8},{"_id":1,"host":"172.8.10.141:22002",priority:10},{"_id":2,"host":"172.8.10.142:22002",arbiterOnly:true}]}});
加入shard3副本集:登陆shard3端口

mongo --host 172.8.10.140 --port 22003
use admin
db.runCommand({"replSetInitiate":{"_id":"shard3","members":[{"_id":0,"host":"172.8.10.140:22003"},{"_id":1,"host":"172.8.10.141:22003"},{"_id":2,"host":"172.8.10.142:22003",arbiterOnly:true}]}});

 

 


四、集群测试
1、启动路由服务器客户端
#进入140的mongodb客户端(主)

       mongo --host 172.8.10.140 --port 21000

 

2、插入数据
db.col.insert({title: 'MongoDB 教程',
    description: 'MongoDB 是一个 Nosql 数据库',

    by: '菜鸟教程',

    url: 'http://www.runoob.com',

    tags: ['mongodb', 'database', 'NoSQL'],

    likes: 100

   })

 

3、验证主从
#进入141的mongodb客户端(从),查看刚刚插入的数据

mongo --host 172.8.10.141 --port 21000
rs.slaveOk();
show dbs
use config
db.col.find().pretty()


4、关闭数据库

mongod  --shutdown  --dbpath /usr/local/mongodb/config/data
5、web控制台(浏览器访问)
Web控制台开启,增加配置参数 httpinterface=yes 。

配置过后可以在浏览器访问,这里没有配置,后期有时间再优化

mongodb默认自带提供了web访问接口,通过 IP + 端口(默认:28017)的形式可以访问。 http://ip:port172.8.10.140:21000

 

五、内核参数调整

查看启动日志,如含有以下警号信息:

 

调整方法如下,在每个节点上输入:

echo "never" > /sys/kernel/mm/transparent_hugepage/enabled

echo "never" > /sys/kernel/mm/transparent_hugepage/defra

六、配置分片的表和片键以及分片的验证

目前搭建了mongodb配置服务器、路由服务器,各个分片服务器,不过应用程序连接到 mongos 路由服务器并不能使用分片机制,还需要在程序里设置分片配置,让分片生效。 

1、登陆路由服务器
#连接到mongos ,登录到路由节点,输入如下命令: 

mongo 172.8.10.140:20000

 

2、串联路由和分片副本集
注意:不识别ip,只是别域名

 #使用admin数据库 use admin
 

#串联路由服务器与分片副本集1 

db.runCommand({addshard:"shard1/172.8.10.140:22001,172.8.10.141:22001,172.8.10.142:22001"})
#串联路由服务器与分片副本集2 

db.runCommand({addshard:"shard2/172.8.10.140:22002,172.8.10.141:22002,172.8.10.142:22002"})
#串联路由服务器与分片副本集3 

db.runCommand({addshard:"shard3/172.8.10.140:22003,172.8.10.141:22003,172.8.10.142:22003"})


3、查看分片服务器的配置 
db.runCommand({ listshards:1 })


因为172.8.10.142是每个分片副本集的仲裁节点,所以在上面结果没有列出来

4、数据库的分片设置
#目前配置服务、路由服务、分片服务、副本集服务都已经串联起来了。连接在mongos上,准备让指定的数据库、指定的集合分片生效。 

#创建 friends 库,指定friends分片生效 

show dbs
use admin
db.runCommand({enablesharding:"siger"})
# 使用 siger里的test 表来做分片,片键为 id 且唯一,指定数据库里分片的集合和片键 

db.runCommand({shardcollection:"siger.test",key:{id:1},unique : true })


注意:设置friends的 user表需要分片,根据 id 自动分片到 shard1 ,shard2,shard3 上面去。要这样设置是因为不是所有mongodb 的数据库和表 都需要分片! 

#批量插入一段数据

use siger
show collections
for (var i = 1; i <= 1000000; i++) db.test.save({id:i, name:"weiyang", addr:"Beijing",  country:"China"})


#查看集合

show collections
#查看数据,显示插入的数据已经成功了

db.test.find()
#查看集合数据的条数

db.test.count()


5、验证分片
use siger
db.test.stats()

 


6、删除分片表和数据库

在config库里面删除这个collection相关的信息,主要涉及到的collection表有locks。 

use siger
db.users.drop()
use config
#删除表

db.collections.remove( { _id: "siger.users" } )
db.locks.remove( { _id: "siger.users" } )


#删除数据库

db. databases.remove( { _id: "siger" } )
db.locks.remove( { _id: "siger" } )
#刷新数据库

use admin
db.adminCommand("flushRouterConfig")
7、磁盘上的物理文件情况

#进入172.8.10.140,输入

ll /usr/local/mongodb/shard1/data/siger/
ll /usr/local/mongodb/shard2/data/siger/
ll /usr/local/mongodb/shard3/data/siger/


表明siger.users 集合已经被分片处理了,

#进入172.8.10.141,输入

ll /usr/local/mongodb/shard1/data/siger/
ll /usr/local/mongodb/shard2/data/siger/
ll /usr/local/mongodb/shard3/data/siger/


说明数据热备生效

七、高可用验证
1、测试集群的高可用性
首先是查看集群的状态图 :

 

下面,我 kill 掉 shard1 服务,看会发生什么情况?截图如下: 

 

这里我已经 kill 了 shard1的进程服务。接下来,我们在 20000 端口的路由 节点输入:db.user.stats()查看状态,显示运行正常。

mongo --host 172.8.10.140 --port 20000
use siger
db.users.stats()


2、查看sharding status
#插入数据时查看最新的sharding status

use admin
db.printShardingStatus()


3、查看数据库配置信息
use siegr
db.stats()

 


八、集群安全验证
1、Key生成
#生成autokey密钥,然后分发到其他两台节点上

/usr/local/mongodb/key
openssl rand -base64 753 >keyfile
chmod 600 keyfile 
scp -r autokey root@172.8.10.141: /usr/local/mongodb/key
scp -r autokey root@172.8.10.142: /usr/local/mongodb/key


2、配置文件修改
分别修改 机器140、141、 142所对应配置, shard 1-3(分片) 、config(配置)、route(路由)下对对应的文件夹下 添加 keyFile 所对应路径 
keyFile= /usr/local/mongodb/key/autokey
auth=true

140机器 :config.conf  route.conf  shard1.conf  shard2.conf  shard3.conf  

141 机器 :config.conf  route.conf  shard1.conf  shard2.conf  shard3.conf  

142 机器:config.conf  route.conf  shard1.conf  shard2.conf  shard3.conf  

 

3、增加权限实例
#admin 库中  增加用户权限

mongo 172.8.10.140:20000/admin
db.createUser( { user: "siger", pwd: "xxxxxx",roles: [ "userAdminAnyDatabase" ] } )
db.auth("siger","xxxxxx")
密码自定义
4、针对于数据库 siger建用户

mongo 172.8.10.140:20000/admin
use siger
db.createUser( { user: "siger", pwd: "xxxxxx",roles: [ "readWrite" ] } )
如果不以用户登录至数据库,操作相关数据(报没有权限异常),如以下:

九、安全管理
1、查询数据库所有用户
use admin
db.system.users.find()
2、查询数据库角色

#在admin数据库中,查询admin 该库中的用户 及 角色 

use admin
db.auth(“kenny”,”xxxxxx”)
show users
3、修改权限

# userAdminAnyDatabase权限

db.createUser( { user: "root", pwd: "xxxxxx",roles: [ "userAdminAnyDatabase" ] } )
db.auth(“root”,” xxxxxx”);
#  root超级管理员权限

db.createUser( { user: "root", pwd: "xxxxxx",roles: [ "root" ] } ) 
db.auth(“root”,” xxxxxx”);
#当前库testdb中创建

use testdb
db.createUser( { user: "auth01", pwd: "xxxxxx",roles: [ "readWrite" ] } )
db.auth(“auth01”,” xxxxxx”);
#当前库 siger库中创建
#read权限

use siger
db.createUser({user: "wy",pwd: "xxxxxx",roles: ["read"]})
# readWrite

db.createUser({user: "yang",pwd: "xxxxxx",roles: ["readWrite"]})
#查看该数据库用户及角色

show users

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!