1. 程式人生 > >MongoDB之分片

MongoDB之分片

索引 第一篇 csdn 屬性 collect sso factor mar popu

本文介紹分片的思想和MongoDB中的實現方法。


首先須要介紹一些主要的概念。


分片

分片。也叫做分區。是一種經常使用的數據庫優化技術。其含義就是將數據拆分,將數據分散到不同機器上的過程。這樣就能夠使得系統能夠存儲很多其它的數據,處於更大的負載。
差點兒全部的數據庫軟件都能夠進行手動分片,通過應用程序管理不同server上的不同數據,查詢也須要尋找正確的server。這樣盡管能夠減輕負載,可是卻難以維護,比方我們向集群加入節點或者刪除節點。都須要相應的調整數據的分布。
MongoDB在這一點上做得不錯,它支持自己主動分片,集群能夠自己主動切分數據,達到負載均衡,從而使管理人員能夠擺脫手動分片。


分片原理

以下說說分片的原理。MongoDB分片的基本思想就是將集合切分成小塊,這些塊分散到若幹片裏面。每一個片僅僅負責總數據的一部分。


應用程序不須要知道哪些片相應哪些數據,也不須要知道數據是否已經拆分

MongoDB通過另外一個獨立的路由進程mongos來實現這個功能。


mongos路由進程知道全部數據的存放位置,所以應用能夠連接它來正常發送請求。而對於應用來說。自己僅僅知道連接了一個普通的mongod。

也就是說,mongos相應用隱藏了分片的細節
為什麽要隱藏了?事實上就是為了拓展的時候,不必改動應用程序的代碼。

應用場景

說完了原理。那什麽時候須要用到分片

呢?有以下幾種情況:
1. 機器的磁盤不夠用了
2. 單個mongodb已經不再滿足性能須要
3. 想將大量數據放入內存提高性能

一般來說,先從不分片開始。然後在須要的時候將其轉換成分片。

片鍵

設置分片時,須要從集合裏面選一個鍵,用該鍵的值作為數據拆分的根據。這個鍵成為片鍵


假設有個文檔集合表示的是人員,假設選擇名字”name”做為片鍵,第一篇可能會存放名字以A-F開頭的文檔;第二片存G-P開頭的文檔;第三篇存Q-Z的文檔。


隨著添加或刪除片,MongoDB會又一次平衡數據,使得每片的流量比較均衡,數據量也在合理範圍內。

那麽我們應該怎樣選擇片鍵呢?
假設我們選擇了時間屬性的鍵作為片鍵。那麽隨著時間增長。全部的文檔都會以最後一片插入。這就不適合寫入操作負載非常高的情況,可是查詢起來就比較方便。


假設我們選擇了分布均勻的片鍵,就會提高寫入操作的負載能力,可是就會影響查詢的性能。
我們也能夠選擇復合片鍵,將兩個屬性鍵結合為一個片鍵。
事實上和索引的原理類似,事實上,片鍵也是最經常使用的索引。

說了半天的概率,也累了,以下看看實際操作吧。


建立分片

建立分片有兩步:啟動server,然後決定怎麽切分數據。


分片一般由三個部分組成:
1.
片就是保存子集合數據的容器。片能夠是單個mongodserver。也能夠是副本集。


2. mongos
路由進程,它接收全部的請求。然後將結果聚合,它本身並不存儲數據或者配置信息,可是會緩存配置server的信息。


3. 配置server
存儲集群的配置信息:數據和片的相應關系。

配置server是幫mongos存放分片的配置信息的,mongos自己不存放數據。直接同步配置server中數據就可以。

以下介紹具體過程:

首先要啟動配置server和mongos。
配置server須要先啟動,由於mongos會用到其上的配置信息。


第一步,啟動配置server

配置server的啟動就像普通的mongod一樣:

mongod – config d:\mongodb\mongo.config --port 20000

技術分享


第二步,建立mongos進程

建立mongos進程。以供應用程序連接。這樣的路由server連接數據文件夾都不須要,但一定要指明配置server的位置:

mongos --port 30000 --configdb 127.0.0.1:20000

技術分享

分片管理一般是通過mongos完畢的,完畢後效果例如以下:
技術分享


第三步,加入片

加入片。片就是普通的mongod:
技術分享
技術分享
連接剛才啟動的mongos,為集群加入一個片。


啟動shell,連接mongos:
確定連接的是mongos而不是mongod,通過addshard命令加入片:

>mongo 127.0.0.1:30000
mongos> use admin
switched to db admin
mongos> db.runCommand(
... {
... "addshard":"127.0.0.1:10000",
... "allowLocal":1
... }
... )
{ "shardAdded" : "shard0000", "ok" : 1 }
mongos> db.runCommand(
... {
... "addshard":"127.0.0.1:10001",
... "allowLocal":1
... }
... )
{ "shardAdded" : "shard0001", "ok" : 1 }

技術分享
技術分享
技術分享

當在本機執行片的時候,得設定allowLocal鍵為true。MongoDB盡量避免由於錯誤的配置,將集群配置到本地,所以得讓它知道這僅僅是開發,並且我們非常清楚自己在做什麽。


假設是生產環境中,則要將其部署在不同的機器上。


想加入片的時候,就執行addshard,MongoDB會負責將片集成到集群


第四步,切分數據

MongoDB不會將存儲的每一條數據都直接公布,得先在數據庫和集合的級別將分片功能打開。
假設是連接配置server,

E:\mongo\bin>mongo 127.0.0.1:20000
MongoDB shell version: 2.0.6
connecting to: 127.0.0.1:20000/test
> use admin
switched to db admin
> db.runCommand({"enablesharding":"test"})
{
"errmsg" : "no such cmd: enablesharding",
"bad cmd" : {
"enablesharding" : "test"
},
"ok" : 0
}

技術分享

應該是連接路由server,

db.runCommand({"enablesharding":"test"})//將test數據庫啟用分片功能.

對數據庫分片後,其內部的集合便會存儲到不同的片上,同一時候也是對這些集合分片的前置條件。
在數據庫級別啟用了分片以後,就能夠使用shardcollection命令堆積和進行分片:

db.runCommand({"shardcollection":"test.refactor","key":{"name":1}})//對test數據庫的lf集合進行分片,片鍵是name

假設如今對lf集合加入數據,就會根據”name”的值自己主動分散到各個片上。

這樣分片就建立完畢啦!


管理分片

分片建立完畢後,怎樣管理分片呢?
分片信息主要存放在config數據庫上,這樣就能被不論什麽連接到mongos的進程訪問到了。
在shell中連接了mongos,並使用了use config數據庫。

查看分片
通過db.shards.find()方法:
技術分享

查看狀態
db.printShardingStatus()
技術分享

刪除分片

db.runCommand({"removeshard":"127.0.0.1:10001"})

MongoDB之分片