MongoDB是非關係型資料庫的典型代表,DB-Engines Ranking 資料顯示,近年來,MongoDB在NoSQL領域一直獨佔鰲頭。MongoDB是為快速開發網際網路應用 而設計的資料庫系統,其資料模型和持久化策略就是為了構建高讀/寫的效能,並且可以方面的彈性擴充。目前公司使用到的MongoDB的主要場景有 庫存中心(原料出入庫、商品出入庫、商品上下架變動、與其它系統平臺的互動報文等)、物流配送(訂單的物流資訊、配送資訊、地理位置資訊等)、日誌中心(系統應用和APP的log資訊、呼叫依賴資訊等)、商品中心(商品資料、推送資訊等)、運維管理平臺(收集記錄的變更資訊等)等。隨著MongoDB的普及和使用量的快速增長,為了規範使用,便於管理和獲取更高的效能,整理此文件。我們從 資料庫設計規範、集合設計規範、文件設計規範、連線規範、操作規範等5個方面進行闡述和要求。
1. 資料庫設計規範
(1)資料庫名約定為小寫。
(2)資料庫名稱不能包含除’_’以外的特殊字元,例如:/ . “ $。
(3)資料庫名稱最多為64個字元。
(4)資料庫上線需經過DBA評審。
2. 集合設計規範
(1)集合名稱約定為小寫。
(2)集合名稱不能包含除’_’以外的特殊字元字元;集合名稱禁止以system.開頭。
(3)集合名稱的最大長度為64個字元,包括字首的【database.】內容。
(4)集合名稱的命名規則和MySQL資料庫表的命名規則相同。
a) 同一模組的集合儘可能使用相同的字首名,集合名稱儘可能表達用途。
b) 資料表 <模組標識>_<表標識> 例如: order_header , order_detail
c) 編碼表 base_<模組標識>_<表標識>
d) 日誌表 log_<模組標識>_<表標識>
(5)固定集合可以用於記錄日誌,其插入資料更快,可以實現在插入資料時,淘汰最早的資料。固定集合需要顯式建立,指定Size的大小,還能夠指定文件的數量。集合不管先達到哪一個限制,之後插入的新文件都會把最老的文件移出。
(6)索引命名:idx_<構成索引的欄位名>。如果欄位名字過長,可採用欄位縮寫。
3. 文件設計規範
(1)Key的命名規範:不能以$開頭;不能包含.(點號)。
(2)文件中的_id鍵推薦使用預設值,禁止向_id中儲存自定義的值。
解讀:MongoDB文件中都會有一個“_id”鍵,預設是個ObjectID物件(識別符號中包含時間戳、機器ID、程式ID和計數器)。MongoDB在指定_id與不指定_id插入時速度相差很大,指定_id會減慢插入的速率。
(3)推薦使用短欄位名。
解讀:與關係型資料庫不同,MongoDB集合中的每一個文件都需要儲存欄位名,長欄位名會需要更多的儲存空間。
(4)禁止在同一個集合欄位中儲存多個資料型別的資料。
(5)如若將日期型別選擇為string,不同的日期格式的文件,不支援等值查詢,不支援範圍查詢。
解讀:建立一個測試集合product,分別向集合插入Date:”20180425″和Date:”2018-04-25″兩筆資料。等值查詢、範圍查詢($gte, $lte)只能查到日期格式相同的資料,都為一筆資料。
(6)MongoDB大小寫敏感,如果欄位無需大小寫敏感,為了提高查詢效率,應儘量在統一了大小寫之後再插入到資料庫中。
(7)MongoDB是文件型資料庫,資料以BSON形式儲存在文件中。MongoDB能夠支援最大16 MB的文件大小。建議儘量不要儲存大型物件,將文件控制在16 MB以內。
(8)通過$size查詢陣列大小,但是$size運算子不使用索引和限制準確匹配(不能指定$Sized 範圍)。因此,如果需要基於陣列的大小執行查詢,可以在文件設計中增加size屬性。
解讀:例如在商品評價中,其他人可以對評價進行投票。為了阻止使用者多次投票和對有幫助的評論進行排序,所以,評價文件設計是:在一個陣列欄位(voter_ids)儲存了所有評論使用者的ID,而陣列大小快取在helpful_votes欄位裡。
(9)分片鍵必須有索引,分片鍵大小限制為512byte,一旦集合已經分片,不可以直接修改分片鍵。不接受向已進行分片的collection上插入無分片鍵的文件,也不支援空值插入。
(10)片鍵的設計原則:
a) 所有的插入、更新、刪除將會均勻傳送到叢集的所有分片中。
b) 所有的查詢將會在叢集中的所有分片中均勻地分發。
c) 所有的更新或者刪除操作將會只面向相關的分片,不會傳送到一個沒有儲存被修改資料的分片上。
d) 一個查詢將不會被髮送到沒有儲存被查詢資料的分片上。
4. 連線規範
(1)正確連線副本集,副本集提供了資料的保護、高可用和災難恢復的機制。如果主節點當機,其中一個從節點會自動提升為從節點。
(2)合理控制連線池的大小,限制連線數資源,可通過Connection String URL中的maxPoolSize 引數來配置連線池大小。
(3)複製集讀選項
預設情況下,複製集的所有讀請求都發到Primary,Driver可通過設定的Read Preference 來將讀請求路由到其他的節點。
a) Primary:預設規則,所有讀請求發到Primary。
b) PrimaryPreferred: Primary優先,如果Primary不可達,請求Secondary。
c) Secondary:所有的讀請求都發到Secondary。
d) SecondaryPreferred:Secondary優先,當所有的Secondary不可達時,請求Primary。
e) Nearest:讀請求傳送到最近的可達節點上(通過ping探測得出最近的節點)。
5. 操作規範
(1)MongoDB資料庫更新文件有兩種實現方式—文件替換和目標欄位更新。既可以完整替換現有的文件,也可以使用更新操作符來修改某個欄位。
解讀:使用操作符,例如$set操作符和$push操作符,無論原始的大小,可以更新文件裡的指定欄位。頻繁文件更新的場景下,使用目標更新可以在序列化和傳輸資料上花費更少的時間,獲得更好的效能。
(2)多文件更新,在預設情況下,只會更新匹配查詢器的第一個文件。要更新所有的匹配文件,需要顯式指定多文件更新模式–新增引數multi:true。
(3)在文件級別更新是原子性的,這意味著一條更新10個文件的語句可能在更新3個文件後由於某些原因失敗。應用程式必須根據自己的策略來處理這些失敗。
(4)update結合upsert可以用來處理,當文件存在時更新,文件不存在時插入。如果查詢選擇器匹配,更新就正常執行;如果沒有匹配的文件,就會插入新的文件。新文件的欄位是查詢選擇器和目標更新文件的邏輯合併。
(5)複製集的資料安全及寫策略,Write Concern 用於控制寫入安全的級別。
解答:Write Concern 是一個效能和資料一致性的權衡,應根據業務場景進行設定。對於強一致性場景,建議w>1或者等於majority。
(6)聚合框架是MongoDB的高階查詢語言,它允許通過轉換和合並由多個文件中的資料來生成新的單個文件裡不存在的文件資訊。可以把MongoDB的聚合框架等價於SQL的Group By 語句。
(7)在聚合框架中,$project操作符允許過濾傳遞給管道下一個階段的欄位。限制每個文件傳遞的大小,可以改善效能,尤其是在處理大文件且只需要每個文件一部分資料的場景下。
本文版權歸作者所有,未經作者同意不得轉載,謝謝配合!!!
本文版權歸作者所有,未經作者同意不得轉載,謝謝配合!!!