Databases / 运维笔记

Mongodb分片集群部署

Einic Yeo · 4月14日 · 2019年 ·

一、架构

1、Mongodb分片集群配置

按照尽量节省资源的原则,不交叉部署的原则:

作用配置数量
分片1-主、分片1-副8C16G300GSSD2
分片1-仲裁节点4C8G100GSSD1
分片2-主、分片2-副8C16G300GSSD2
分片2-仲裁节点4C8G100GSSD1
config服务复制集(1主2副)4C8G100GSSD3
mongos路由2C4G40GSSD版权声明:本文遵循 CC 4.0 BY-SA 版权协议,若要转载请务必附上原文出处链接及本声明,谢谢合作!3

2、说明

MongoDB分片集群,英文名称为: Sharded Cluster。旨在通过横向扩展,来提高数据吞吐性能、增大数据存储量。

分片集群由三个组件:“mongos”, “config server”, “shard” 组成。

  • mongos:数据库请求路由。负责接收所有客户端应用程序的连接查询请求,并将请求路由到集群内部对应的分片上。”mongos”可以有1个或多个。本身不保存数据,在启动时从配置服务器加载集群信息,开启mongos进程需要知道配置服务器的地址,指定configdb选项。
  • config server: 配置服务器。是一个独立的mongod进程,保存集群和分片的元数据,即各分片包含了哪些数据的信息。最先开始建立,启用日志功能。像启动普通的mongod一样启动配置服务器,指定configsvr选项。不需要太多的空间和资源,配置服务器的1KB空间相当于真是数据的200MB。保存的只是数据的分布表。当服务不可用,则变成只读,无法分块、迁移数据。
  • shard: 分片存储。将数据分片存储在多个服务器上。有点类似关系数据库”分区表”的概念,只不过分区表是将数据分散存储在多个文件中,而sharding将数据分散存储在多个服务器上。一版权声明:本文遵循 CC 4.0 BY-SA 版权协议,若要转载请务必附上原文出处链接及本声明,谢谢合作!个集群可以有一个或多个分片。
  • 每个分片都必须是副本集,“config server” 必须是副本集!

二、环境准备

  • 操作系统:Centos6.5
  • Mongodb版本:3.2.1 RPM包
mongodb-org-server-3.2.1-1.el7.x86_64.rpm
mongodb-org-tools-3.2.1-1.el7.x86_64.rpm
mongodb-org-mongos-3.2.1-1.el7.x86_64.rpm
mongodb-org-shell-3.2.1-1.el7.x86_64.rpm
mongodb-org-3.2.1-1.el7.x86_64.rpm
  • 主机规划:mongos(3个)+ config server 副本集(1主2从) + 分片(2个,每个分片由1主1从1仲裁组成),一共12台主版权声明:本文遵循 CC 4.0 BY-SA 版权协议,若要转载请务必附上原文出处链接及本声明,谢谢合作!机:
主机编号IP地址角色
1192.168.1.1Mongos-1
2192.168.1.2Mongos-2
3192.168.1.3 Mongos-3
4192.168.1.11Config-1
5192.168.1.12Config-2
6192.168.1.13Config-3
7192.168.1.21Shard1-Primary
8192.168.1.22Shard1-Secondary
9192.168.1.23Shard1-Arbiter
10192.168.1.31Shard2-Primary
11192.168.1.32Shard2-Secondary
12192.168.1.33Shard2-Arbiter

注意:所有主机的hostname最好不要相同,以免影响mongos信息在config服务数据库中的存储。

三、分片集群搭建

1、搭建步骤

分片集群各组件搭建顺序如下,不能错:

  1. ConfigServer –> 2.Shard集群 –> 3.Mongos

启动顺序也是这样

2、所有主机预备操作

2.1、修改Linux主机能创建的文件数量限制

echo "ulimit -c unlimited" >> /etc/profile && source /etc/profile

cat >> /etc/security/limits.conf << EOF
* soft nofile 262140
* hard nofile 262140
root soft nofile 262140
root hard nofile 262140
* soft core unlimited
* hard core unlimited
root soft core unlimited
root hard core unlimited
EOF
echo "session  required  pam_limits.so">> /etc/pam.d/login

2.2、使用RPM包安装mongodb

rpm -ivh mongodb-org-server-3.2.1-1.el7.x86_64.rpm
rpm -ivh mongodb-org-tools-3.2.1-1.el7.x86_64.rpm
rpm -ivh mongodb-org-mongos-3.2.1-1.el7.x86_64.rpm
rpm -ivh mongodb-org-shell-3.2.1-1.el7.x86_64.rpm
rpm -ivh mongodb-org-3.2.1-1.el7.x86_64.rpm

2.3、修改监听IP

sed -i "s/bindIp: 127.0.0.1/bindIp: 0.0.0.0/g" /etc/mongod.conf

2.4、清空防火墙

iptables -F
systemctl stop firewalld
systemctl disable firewalld

或者,在防火墙添加相应的放通策略,也可以

3、搭建Config-Server集群

ConfigServer是一个副本集集群,一主两从,按照搭建副本集的方式搭建即可。

3.1、修改Congfig-Server配置文件

三台主机配置相同,依次执行如下命令:

cat >> /etc/mongod.conf << EOF
replication:
  oplogSizeMB: 2048
  replSetName: mars-config

sharding:
  clusterRole: configsvr
EOF

注意:集群角色必须是configsvr

3.2、启动Mongod

三台主机依次启动mongod程序

systemctl start mongod   

3.3、初始化config-server副本集

三台主机随便挑一台,敲mongo进入mongo shell,执行如下命令:

rs.initiate( {
    _id: "mars-config",
    configsvr: true,
    members: [
        { _id: 0, host: "192.168.0.11:27017"},
        { _id: 1, host: "192.168.0.12:27017"},
        { _id: 2, host: "192.168.0.13:27017"}
    ]
} )

注意:id为集群名称,configsvr为true。

3.4 验证

rs.status()

4、搭建Shard分片复制集集群

此处我们采用2个Shard分片,每个分片是一个主-从-仲裁的三节点复制集。两个分片配置过程一致。

4.1、分片1

4.1.1、修改配置文件

三台主机配置相同,依次执行如下shell命令:

cat >> /etc/mongod.conf << EOF
replication:
  oplogSizeMB: 2048
  replSetName: mars-shard1

sharding:
  clusterRole: shardsvr
EOF

注意:集群名字为shard1,要和分片2区分开。集群角色为shardsvr。

4.1.2、启动mongod
systemctl start mongod
4.1.3、初始化Shard1副本集

三台主机随便挑一台,敲mongo进入mongo shell,执行如下命令:

rs.initiate( {
    _id: "mars-shard1",
    members: [
        { _id: 0, host: "192.168.0.21:27017"},
        { _id: 1, host: "192.168.0.22:27017"},
        { _id: 2, host: "192.168.0.23:27017", arbiterOnly: true}
    ]
} )

注意:id为配置文件中的集群名称。

4.1.4、验证
rs.status()

4.2、分片2

4.2.1、修改配置文件

三台主机配置相同,依次执行如下shell命令:

cat >> /etc/mongod.conf << EOF
replication:
  oplogSizeMB: 2048
  replSetName: mars-shard2

sharding:
  clusterRole: shardsvr
EOF

注意:集群名字为shard2,要和分片1区分开。集群角色为shardsvr。

4.2.2、启动mongod
systemctl start mongod
4.2.3、初始化Shard1副本集

三台主机随便挑一台,敲mongo进入mongo shell,执行如下命令:

rs.initiate( {
    _id: "mars-shard1",
    members: [
        { _id: 0, host: "192.168.0.31:27017"},
        { _id: 1, host: "192.168.0.32:27017"},
        { _id: 2, host: "192.168.0.33:27017", arbiterOnly: true}
    ]
} )

注意:id为配置文件中的集群名称。

我这里把第三台主机设为仲裁主机,是为了节省硬件资源,节约成本。如果不在乎这点成本,可以去掉上面arbiterOnly的配置。

4.2.4、验证版权声明:本文遵循 CC 4.0 BY-SA 版权协议,若要转载请务必附上原文出处链接及本声明,谢谢合作!
rs.status()

5、搭建mongos路由

mongos可以为1个,也可以为多个,可以根据需要横向扩展,这里采用3个。

mongos的主机名hostname必须要保持不同,如果相同,config的数据库中就只会保存一个mongos信息,从而造成active mongos数量永远是1。

5.1、修改配置文件

mongos的配置文件为mongos.conf,如果不存在就采用如下方式新建,三台主机依次执行:

cat >> /etc/mongos.conf << EOF
systemLog:
  destination: file
  logAppend: true
  path: /var/log/mongodb/mongod.log

# how the process runs
processManagement:
  fork: true  # fork and run in background
  pidFilePath: /var/run/mongodb/mongos.pid  # location of pidfile

# network interfaces
net:
  port: 27017

sharding:
  configDB: mars-config/192.168.0.11:27017, 192.168.0.12:27017, 192.168.0.13:27017
EOF

注意:configDB为config-server集群的IP和端口,不要填错。

5.2、启动mongos

已mongod用户启动mongos,三台主机依次执行:

sudo -u mongod mongos -f /etc/mongos.conf

5.3、添加分片

连接任意一个mongos,在任意一台主机上执行mongo,添加分片信息:

use admin

sh.addShard("mars-shard1/192.168.0.21:27017,192.168.0.22:27017,192.168.0.23:27017")

sh.addShard("mars-shard2/192.168.0.31:27017,192.168.0.32:27017,192.168.0.33:27017")

5.4、验证

sh.status()

6、使用分片

使用分片的基本步骤是:1.开启数据库分片–> 2.开启集合分片

对数据库分片是对集合分片的先决条件。

6.1、开启数据库分片

以testdb数据库为例,在一台mongos上,进入mongoshell,执行:

sh.enableSharding("testdb")

6.2、开始集合分片

已testdb.coll1集合为例:

sh.shardCollection("testdb.coll1", {"name" : "hashed"})

说明:

  • 第一个参数为集合的完整namespace名称,此例集合为testdb.coll1。
  • 第二个参数为片键,指定根据哪个字段进行分片,此例对name字段进行hash分片。

6.3、插入数据验证分片

插入测试数据

use testdb

for (var i = 1; i <= 100000; i++){
  db.coll1.insert({"id" : i, "name" : "name" + i});
}

验证是否分片

sh.status()

7、添加集群版权声明:本文遵循 CC 4.0 BY-SA 版权协议,若要转载请务必附上原文出处链接及本声明,谢谢合作!认证

上文已经成功创建一个分片集群,并验证数据分片可用。但在部署生产环境时,还需添加认证,用以保障集群安全性。
认证分两种:

  • 集群内部认证 (Internal Authentication)
    用于集群内的各个组件(mongos, config server, shard)之间相互访问认证,也就是所有的mongos进程和mongod进程之间相互访问认证。
    内部认证通过keyfile密钥文件实现,即所有的monogs/mongod公用同一个keyfile文件来相互认证。如果集群外随便来一个”mongod”进程,如果没有相同的keyfile,想加入集群,是不可能的。
  • 外部用户访问集群所需的用户认证 (User Access Controls)
    用于外部客户端访问mongos时,所需的用户认证。

7.1、生成并分发密钥文件Keyfile

在第一台主机上执行

openssl rand -base64 756 > /var/lib/mongo/keyFile
chmod 600 /var/lib/mongo/keyFile
chown -R mongod:mongod /var/lib/mongo/keyFile

其他所有主机复制第一台生成的keyFile文件(通过lszrz 或者 scp 或者 ftp),并执行以下命令:

cp keyFile /var/lib/mongo/
chmod 600 /var/lib/mongo/keyFile
chown -R mongod:mongod /var/lib/mongo/keyFile

7.2、添加用户

连接到任意一台mongos上,添加超级管理员用户:

use admin
db.createUser({user: "admin",pwd: "[email protected]",roles: [ { role: "userAdminAnyDatabase", db: "admin" },{ role: "clusterAdmin", db: "admin" }]})

添加客户端用户:

use test_db
db.createUser({user: "test_rw",pwd: "xxx#111",roles: [{ role: "dbOwner", db: "test_db"}]})

在”mongos”上添加用户,用户信息实际保存在”config server”上,”mongos”本身不存储任何数据,包括用户信息。

然而,”mongos”上创建的用户,是不会自动添加到”shard”分片服务器上的。
为了以后方便维护shard分片服务器,分别登录到每个分片服务器的”primary”节点,添加管理员用户:

use admin
db.createUser({user: "admin",pwd: "[email protected]",roles: [ { role: "userAdminAnyDatabase", db: "admin" },{ role: "clusterAdmin", db: "admin" }]})

7.3、开启认证

7.3.1、为所有mongod程序添加认证参数

所有mongod程序包括,config-server主机3台,分片集群6台。

cat >> /etc/mongod.conf << EOF

security:
  authorization: enabled
  keyFile: /var/lib/mongo/keyFile
EOF
7.3.2、为所有mongos程序添加认证参数

在三台mongos主机上执行:

cat >> /etc/mongos.conf << EOF

security:
  keyFile: /var/lib/mongo/keyFile
EOF
7.3.3、停止集群内所有mongos和mongod程序

mongos程序使用kill -9 pid停止,mongod程序使用systemctl stop mongod停止。

7.3.4、按顺序启动所有程序
  1. config-server -> 2. shard集群 -> 3. mongos
7.3.5、验证用户访问

通过连接任意一个mongos,验证管理员用户和客户端用户的访问。

0 条回应