#轉帖#MongoDB的基本特性與內部構造


MongoDB是一個介於關係數據庫和非關係數據庫之間的產品,是非關係數據庫當中功能最豐富,最像關係數據庫的。他支持的數據結構很是鬆散,是相似json的bjson格式,所以能夠存儲比較複雜的數據類型。Mongo最大的特色是他支持的查詢語言很是強大,其語法有點相似於面向對象的查詢語言,幾乎能夠實現相似關係數據庫單表查詢的絕大部分功能,並且還支持對數據創建索引。

對於大多數的MongoDB的用戶來講,MongoDB就像是一個大黑盒。可是若是你可以瞭解到MongoDB一些內部構造的話,將有利於你更好地理解和使用MongoDB。


BSON
在MongoDB中,文檔是對數據的抽象,它被使用在Client端和Server端的交互中。全部的Client端(各類語言的Driver)都會使用這種抽象,它的表現形式就是咱們常說的BSON(Binary JSON)。

BSON 是一個輕量級的二進制數據格式。MongoDB可以使用BSON,並將BSON做爲數據的存儲存放在磁盤中。

當Client端要將寫入文檔,使用查詢等操做時,須要將文檔編碼爲BSON格式,而後再發送給Server端。一樣,Server端的返回結果也是編碼爲BSON格式再返回給Client端的。

使用BSON格式出於如下3種目的:

效率。BSON是爲效率而設計的,它只須要使用不多的空間。即便在最壞的狀況下,BSON格式也比JSON格式在最好的狀況下存儲效率高。

傳輸性。在某些狀況下,BSON會犧牲額外的空間讓數據的傳輸更加方便。好比,字符串的傳輸的前綴會標識字符串的長度,而不是在字符串的末尾打上結束的標記。這樣的傳輸形式有利於MongoDB修改傳輸的數據。

性能。最後,BSON格式的編碼和解碼都是很是快速的。它使用了C風格的數據表現形式,這樣在各類語言中均可以高效地使用。


寫入協議
Client端訪問Server端使用了輕量級的TCP/IP寫入協議。這種協議在MongoDB Wiki中有詳細介紹,它實際上是在BSON數據上面作了一層簡單的包裝。好比說,寫入數據的命令中包含了1個20字節的消息頭(由消息的長度和寫入命令標識組成),須要寫入的Collection名稱和須要寫入的數據。


數據文件
在MongoDB的數據文件夾中(默認路徑是/data/db)由構成數據庫的全部文件。每個數據庫都包含一個.ns文件和一些數據文件,其中數據文件會隨着數據量的增長而變多。因此若是有一個數據庫名字叫作foo,那麼構成foo這個數據庫的文件就會由foo.ns,foo.0,foo.1,foo.2等等組成。

數據文件每新增一次,大小都會是上一個數據文件的2倍,每一個數據文件最大2G。這樣的設計有利於防止數據量較小的數據庫浪費過多的空間,同時又能保證數據量較大的數據庫有相應的空間使用。

MongoDB會使用預分配方式來保證寫入性能的穩定(這種方式可使用–noprealloc關閉)。預分配在後臺進行,而且每一個預分配的文件都用0進行填充。這會讓MongoDB始終保持額外的空間和空餘的數據文件,從而避免了數據增加過快而帶來的分配磁盤空間引發的阻塞。


名字空間和盤區
每個數據庫都由多個名字空間組成,每個名字空間存儲了相應類型的數據。數據庫中的每個Collection都有各自對應的名字空間,索引文件一樣也有名字空間。全部名字空間的元數據都存儲在.ns文件中。

名字空間中的數據在磁盤中分爲多個區間,這個叫作盤區。在下圖中,foo這個數據庫包含3個數據文件,第三個數據文件屬於空的預分配文件。頭兩個數據文件被分爲了相應的盤區對應不一樣的名字空間。

 

上圖顯示了名字空間和盤區的相關特色。每個名字空間能夠包含多個不一樣的盤區,這些盤區並非連續的。與數據文件的增加相同,每個名字空間對應的盤區大小的也是隨着分配的次數不斷增加的。這樣作的目的是爲了平衡名字空間浪費的空間與保持某一個名字空間中數據的連續性。上圖中還有一個須要注意的名字空間:$freelist,這個名字空間用於記錄再也不使用的盤區(被刪除的Collection或索引)。每當名字空間須要分配新的盤區的時候,都會先查看$freelist是否有大小合適的盤區可使用。

內存映射存儲引擎
MongoDB目前支持的存儲引擎爲內存映射引擎。當MongoDB啓動的時候,會將全部的數據文件映射到內存中,而後操做系統會託管全部的磁盤操做。這種存儲引擎有如下幾種特色:

MongoDB中關於內存管理的代碼很是精簡,畢竟相關的工做已經有操做系統進行託管。
MongoDB服務器使用的虛擬內存將很是巨大,並將超過整個數據文件的大小。不用擔憂,操做系統會去處理這一切。要注意的是,MongoDB本身是無論理內存的,沒法指定內存大小,徹底交給操做系統來管理,所以有時候是不可控的,在生產環境使用必須在OS層面監控內存使用狀況。
MongoDB沒法控制數據寫入磁盤的順序,這樣將致使MongoDB沒法實現writeahead日誌的特性。因此,若是MongoDB但願提供一種durability的特性,須要實現另一種存儲引擎。
32位系統的MongoDB服務器每個Mongod實例只能使用2G的數據文件。這是因爲地址指針只能支持32位。


特性
它的特色是高性能、易部署、易使用,存儲數據很是方便。主要功能特性有:
面向集合存儲,易存儲對象類型的數據。
模式自由。
支持動態查詢。
支持徹底索引,包含內部對象。
支持查詢。
支持複製和故障恢復。
使用高效的二進制數據存儲,包括大型對象(如視頻等)。
自動處理碎片,以支持雲計算層次的擴展性
支持RUBY,PYTHON,JAVA,C++,PHP等多種語言。
文件存儲格式爲BSON(一種JSON的擴展)
可經過網絡訪問
所謂「面向集合」(Collenction-Orented),意思是數據被分組存儲在數據集中,被稱爲一個集合(Collenction)。每一個 集合在數據庫中都有一個惟一的標識名,而且能夠包含無限數目的文檔。集合的概念相似關係型數據庫(RDBMS)裏的表(table),不一樣的是它不須要定 義任何模式(schema)。

模式自由(schema-free),意味着對於存儲在mongodb數據庫中的文件,咱們不須要知道它的任何結構定義。若是須要的話,你徹底能夠把不一樣結構的文件存儲在同一個數據庫裏。

存儲在集合中的文檔,被存儲爲鍵-值對的形式。鍵用於惟一標識一個文檔,爲字符串類型,而值則能夠是各中複雜的文件類型。咱們稱這種存儲形式爲BSON(Binary Serialized dOcument Format)。


其它
在《MongoDB The Definitive Guide》中介紹的MongoDB內部構造只有這麼多,若是真要把它說清楚,可能須要另一本書來專門講述了。好比內部的JS解析,查詢的優化,索引的創建等等。有興趣的朋友能夠直接參考源代碼:)mongodb

相關文章
相關標籤/搜索