MongoDB入門教程04

注:本系列教程是自己學(xué)習(xí)的記錄轧坎,內(nèi)容來至 菜鳥教程
MongoDB入門教程01
MongoDB入門教程02
MongoDB入門教程03
MongoDB入門教程04
MongoDB入門教程05

1. MongoDB聚合

MongoDB中聚合(aggregate)主要用于處理數(shù)據(jù)(諸如統(tǒng)計平均值,求和等)泽示,并返回計算后的數(shù)據(jù)結(jié)果缸血。

aggregate()方法

語法

> db.COLLECTION_NAME.aggregate(AGGREGATE_OPERATION)

實例

集合中的數(shù)據(jù)如下:

{
 "_id" : ObjectId("5aefc46e58072d466fd8277e"),
 "title" : "MongoDB Overview",
 "description" : "MongoDB is no sql database",
 "by_user" : "runoob.com",
 "url" : "http://www.runoob.com",
 "tags" : [ 
 "mongodb", 
 "database", 
 "NoSQL"
 ],
 "likes" : 100.0
},
{
 "_id" : ObjectId("5aefc46e58072d466fd8277f"),
 "title" : "NoSQL Overview",
 "description" : "No sql database is very fast",
 "by_user" : "runoob.com",
 "url" : "http://www.runoob.com",
 "tags" : [ 
 "mongodb", 
 "database", 
 "NoSQL"
 ],
 "likes" : 10.0
},
{
 "_id" : ObjectId("5aefc46e58072d466fd82780"),
 "title" : "Neo4j Overview",
 "description" : "Neo4j is no sql database",
 "by_user" : "Neo4j",
 "url" : "http://www.neo4j.com",
 "tags" : [ 
 "neo4j", 
 "database", 
 "NoSQL"
 ],
 "likes" : 750.0
}

統(tǒng)計以上集合中每個作者所寫的文章數(shù),使用aggregate()計算結(jié)果如下:

> db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$sum : 1}}}])
{
 "result" : [
 {
 "_id" : "runoob.com",
 "num_tutorial" : 2
 },
 {
 "_id" : "Neo4j",
 "num_tutorial" : 1
 }
 ],
 "ok" : 1
}

類似SQL: select by_user, count(*) from mycol group by by_user

下表展示了一些聚合的表達(dá)式:

表達(dá)式 描述 實例
$sum 計算總和 db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$sum: "$likes"}}}])
$avg 計算平均值 db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$avg : "$likes"}}}])
$min 獲取集合中所有文檔對應(yīng)值得最小值械筛。 db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$min : "$likes"}}}])
$max 獲取集合中所有文檔對應(yīng)值得最大值捎泻。 db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$max : "$likes"}}}])
$push 在結(jié)果文檔中插入值到一個數(shù)組中。 db.mycol.aggregate([{$group : {_id : "$by_user", url : {$push: "$url"}}}])
$addToSet 在結(jié)果文檔中插入值到一個數(shù)組中埋哟,但不創(chuàng)建副本笆豁。 db.mycol.aggregate([{$group : {_id : "$by_user", url : {$addToSet : "$url"}}}])
$first 根據(jù)資源文檔的排序獲取第一個文檔數(shù)據(jù)。 db.mycol.aggregate([{$group : {_id : "$by_user", first_url : {$first : "$url"}}}])
$last 根據(jù)資源文檔的排序獲取最后一個文檔數(shù)據(jù) db.mycol.aggregate([{$group : {_id : "$by_user", last_url : {$last :"$url"}}}])

管道的概念

管道在Unix和Linux中一般用于將當(dāng)前命令的輸出結(jié)果作為下一個命令的參數(shù)赤赊。

MongoDB的聚合管道將MongoDB文檔在一個管道處理完畢后將結(jié)果傳遞給下一個管道處理闯狱。管道操作是可以重復(fù)的。

表達(dá)式:處理輸入文檔并輸出抛计。表達(dá)式是無狀態(tài)的哄孤,只能用于計算當(dāng)前聚合管道的文檔,不能處理其它的文檔吹截。

聚合框架中常用的幾個操作:

  • $project:修改輸入文檔的結(jié)構(gòu)瘦陈∧#可以用來重命名、增加或刪除域晨逝,也可以用于創(chuàng)建計算結(jié)果以及嵌套文檔蛾默。
  • $match: 用以過濾數(shù)據(jù),只輸出滿足條件的文檔捉貌,match使用MongoDB的標(biāo)準(zhǔn)查詢操作支鸡。
  • $limit:用來限制MongoDB聚合管道返回的文檔數(shù)。
  • $skip:在聚合管道中跳過指定數(shù)量的文檔趁窃,并返回余下的文檔苍匆。
  • $unwind:將文檔中的某一個數(shù)組類型字段拆分成多條,每條包含數(shù)組中的一個值棚菊。
  • $group:將集合中的文檔分組,可用于統(tǒng)計結(jié)果叔汁。
  • $sort:將輸入文檔排序后輸出统求。
  • $geoNear:輸出接近某一地理位置的有序文檔。

管道操作符實例

  1. $project實例
> db.article.aggregate({ $project : { title : 1,  author : 1 }})

這樣的話結(jié)果中就只還有_id, tilteauthor三個字段了据块,默認(rèn)情況下_id字段是被包含的码邻,如果要想不包含_id話可以這樣:

> db.article.aggregate( { $project : {_id : 0 , title : 1,author : 1}})
  1. $match實例
>db.articles.aggregate( [
 { $match : { score : { $gt : 70, $lte : 90 } } },
 { $group: { _id: null, count: { $sum: 1 } } }
 ] )

match 用以篩選分?jǐn)?shù)大于70小于等于90的記錄,將符合條件的記錄送入group管道操作符進(jìn)行處理另假。

  1. $skip實例
> db.article.aggregate({ $skip : 5 });

經(jīng)過$skip管道操作符處理后像屋,前五個文檔被"過濾"掉。

2. MongoDB 復(fù)制(副本集)

MongoDB復(fù)制是將數(shù)據(jù)同步在多個服務(wù)器上的過程边篮。
復(fù)制提供了數(shù)據(jù)的冗余備份己莺,并在多個服務(wù)器上存儲數(shù)據(jù)副本,提高了數(shù)據(jù)的可用性戈轿,并可以保證數(shù)據(jù)的安全性凌受。
復(fù)制還允許您從硬件故障和服務(wù)中斷中恢復(fù)數(shù)據(jù)。


什么是復(fù)制?

  • 保障數(shù)據(jù)的安全性
  • 數(shù)據(jù)高可用性 (24*7)
  • 災(zāi)難恢復(fù)
  • 無需停機維護(hù)(如備份思杯,重建索引胜蛉,壓縮)
  • 分布式讀取數(shù)據(jù)

MongoDB 復(fù)制原理

mongodb的復(fù)制至少需要兩個節(jié)點。其中一個是主節(jié)點色乾,負(fù)責(zé)處理客戶端請求誊册,其余的都是從節(jié)點,負(fù)責(zé)復(fù)制主節(jié)點上的數(shù)據(jù)暖璧。

mongodb各個節(jié)點常見的搭配方式為:一主一從案怯、一主多從。主節(jié)點記錄在其上的所有操作oplog澎办,從節(jié)點定期輪詢主節(jié)點獲取這些操作殴泰,然后對自己的數(shù)據(jù)副本執(zhí)行這些操作于宙,從而保證從節(jié)點的數(shù)據(jù)與主節(jié)點一致。

副本集特征

  • N個節(jié)點的集群
  • 任何節(jié)點可作為主節(jié)點
  • 所有寫入操作都在主節(jié)點上
  • 自動故障轉(zhuǎn)移
  • 自動恢復(fù)
讀寫分離:主節(jié)點負(fù)責(zé)寫入悍汛,子節(jié)點負(fù)責(zé)讀取捞魁,從而實現(xiàn)讀寫分離
試驗參考:參考

3. MongoDB 分片

分片

在MongoDB里存在另一種集群,可以滿足MongoDB數(shù)據(jù)量大量增長的需求离咐。
當(dāng)MongoDB存儲海量的數(shù)據(jù)時谱俭,一臺機器可能不足以存儲數(shù)據(jù),也可能不足以提供可接受的讀寫吞吐量宵蛀。這時昆著,我們就可以通過在多臺機器上分割數(shù)據(jù),使得數(shù)據(jù)庫系統(tǒng)能存儲和處理更多的數(shù)據(jù)术陶。

為什么使用分片

  • 復(fù)制所有的寫入操作到主節(jié)點
  • 延遲的敏感數(shù)據(jù)會在主節(jié)點查詢
  • 單個副本集限制在12個節(jié)點
  • 當(dāng)請求量巨大時會出現(xiàn)內(nèi)存不足凑懂。
  • 本地磁盤不足
  • 垂直擴展價格昂貴

MongoDB分片

下圖展示了在MongoDB中使用分片集群結(jié)構(gòu)分布:

集群分布結(jié)構(gòu)

上圖中主要有如下所述三個主要組件:

  • Shard: 用于存儲實際的數(shù)據(jù)塊,實際生產(chǎn)環(huán)境中一個shard server角色可由幾臺機器組個一個replica set承擔(dān)梧宫,防止主機單點故障
  • Config Server: mongod實例接谨,存儲了整個 ClusterMetadata,其中包括 chunk信息塘匣。
  • Query Routers: 前端路由脓豪,客戶端由此接入,且讓整個集群看上去像單一數(shù)據(jù)庫忌卤,前端應(yīng)用可以透明使用扫夜。

Mongos

MongoDB分片的基本思想就是將集合切分成小塊.這些塊分散到若干片里面,每個片只負(fù)責(zé)總數(shù)據(jù)的一部分。應(yīng)用程序不必知道哪片對應(yīng)哪些數(shù)據(jù)驰徊,甚至不需要知道數(shù)據(jù)已經(jīng)被拆分了笤闯,所以在分片之前要運行一個路由進(jìn)程,進(jìn)程名mongos棍厂,這個路由器知道所有數(shù)據(jù)的存放位置望侈,所以應(yīng)用可以連接它來正常發(fā)送請求.對應(yīng)用來說,它僅知道連接了一個普通的mongod勋桶。路由器知道和片的對應(yīng)關(guān)系,能夠轉(zhuǎn)發(fā)請求到正確的片上脱衙。如果請求有了回應(yīng),路由器將其收集起來回送給應(yīng)用例驹。

在沒有分片的時候捐韩,客戶端連接mongod進(jìn)程,分片時客戶端會連接mongos進(jìn)程鹃锈。mongos對應(yīng)用隱藏了分片的細(xì)節(jié)荤胁。從應(yīng)用的角度看,分片和不分片沒有區(qū)別屎债。所以需要擴展的時候仅政,不必修改應(yīng)用程序的代碼垢油。

健壯的片

生產(chǎn)環(huán)境中,每個片都應(yīng)是副本集,這樣單個服務(wù)器壞了,就不會導(dǎo)致整個片失效.用addshard命令就可以將副本集作為片添加,
添加時,只要指定副本集的名稱和種子就行了.
如要添加副本集圆丹,其中包含一個服務(wù)器127.0.0.1:27020(還有別的服務(wù)器),就可以用下列命令將其添加到集群中

>$ mongo localhost:40000
> use admin
> db.runCommand({ addshard: 'rs0/localhost:27020,localhost:27021'})
> db.runCommand({ addshard: 'rs1/localhost:27030,localhost:27031'})
> db.runCommand({ enablesharding: 'test'})   # 設(shè)置分片數(shù)據(jù)庫
> db.runCommand({ shardcollection: 'test.user', key: {name: 1}})

操作參考

4. MongoDB 備份(mongodump)與恢復(fù)(mongorestore)


1. MongoDB數(shù)據(jù)備份

語法

mongodump命令腳本語法如下:

> mongodump -h dbhost -d dbname -o dbdirectory
  • -h: MongDB所在服務(wù)器地址滩愁,例如:127.0.0.1,當(dāng)然也可以指定端口號:127.0.0.1:27017
  • -d: 需要備份的數(shù)據(jù)庫實例辫封,例如:test
  • -o: 備份的數(shù)據(jù)存放位置硝枉,例如:c:\data\dump,當(dāng)然該目錄需要提前建立倦微,在備份完成后妻味,系統(tǒng)自動在dump目錄下建立一個test目錄,這個目錄里面存放該數(shù)據(jù)庫實例的備份數(shù)據(jù)欣福,導(dǎo)出文件格式為 BSON 和 JSON

mongodump 命令可選參數(shù)列表如下所示:

語法 描述 實例
mongodump --host HOST_NAME --port PORT_NUMBER 該命令將備份所有MongoDB數(shù)據(jù) mongodump --host runoob.com --port 27017
mongodump --dbpath DB_PATH --out BACKUP_DIRECTORY 該命令將數(shù)據(jù)庫導(dǎo)出到指定文件夾 mongodump --dbpath /data/db/ --out /data/backup/
mongodump --collection COLLECTION --db DB_NAME 該命令將備份指定數(shù)據(jù)庫的集合责球。 mongodump --collection mycol --db test

2. MongoDB數(shù)據(jù)恢復(fù)

mongodb使用 mongorestore 命令來恢復(fù)備份的數(shù)據(jù)。

語法

mongorestore命令腳本語法如下:

> mongorestore -h <hostname><:port> -d dbname <path>
  • --host <:port>, -h <:port>: MongoDB所在服務(wù)器地址拓劝,默認(rèn)為: localhost:27017

  • --db, -d: 需要恢復(fù)的數(shù)據(jù)庫實例雏逾,例如:test,當(dāng)然這個名稱也可以和備份時候的不一樣凿将,比如test2

  • --drop: 恢復(fù)的時候,先刪除當(dāng)前數(shù)據(jù)价脾,然后恢復(fù)備份的數(shù)據(jù)牧抵。就是說,恢復(fù)后侨把,備份后添加修改的數(shù)據(jù)都會被刪除犀变,慎用哦!

  • path: mongorestore 最后的一個參數(shù)秋柄,設(shè)置備份數(shù)據(jù)所在位置获枝,例如:c:\data\dump\test。你不能同時指定 <path> 和 --dir 選項骇笔,--dir也可以設(shè)置備份目錄省店。

  • --dir: 指定備份的目錄你不能同時指定 <path> 和 --dir 選項。

5. MongoDB 監(jiān)控


mongostat 命令

它會間隔固定時間獲取mongodb的當(dāng)前運行狀態(tài)笨触,并輸出懦傍。

mongotop 命令

mongotop提供了一個方法,用來跟蹤一個MongoDB的實例芦劣,查看哪些大量的時間花費在讀取和寫入數(shù)據(jù)粗俱。 mongotop提供每個集合的水平的統(tǒng)計數(shù)據(jù)。默認(rèn)情況下虚吟,mongotop返回值的每一秒

> mongotop <sleeptime> —locks

輸出結(jié)果字段說明:

  • ns: 包含數(shù)據(jù)庫命名空間寸认,后者結(jié)合了數(shù)據(jù)庫名稱和集合签财。
  • db: 包含數(shù)據(jù)庫的名稱。名為 . 的數(shù)據(jù)庫針對全局鎖定偏塞,而非特定數(shù)據(jù)庫唱蒸。
  • total: mongod花費的時間工作在這個命名空間提供總額。
  • read: 提供了大量的時間烛愧,這mongod花費在執(zhí)行讀操作油宜,在此命名空間。
  • write: 提供這個命名空間進(jìn)行寫操作怜姿,這mongod花了大量的時間慎冤。
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市沧卢,隨后出現(xiàn)的幾起案子蚁堤,更是在濱河造成了極大的恐慌,老刑警劉巖但狭,帶你破解...
    沈念sama閱讀 206,311評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件披诗,死亡現(xiàn)場離奇詭異,居然都是意外死亡立磁,警方通過查閱死者的電腦和手機呈队,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,339評論 2 382
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來唱歧,“玉大人宪摧,你說我怎么就攤上這事÷溃” “怎么了几于?”我有些...
    開封第一講書人閱讀 152,671評論 0 342
  • 文/不壞的土叔 我叫張陵,是天一觀的道長沿后。 經(jīng)常有香客問我沿彭,道長,這世上最難降的妖魔是什么尖滚? 我笑而不...
    開封第一講書人閱讀 55,252評論 1 279
  • 正文 為了忘掉前任喉刘,我火速辦了婚禮,結(jié)果婚禮上漆弄,老公的妹妹穿的比我還像新娘饱搏。我一直安慰自己,他們只是感情好置逻,可當(dāng)我...
    茶點故事閱讀 64,253評論 5 371
  • 文/花漫 我一把揭開白布推沸。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪鬓催。 梳的紋絲不亂的頭發(fā)上肺素,一...
    開封第一講書人閱讀 49,031評論 1 285
  • 那天,我揣著相機與錄音宇驾,去河邊找鬼倍靡。 笑死,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播掰邢,決...
    沈念sama閱讀 38,340評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼捡需!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起筹淫,我...
    開封第一講書人閱讀 36,973評論 0 259
  • 序言:老撾萬榮一對情侶失蹤站辉,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后损姜,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體饰剥,經(jīng)...
    沈念sama閱讀 43,466評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 35,937評論 2 323
  • 正文 我和宋清朗相戀三年摧阅,在試婚紗的時候發(fā)現(xiàn)自己被綠了汰蓉。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 38,039評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡棒卷,死狀恐怖顾孽,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情娇跟,我是刑警寧澤岩齿,帶...
    沈念sama閱讀 33,701評論 4 323
  • 正文 年R本政府宣布太颤,位于F島的核電站苞俘,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏龄章。R本人自食惡果不足惜吃谣,卻給世界環(huán)境...
    茶點故事閱讀 39,254評論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望做裙。 院中可真熱鬧岗憋,春花似錦、人聲如沸锚贱。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,259評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至监徘,卻和暖如春晋修,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背凰盔。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工墓卦, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人户敬。 一個月前我還...
    沈念sama閱讀 45,497評論 2 354
  • 正文 我出身青樓落剪,卻偏偏與公主長得像,于是被迫代替她去往敵國和親尿庐。 傳聞我的和親對象是個殘疾皇子忠怖,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 42,786評論 2 345

推薦閱讀更多精彩內(nèi)容