MongoDB副本集

簡介html

       mongodb複製(replication)是將數據同步在多個服務器的過程。主節點記錄在其上的全部操做oplog,從節點按期輪詢主節點獲取這些操做,而後對本身的數據副本執行這些操做,從而保證從節點的數據與主節點一致。複製提供了數據的冗餘備份,並在多個服務器上存儲數據副本,提升了數據的可用性,並保證數據的安全性。複製還容許您從硬件故障和服務中斷中恢復數據。linux

       而副本集(replica set)是從mongodb 1.6 提供的新功能,比複製功能要強大一些並增長了故障自動切換和自動修復成員節點,各個DB之間數據徹底一致。Replica Sets的結構相似一個集羣,徹底能夠把它當成一個集羣,由於它確實與集羣實現的做用是同樣的,若是其中一個節點出現故障,其餘節點立刻回將業務接管過來而無需停機操做。sql

  提示:關於mongodb相關核心理論知識,建議去看對應的文檔以及書籍,我這裏就不作對應的介紹(由於理論的東西寫起來太費勁)。mongodb

安裝shell

提示:本環境爲3臺主機的環境,IP分別爲192.168.58.128(PRIMARY)、192.168.58.129(SECONDARY)、192.168.58.130(ARBITER);數據庫

1、安裝mongodb安全

1.1 安裝mongodbbash

下載:https://www.mongodb.org/dl/linux/x86_64-rhel70;服務器

mkdir /data
tar zxf mongodb-linux-x86_64-rhel70-3.2.0.tgz 
mv mongodb-linux-x86_64-rhel70-3.2.0 /data/mongodb-3.2.0
mkdir /data/mongodb-3.2.0/{data,conf,logs}

1.2 配置mongodbapp

首先關閉透明頁面,自CentOS6版本開始引入了Transparent Huge Pages(THP),從CentOS7版本開始,該特性默認就會啓用。儘管THP的本意是爲提高內存的性能,不過某些數據庫廠商仍是建議直接關閉THP(好比Redis和MongoDB等),不然可能會致使性能出現降低。

# 查看是否啓用

[root@localhost ~]# cat /sys/kernel/mm/transparent_hugepage/defrag
[always] madvise never
[root@localhost ~]# cat /sys/kernel/mm/transparent_hugepage/enabled
[always] madvise never

# 禁用HTP功能

將如下內容加入到"/etc/rc.d/rc.local"文件中,記得執行"chmod +x /etc/rc.d/rc.local"。

# disable THP(Transparent Huge Pages)
echo never >> /sys/kernel/mm/transparent_hugepage/enabled
echo never >> /sys/kernel/mm/transparent_hugepage/defrag

# 建立keyfile文件

openssl rand -base64 756 > /data/mongodb-3.2.0/conf/mongodb_authkey
chmod 600 /data/mongodb-3.2.0/conf/mongodb_authkey
scp /data/mongodb-3.2.0/conf/mongodb_authkey 192.168.58.129:/data/mongodb-3.2.0/conf/
scp /data/mongodb-3.2.0/conf/mongodb_authkey 192.168.58.130:/data/mongodb-3.2.0/conf/

提示:

  keyfile文件是副本集不可缺乏的,他們之間的通訊依賴於此。不過我在測試yum安裝的時候,彷佛不須要該配置,然而在二進制安裝的時候,若是缺乏keyfile就提示認證失敗。

# 配置mongodb配置文件

[root@localhost ~]# cat /data/mongodb-3.2.0/conf/mongodb.conf 
bind_ip=192.168.58.128
port=5336
dbpath=/data/mongodb-3.2.0/data
logpath=/data/mongodb-3.2.0/logs/mongodb.logs
logappend=true
replSet=mongodb01
fork=true
auth=true
directoryperdb=true
maxConns=8000
cpu=true
oplogSize=8000

提示:建議先關閉"auth=true"參數以及禁用掉keyFile,由於若是開啓該配置項在初次添加副本集的過程當中,須要進行相關認證。可是,此時你並無相關用戶和密碼,致使你沒法經過mongodb認證。若是不由用,就會出現以下錯誤:

> db.createUser({
...   user: "admin",
...   pwd: "123456",
...   roles: [{
...     role: "userAdminAnyDatabase",
...     db: "admin"
...   }]
... })
2017-10-11T17:17:19.247+0800 E QUERY    [thread1] Error: couldn't add user: not authorized on admin to execute command { createUser: "admin", pwd: "xxx", roles: [ { role: "userAdminAnyDatabase", db: "admin" } ], digestPassword: false, writeConcern: { w: "majority", wtimeout: 30000.0 } } :
_getErrorWithCode@src/mongo/shell/utils.js:23:13
DB.prototype.createUser@src/mongo/shell/db.js:1225:11

因此先禁止掉該參數並在添加完新用戶以後再開啓認證功能。在其中一臺關閉就行,我這裏選擇在192.168.58.128(PRIMARY)主機上操做。

1.3 啓動mongodb

/data/mongodb-3.2.0/bin/mongod -f /data/mongodb-3.2.0/conf/mongodb.conf

 3、配置副本集

3.1 建立一個管理用戶

/data/mongodb-3.2.0/bin/mongo 192.168.58.128:5336
> rs.initiate()
{
	"info2" : "no configuration specified. Using a default configuration for the set",
	"me" : "192.168.58.128:5336",
	"ok" : 1
}
mongodb01:OTHER> db.createUser(  
   {  
     user: "admin",  
     pwd: "admin@123",  
     roles: [ { role: "root", db: "admin" } ]  
   }  
) 
mongodb01:PRIMARY> exit

3.2 開啓用戶認證並重啓服務

提示:在平常維護過程當中,mongodb關閉建議使用kill -2而不該該使用kill -9。

3.3 配置mongodb副本集

/data/mongodb-3.2.0/bin/mongo 192.168.58.128:5336 -u admin -p --authenticationDatabase admin

# 添加副本集

mongodb01:PRIMARY> show dbs
admin 0.000GB
local 0.000GB
mongodb01:PRIMARY> rs.add("192.168.58.129:5336")
mongodb01:PRIMARY> rs.addArb("192.168.58.130:5336")
mongodb01:PRIMARY> rs.status()

# 測試複製

在插入數據

for(var i=0;i<100000;i++)db.test.insert({title: 'MongoDB 教程'+i, 
     description: 'MongoDB 是一個 Nosql 數據庫'+i,
     by: '菜鳥教程'+i,
     url: 'http://www.runoob.com',
     tags: ['mongodb', 'database', 'NoSQL'],
     likes: 100
 })

在PRIMARY和SECONDARY查看數據是否一致  

db.test.count()

# 測試切換

kill 掉PRIMARY,並在SECONDARY查看狀態

mongodb01:PRIMARY> rs.status()
{
	"set" : "mongodb01",
	"date" : ISODate("2017-09-20T02:15:23.819Z"),
	"myState" : 1,
	"term" : NumberLong(3),
	"heartbeatIntervalMillis" : NumberLong(2000),
	"members" : [
		{
			"_id" : 0,
			"name" : "192.168.58.128:5336",
			"health" : 0,
			"state" : 8,
			"stateStr" : "(not reachable/healthy)",
			"uptime" : 0,
			"optime" : {
				"ts" : Timestamp(0, 0),
				"t" : NumberLong(-1)
			},
			"optimeDate" : ISODate("1970-01-01T00:00:00Z"),
			"lastHeartbeat" : ISODate("2017-09-20T02:15:21.902Z"),
			"lastHeartbeatRecv" : ISODate("2017-09-20T02:01:16.163Z"),
			"pingMs" : NumberLong(0),
			"lastHeartbeatMessage" : "Connection refused",
			"configVersion" : -1
		},
		{
			"_id" : 1,
			"name" : "192.168.58.129:5336",
			"health" : 1,
			"state" : 1,
			"stateStr" : "PRIMARY",
			"uptime" : 69990,
			"optime" : {
				"ts" : Timestamp(1505872886, 2),
				"t" : NumberLong(3)
			},
			"optimeDate" : ISODate("2017-09-20T02:01:26Z"),
			"electionTime" : Timestamp(1505872886, 1),
			"electionDate" : ISODate("2017-09-20T02:01:26Z"),
			"configVersion" : 3,
			"self" : true
		},
		{
			"_id" : 2,
			"name" : "192.168.58.130:5336",
			"health" : 1,
			"state" : 7,
			"stateStr" : "ARBITER",
			"uptime" : 69615,
			"lastHeartbeat" : ISODate("2017-09-20T02:15:23.303Z"),
			"lastHeartbeatRecv" : ISODate("2017-09-20T02:15:21.905Z"),
			"pingMs" : NumberLong(0),
			"configVersion" : 3
		}
	],
	"ok" : 1
}

能夠看到原 SECONDARY 已經變爲 PRIMARY。此時咱們在向該PRIMARY插入數據;

mongodb01:PRIMARY> for(var i=0;i<100000;i++)db.test.insert({title: 'MongoDB 教程'+i, 
     description: 'MySQL 是一個 關係型數據庫'+i,
     by: '菜鳥教程'+i,
     url: 'http://www.runoob.com',
     tags: ['MySQL', 'database', 'SQL'],
     likes: 100
 })

重啓剛kill掉的 "PRIMARY",查看數據是否同步

mongodb01:SECONDARY> db.getMongo().setSlaveOk()
mongodb01:SECONDARY> db.test.count()
200000

       最後,在給一些在生產環境中的建議,當某個節點宕機後從新啓動該節點會有一段的時間(時間長短視集羣的數據量和宕機時間而定)致使整個集羣中全部節點都成爲secondary而沒法進行寫操做(若是應用程序沒有設置相應的ReadReference也可能不能進行讀取操做)。

  所以官方推薦的最小的副本集也應該具有一個primary節點和兩個secondary節點。兩個節點的副本集不具有真正的故障轉移能力。

  最後的最後,MongoDB相關文章,參考http://www.cnblogs.com/zhanjindong/p/3268963.html,文章至關不錯。

相關文章
相關標籤/搜索