MongoDB 3.4 - 复制集、鉴权、主从同步以及读写分离

许久没更新了。带来centos7下MongoDB3.4的复制集、鉴权、主从同步和读写分离方案。
转载请注明出处:http://blog.lzoro.com

BiuBiu

老惯例之碎碎念。
厦门的夏天又来了,热得整个人都没脾气了。
最近忙得连轴转,博客也停了很久,空闲下来还是要继续写的。

环境

一台装有vsphere6.5的宿主机,和宿主机上的centos7三台。

1、vsphere 6.5
2、centos 7 X 3
    192.168.1.207(master)
    192.168.1.245(secodary)
    192.168.1.249(arbiter)
3、MongoDB 3.4
4、Java SSM 结构的应用

安装MongoDB

1、这里采用的是yum源的方式安装,所以需要先添加yum源
vim /etc/yum.repos.d/mongodb-org-3.4.repo
2、输入以下内容并保存,如果yum源无效,请百度新的yum源。
[mongodb-org-3.4]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/$releasever/mongodb-org/3.4/x86_64/
gpgcheck=0
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-3.2.asc
3、执行安装
yum install -y mongodb-org
安装成功的提示
4、修改配置(yaml格式),如有需要可以对配置文件的标注的[1][2][3][4]点进行修改。
vim /etc/mongod.conf

下面为配置文件内容

# mongod.conf

# for documentation of all options, see:
#   http://docs.mongodb.org/manual/reference/configuration-options/

# where to write logging data.
systemLog:
  destination: file
  logAppend: true
  # [1]日志存储路径
  path: /var/log/mongodb/mongod.log

# Where and how to store data.
storage:
  # [2]数据存储路径
  dbPath: /var/lib/mongo
  journal:
    enabled: true
#  engine:
#  mmapv1:
#  wiredTiger:

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

# network interfaces
net:
  # [3]端口,默认为27017,可修改为其他
  port: 27017
  # [4]如果需要对外提供访问,请把该下面那行注释掉
  bindIp: 127.0.0.1  # Listen to local interface only, comment to listen on all interfaces.


#security:

#operationProfiling:

#replication:

#sharding:

## Enterprise-Only Options

#auditLog:

#snmp:
5、分别在三台服务器上执行上述三个安装操作

配置鉴权、复制集并启动

1、从三台MongoDB中选择一台作为master,我这里是192.168.1.207,启动并创建管理员,方便开启鉴权后的操作

启动

mongod -f /etc/mongod.conf

连接

mongo --port=27017

创建账号

use admin;

db.createUser({user:"dba",pwd:"yourpassword",roles:[{role:"root",db:"admin"},{role:"userAdminAnyDatabase",db:"admin"}]});
2、主从间的同步需要安全机制,所以需要先生成秘钥,yourKeyFile为秘钥文件名称,可以自定义
openssl rand -base64 753 > yourKeyFile 
3、将yourKeyFile放到MongoDB的数据存储路径下,也就是上面配置文件中的dbPath,上面的例子为/var/lib/mongo,并授权,注意你的秘钥存放路径。
chmod 600 yourKeyFile
4、拷贝yourKeyFile分别放到其他两台mongo服务器的数据存储路径下,也需要上面的600授权。
5、配置复制集和鉴权,还是上面的配置文件,yaml节点为securityreplication,三台机器都需要配置。
security:
  # 启用鉴权
  authorization: enabled
  # 你的keyFile存放路径
  keyFile: /var/lib/mongo/yourKeyfile
replication:
  # oplogSize的大小,单位为M,建议空闲磁盘的5%
  oplogSizeMB: 1024
  # 复制集的名称,需要记住
  replSetName: myReplSet
6、分别重启MongoDB服务,并进入master(192.168.1.207)

确认服务器的防火墙是否开放了相应的端口27017,如未开放,先开放

firewall-cmd --zone=public --add-port=27017/tcp --permanent
systemctl reload firewalld.service

若关闭Mongo时出现There doesn't seem to be a server running with dbpath: /data/db提示,则需指定数据库路径来关闭

mongod --shutdown --dbpath=/var/lib/mongo

连接后,由于开启了鉴权,所以需要认证

# 连接
mongo --port=27017
# 使用admin
use admin;
# 鉴权
db.auth('dba','yourpassword');

输入配置,这里的第一个_id需要和配置里面的replSetName一致

myReplSet_conf={
    _id: "myReplSet",
    members: [{
        _id: 0,
        host: "192.168.1.207:27017"
    }, {
        id: 1,
        host: "192.168.1.245:27017"
    }]
};

初始化

rs.initiate(myReplSet_conf);

若出现{ "ok" : 1}则表示配置成功,退出再重启则可以看到PRIMARY标识,在192.168.1.245登录,则看到的是SECONDARY

测试主从同步情况

登录主库(192.168.1.207),创建数据库,并创建用户,然后插入数据

# 连接
mongo --port=27017
# 使用admin
use admin;
# 鉴权
db.auth('dba','yourpassword');
# 创建数据库
use test;
# 创建用户
db.createUser({user:"testdba",pwd:"testpassword",roles:[{role:"dbOwner",db:"test"}]});
# 插入数据
db.testCol.insert({id:1,name:'zoro'});

登录从库(192.168.1.245),查询是否有主库插入的数据

# 连接
mongo --port=27017
# 使用test
use test;
# 鉴权
db.auth('testdba','testpassword');
# 允许读
rs.slaveOk();
# 查询
db.testCol.find();

如果有数据,则证明同步成功

实现master自动切换

MongoDB的复制集是有mater自动切换机制的,当集群中的master出现问题的时候,会由剩下的机器进行投票重新选举出master,但是,如果剩余活跃的机器是偶数个的话,比如现在只有两台/或一台,那将有可能陷入僵持,导致投票失败而没有master出现,这个时候,就需要配置一台MongoDB,作为仲裁角色加入集群(不做数据存储,只做为投票)。

1、启动最后一台mongo服务(192.168.1.249)
mongod -f /etc/mongod.conf
2、在主机上配置仲裁角色
# 连接
mongo --port=27017
# 使用admin
use admin;
# 鉴权
db.auth('dba','yourpassword');
# 加入仲裁角色
rs.addArb("192.168.1.249:27017");
3、查看复制集状态,以下为正常状态
{
    "set" : "myReplSet",
    "date" : ISODate("2018-05-25T09:46:12.137Z"),
    "myState" : 1,
    "term" : NumberLong(1),
    "heartbeatIntervalMillis" : NumberLong(2000),
    "optimes" : {
        "lastCommittedOpTime" : {
            "ts" : Timestamp(1527241561, 1),
            "t" : NumberLong(1)
        },
        "appliedOpTime" : {
            "ts" : Timestamp(1527241561, 1),
            "t" : NumberLong(1)
        },
        "durableOpTime" : {
            "ts" : Timestamp(1527241561, 1),
            "t" : NumberLong(1)
        }
    },
    "members" : [
        {
            "_id" : 0,
            "name" : "192.168.1.207:27017",
            "health" : 1,
            "state" : 1,
            "stateStr" : "PRIMARY",
            "uptime" : 1403,
            "optime" : {
                "ts" : Timestamp(1527241561, 1),
                "t" : NumberLong(1)
            },
            "optimeDate" : ISODate("2018-05-25T09:46:01Z"),
            "electionTime" : Timestamp(1527240420, 1),
            "electionDate" : ISODate("2018-05-25T09:27:00Z"),
            "configVersion" : 2,
            "self" : true
        },
        {
            "_id" : 1,
            "name" : "192.168.1.245:27017",
            "health" : 1,
            "state" : 2,
            "stateStr" : "SECONDARY",
            "uptime" : 1162,
            "optime" : {
                "ts" : Timestamp(1527241561, 1),
                "t" : NumberLong(1)
            },
            "optimeDurable" : {
                "ts" : Timestamp(1527241561, 1),
                "t" : NumberLong(1)
            },
            "optimeDate" : ISODate("2018-05-25T09:46:01Z"),
            "optimeDurableDate" : ISODate("2018-05-25T09:46:01Z"),
            "lastHeartbeat" : ISODate("2018-05-25T09:46:11.898Z"),
            "lastHeartbeatRecv" : ISODate("2018-05-25T09:46:11.913Z"),
            "pingMs" : NumberLong(0),
            "configVersion" : 2
        },
        {
            "_id" : 2,
            "name" : "192.168.1.249:27017",
            "health" : 1,
            "state" : 7,
            "stateStr" : "ARBITER",
            "uptime" : 10,
            "lastHeartbeat" : ISODate("2018-05-25T09:46:11.898Z"),
            "lastHeartbeatRecv" : ISODate("2018-05-25T09:46:11.930Z"),
            "pingMs" : NumberLong(0),
            "configVersion" : 2
        }
    ],
    "ok" : 1
}

测试是否能够自动切换master

先关闭master服务,然后进入原先secondary的服务,查看是否被提升成master,如果是,则测试成功。

注:切换会有延迟,示网络情况而定

SSM应用中配置读写分离

格子这边的应用是用java语言,基于SringMVC + Mybatis + mongoTemplate等框架的,下面说一下在这个框架下,如何配置MongoDB的读写分离。

配置文件,省略了其他,只列出mongo的关键配置

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:mvc="http://www.springframework.org/schema/mvc"
       xmlns:tx="http://www.springframework.org/schema/tx"
       xmlns:mongo="http://www.springframework.org/schema/data/mongo"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:task="http://www.springframework.org/schema/task" xmlns:dubbo="http://code.alibabatech.com/schema/dubbo"
       xmlns:aop="http://www.springframework.org/schema/aop"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/mvc
        http://www.springframework.org/schema/mvc/spring-mvc.xsd
        http://www.springframework.org/schema/data/mongo
        http://www.springframework.org/schema/data/mongo/spring-mongo.xsd
        http://www.springframework.org/schema/tx
        http://www.springframework.org/schema/tx/spring-tx.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/aop
        http://www.springframework.org/schema/aop/spring-aop.xsd
        http://www.springframework.org/schema/task
        http://www.springframework.org/schema/task/spring-task.xsd http://code.alibabatech.com/schema/dubbo http://code.alibabatech.com/schema/dubbo/dubbo.xsd">


    ...

   <!--mongo factory-->
   <mongo:db-factory id="mongoDbFactory" mongo-ref="mongoClient" dbname="${mongodb.database}"/>
   <!--mongo client config-->
   <mongo:mongo-client id="mongoClient" replica-set="${mongodb.host}:${mongodb.port}"
                        credentials="${mongodb.username}:${mongodb.password}@${mongodb.database}">
        <mongo:client-options
                connections-per-host="100"
                threads-allowed-to-block-for-connection-multiplier="10"
                connect-timeout="10000"
                max-wait-time="10000"
                socket-keep-alive="true"
                read-preference="SECONDARY_PREFERRED"
        />
    </mongo:mongo-client>
    
    ...

配置后开启MongoDB的日志,然后启动项目,并执行MongoDB响应的写入和读取操作,观察日志打印,就可以验证读写分离是否成功,是不是很简单呢。Spring家的东西还是蛮强大的。

写在最后

如果对你有帮助,帮格子点个赞呗。
溜了溜了。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 206,214评论 6 481
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 88,307评论 2 382
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 152,543评论 0 341
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 55,221评论 1 279
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 64,224评论 5 371
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,007评论 1 284
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,313评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,956评论 0 259
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 43,441评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,925评论 2 323
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,018评论 1 333
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,685评论 4 322
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,234评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,240评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,464评论 1 261
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,467评论 2 352
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,762评论 2 345

推荐阅读更多精彩内容

  • 由于vue官网教程提示使用webpack来开发vue,所以就入坑了。官网代码如下: 官网在输入命令 vue ini...
    孤独花园阅读 1,659评论 0 1
  • 清风拂面 月色撩人 不及你眉梢的容颜 黑夜如此幽静 风月笙歌 扰人梦 夜色苍茫 繁星璀璨 不及你含笑的明眸 城市异...
    海水微凉浅喜深爱阅读 377评论 2 3
  • 今年我大三了,有一票哥们,一个女朋友,在校外租了个挺不错的房子,准备考研,日子过得算是不错。 但好景不长,女朋友最...
    村头小撸阅读 938评论 0 1
  • 冬天不知不觉过去,虫醒了,猫叫了,树儿发芽了,胃口大开。 早春的荠菜,带有浓郁而独特的香味,与任何菜相搭都出彩,因...
    梦蓝砂阅读 618评论 16 2
  • 深夜不睡就容易东想西想。前天晚上逃课去看了春娇救志明,晚上到学校九点多。 2010年到2017年,八年的荧幕情侣也...
    落叶满街红不扫阅读 245评论 0 0