1. 程式人生 > >Mongodb 入門學習筆記

Mongodb 入門學習筆記

  • NoSql簡介
    • Not only sql,非關係型資料庫,用於超大規模的資料儲存
      • 優點
        • 高可擴充套件性
        • 分散式計算
        • 低成本
        • 架構的靈活性,半結構化資料
        • 沒有複雜的關係
      • 缺點
        • 沒有標準化
        • 有限的查詢功能
        • 最終一致不是直觀的程式
    • 關係型資料庫的ACID
    • 分散式系統
      • 優點
      • 缺點
    • CAP定理
      • 一個分散式系統不可能同時滿足以下三個特點
      • 一致性(Consistency) (所有節點在同一時間具有相同的資料)
      • 可用性(Availability) (保證每個請求不管成功或者失敗都有響應)
      • 分隔容忍(Partition tolerance) (系統中任意資訊的丟失或失敗不會影響系統的繼續運作)
      • 參考文章
    • BASE理論
      • 對可用性及一致性的弱要求原則
      • Basically Available 基本可用
      • Soft-state 軟狀態 無連線的(分散式不同節點副本的同步延時)
      • Eventually Consistent 最終一致性
  • Mongodb簡介
    • 面向文件儲存
    • JSON
  • Mongodb概念解析
    • 文件,集合,資料庫
sql術語 monogdb術語 解釋
database database 資料庫
table collection 資料庫表/集合
row docunment 資料庫行/文件
column filed 列/欄位
index index 索引
table joins 資料庫表連線
primary key primary key 自增主鍵
  • 資料庫
    • show dbs #檢視所有資料庫
    • use test #切換到test資料庫
  • 特殊資料庫
    • admin
      • 從許可權的角度來看,這是"root"資料庫。要是將一個使用者新增到這個資料庫,這個使用者自動繼承所有資料庫的許可權。一些特定的伺服器端命令也只能從這個資料庫執行,比如列出所有的資料庫或者關閉伺服器。
    • config
      • 當Mongo用於分片設定時,config資料庫在內部使用,用於儲存分片的相關資訊
    • local
      • 這個資料永遠不會被複制,可以用來儲存限於本地單臺伺服器的任意集合
  • 文件
    • key-value鍵值對
    • 例如 {“site”:“www.runoob.com”, “name”:“菜鳥教程”}
  • 集合
    • 文件組
    • capped collections 固定大小的collection
      • 高效能
      • 自動維護物件插入順序
      • 儲存空間是提前分配的
  • 元資料
    • 資料庫的資訊儲存在
      • dbname.system.*
  • Mongodb資料型別
    • String
    • Integer
    • Boolean
    • Double
    • Min/Max keys 將值與BSON的最高低值進行比較
    • Arrays
    • TimeStamp 時間戳。記錄文件修改或新增的具體時間
    • Object 用於內嵌文件
    • Null
    • Symbol 符號
    • Date
    • Object ID 物件Id 用於建立文件的ID
    • Binary Data
    • Code 程式碼型別
    • Regular expression 用於儲存正則表示式
  • 操作資料庫
    • 刪除集合
      • db.coll_name.drop()
    • 檢視集合
      • show collections
    • 刪除資料庫
      • db.dropDatabase()
    • 插入文件
      • db.COLLECTION_NAME.insert(document)
      • db.col.save(document) 也可以用於更新
      • document=({title: ‘MongoDB 教程’,
        description: ‘MongoDB 是一個 Nosql 資料庫’,
        by: ‘Mongodb中文網’,
        url: ‘http://www.mongodb.org.cn’,
        tags: [‘mongodb’, ‘database’, ‘NoSQL’],
        likes: 100
        });
    • 更新文件
      • 更新已存在的文件
      • db.collection.update(
        query,
        update,
        {
        upsert: ,
        multi: ,
        writeConcern:
        })
      • query : update的查詢條件,類似sql update查詢內where後面的。
      • update : update的物件和一些更新的操作符(如 , , inc…)等,也可以理解為sql update查詢內set後面的
      • upsert : 可選,這個引數的意思是,如果不存在update的記錄,是否插入objNew,true為插入,預設是false,不插入。
      • multi : 可選,mongodb 預設是false,只更新找到的第一條記錄,如果這個引數為true,就把按條件查出來多條記錄全部更新。
      • writeConcern :可選,丟擲異常的級別。
      • $gt 大於
      • $lt 小於
    • 刪除文件
      • db.collectionName.remove(
      • query,
        {
        justOne: ,
        writeConcern:
        })
      • query :(可選)刪除的文件的條件。
      • justOne : (可選)如果設為 true 或 1,則只刪除一個文件。
      • writeConcern :(可選)丟擲異常的級別
    • MongoDB 查詢文件
      • db.col.find()
      • db.col.find().pretty() #易讀
      • Mongodb與RDBMS比較
        • 等於
          • db.col.find({“by”:“菜鳥教程”}).pretty()
          • where by = ‘菜鳥教程’
        • 不等於
          • db.col.find({“likes”:{$ne:50}}).pretty()
          • where likes != 50
        • 大於
          • $gt
        • 小於
          • $lt
        • 大於等於
          • $gte
        • 小於等於
          • $lte
      • AND
        • find()內傳入多個key ,逗號隔開
        • db.col.find({key1:value1, key2:value2}).pretty()
      • OR
        • $or
        • db.col.find({$or: [{key1: value1}, {key2:value2}]}).pretty()
      • AND OR 聯合使用
        • db.col.find({“likes”: {$gt:50}, $or: [{“by”: “Mongodb中文網”},{“title”: “MongoDB 教程”}]}).pretty()
      • $type 操作符
        • 於BSON型別來檢索集合中匹配的資料型別,並返回結果
        • db.col.find({“title” : {$type : 2}})
      • Limit與Skip方法
        • db.COLLECTION_NAME.find().limit(NUMBER)
        • db.COLLECTION_NAME.find().limit(NUMBER).skip(NUMBER) #跳過指定數量的資料
      • 排序
        • db.COLLECTION_NAME.find().sort({KEY:1}) # 1升序 -1降序
        • 如果沒有指定sort()方法的排序方式,預設按照文件的升序排列
      • 索引
        • 索引儲存在一個易於遍歷讀取的資料集合中,索引是對資料庫表中一列或多列的值進行排序的一種結構
        • 建立索引
          • ensureIndex()
          • db.col.ensureIndex({“title”:1}) # 1升序 -1降序
  • 聚合
    • Mongodb聚合
      • 用於處理資料並返回結果
      • db.COLLECTION_NAME.aggregate(AGGREGATE_OPERATION)
      • 例子 db.mycol.aggregate([{KaTeX parse error: Expected '}', got 'EOF' at end of input: …roup : {_id : "by_user", num_tutorial : {$sum : 1}}}])
      • 常見例子
      • 管道
        • linux中 一般用於將當前命令的輸出結果作為下一個命令的引數
        • MongoDB的聚合管道將MongoDB文件在一個管道處理完畢後將結果傳遞給下一個管道處理。管道操作是可以重複的
        • 表示式
          • 處理輸入文件並輸出
        • 常見操作
          • $project: 修改輸入文件的結構。可以用來重新命名、增加或刪除域,也可以用於建立計算結果以及巢狀文件
          • m a t c h match:用於過濾資料,只輸出符合條件的文件。 match使用MongoDB的標準查詢操作。
            • db.articles.aggregate( [
              { $match : { score : { $gt : 70, $lte : 90 } } },
              { $group: { _id: null, count: { $sum: 1 } } }
              ] );
          • $limit:用來限制MongoDB聚合管道返回的文件數。
          • $skip:在聚合管道中跳過指定數量的文件,並返回餘下的文件。
            • db.article.aggregate({ $skip : 5 });
          • $unwind:將文件中的某一個數組型別欄位拆分成多條,每條包含陣列中的一個值。
          • $group:將集合中的文件分組,可用於統計結果。
          • $sort:將輸入文件排序後輸出。
          • $geoNear:輸出接近某一地理位置的有序文件
    • Mongodb複製 副本集
      • 將資料同步到多個伺服器的過程
      • 什麼是複製
        • 保障資料的安全性
        • 資料高可用性 (24*7)
        • 災難恢復
        • 無需停機維護(如備份,重建索引,壓縮)
        • 分散式讀取資料
      • 原理
        • 一主一從、一主多從
        • 主節點記錄在其上的所有操作 oplog,從節點定期輪詢主節點獲取這些操作,然後對自己的資料副本執行這些操作,從而保證從節點的資料與主節點一致
      • 副本集特徵
        • N個點的叢集
        • 任何節點可作為主節點
        • 所有寫入都在主節點
        • 自動故障轉移
        • 自動恢復
      • 實踐
    • MongoDB 分片
      • 在多臺機器上分割資料,使得資料庫系統能儲存和處理更多的資料
      • 原因
        • 複製所有的寫入操作到主節點
        • 延遲的敏感資料會在主節點查詢
        • 單個副本集限制在12個節點
        • 當請求量巨大時會出現記憶體不足
        • 本地磁碟不足
        • 垂直擴充套件價格昂貴
      • 元件
        • Shard
          • 用於儲存實際的資料塊,實際生產環境中一個shard server角色可由幾臺機器組個一個relica set承擔,防止主機單點故障
        • Config Server
          • mongod例項,儲存了整個 ClusterMetadata,其中包括 chunk資訊
        • Query Routers
          • 前端路由,客戶端由此接入,且讓整個叢集看上去像單一資料庫,前端應用可以透明使用
  • 資料備份
    • mongodump -h dbhost -d dbname -o dbdirectory
  • 資料恢復
    • mongorestore -h dbhost -d dbname --directoryperdb dbdirectory
  • 監控
    • mongostat,當前執行狀態
    • mongotop,檢視讀寫花費的時間
      • mongotop 10 10秒鐘讀取一次
      • –locks 報告每個資料庫的鎖的使用中 3.0後已取消
  • MongoDB 關係
    • 1:1
    • 1:N
    • N:1
    • N:N
    • 嵌入式關係
      • {
        “_id”:ObjectId(“52ffc33cd85242f436000001”),
        “contact”: “987654321”,
        “dob”: “01-01-1991”,
        “name”: “Tom Benzamin”,
        “address”: [
        {
        “building”: “22 A, Indiana Apt”,
        “pincode”: 123456,
        “city”: “Los Angeles”,
        “state”: “California”
        },
        {
        “building”: “170 A, Acropolis Apt”,
        “pincode”: 456789,
        “city”: “Chicago”,
        “state”: “Illinois”
        }]
        }
    • 引用式關係
      • {
        “_id”:ObjectId(“52ffc33cd85242f436000001”),
        “contact”: “987654321”,
        “dob”: “01-01-1991”,
        “name”: “Tom Benzamin”,
        “address_ids”: [
        ObjectId(“52ffc4a5d85242602e000000”),
        ObjectId(“52ffc4a5d85242602e000001”)
        ]
        }
  • 資料庫引用
    • 手動引用
    • DBRefs
      • 一個文件從多個集合引用文件,我們應該使用 DBRefs
      • { $ref(集合名稱) : , $id(引用的ID) : , $db(資料庫的名稱) : }
  • 覆蓋索引查詢
    • 所有的查詢欄位是索引的一部分
    • 所有的查詢返回欄位在同一個索引中
    • 例子
      • db.users.insert({“contact”: “987654321”, “dob”: “01-01-1991”, “gender”: “M”, “name”: “Tom Benzamin”, “user_name”: “tombenzamin”})
      • db.users.ensureIndex({gender:1,user_name:1}) //createIndex()
      • //覆蓋 db.users.find({gender:“M”},{user_name:1,_id:0})
      • //不覆蓋 db.users.find({gender:“M”},{user_name:1})
    • 注意以下不能使用覆蓋索引
      • 所有索引欄位是一個子文件
      • 所有索引欄位是一個數組
    • 查詢索引
      • db.users.getIndexes()
  • 查詢分析
    • explain()
      • indexOnly true表示使用了索引
      • cursor
    • hint()
      • 強迫使用一個指定索引
  • 原子操作
    • mongodb不支援事務,要麼儲存要麼不儲存不會出現不完整的情況。
    • db.collection.findAndModify()
    • $set
    • $unset
    • $inc
    • $push
    • $pushAll
    • $pull
    • $addToSet
    • $pop
    • $rename
    • $bit
  • 高階索引
    • 索引陣列欄位
      • db.users.ensureIndex({“tags”:1})
    • 索引子文件欄位
      • db.users.ensureIndex({“address.city”:1,“address.state”:1,“address.pincode”:1})
  • 索引限制
    • 額外開銷
    • 記憶體使用
    • 查詢限制
    • 索引鍵限制
    • 插入文件超過索引鍵限制
    • 最大範圍
      • 集合中索引不能超過64個
      • 索引名的長度不能超過125個字元
      • 一個複合索引最多可以有31個欄位
  • ObjectId
    • 一個12位元組 BSON 型別資料結構
      • 前4個位元組表示時間戳
      • 接下來的3個位元組是機器標識碼
      • 緊接的兩個位元組由程序id組成(PID)
      • 最後三個位元組是隨機數
    • 建立新的id
      • newObjectId = ObjectId()
      • ObjectId(“5be3e06a0d79133288002c7c”).getTimestamp() 獲取文件建立時間
    • 轉字串
      • new ObjectId().str
  • Map Reduce
    • Map-Reduce是一種計算模型,簡單的說就是將大批量的工作(資料)分解(MAP)執行,然後再將結果合併成最終結果(REDUCE)

       ```
       db.posts.mapReduce( 
          function() { emit(this.user_name,1); }, 
          function(key, values) {return Array.sum(values)}, 
             {  
                query:{status:"active"},  
                out:"post_total" 
             }
       )
       ```
      
  • 全文檢索
    • 對每一個詞建立索引
    • v2.6以後預設開啟
    • db.p.ensureIndex({post_text: “text”})
    • db.p.find({KaTeX parse error: Expected '}', got 'EOF' at end of input: text:{search:“mongodb.org.cn”}})
    • 刪除
      • db.p.dropIndex(“post_text_text”)
  • 正則表示式
    • $regex
  • GridFS
    • 用於儲存和恢復那些超過16M(BSON檔案限制)的檔案(如:圖片、音訊、視訊等
    • mongofiles.exe -d gridfs put song.mp3
    • db.fs.files.find() 查詢文件
    • db.fs.chunks.find({files_id:ObjectId(‘534a811bf8b4aa4d33fdf94d’)}) 根據文件id查詢chunks
  • 固定集合 Capped Collections
    • db.createCollection(“cappedLogCollection”,{capped:true,size:10000})
    • db.cappedLogCollection.isCapped() 判斷是否固定
    • db.runCommand({“convertToCapped”:“posts”,size:10000}) 已存在post集合轉為固定集合
    • db.createCollection(“cappedLogCollection”,{capped:true,size:10000}) 建立固定集合
    • 查詢安裝插入順序返回
    • 特點
      • 在32位機子上一個cappped collection的最大值約為482.5M,64位上只受系統檔案大小的限制
      • 對固定集合進行插入速度極快
      • 按照插入順序的查詢輸出速度極快
      • 能夠在插入最新資料時,淘汰最早的資料
    • 用途
      • 儲存日誌資訊
      • 快取一些少量的文件
  • MongoDB 自動增長
    • db.user.save({
      uid: db.ids .findAndModify({
      update:{$inc:{‘id’:1}},
      query:{“name”:“user”},
      new:true}).id, //讓db.ids集合中的name="user"文件的id值加1並返回充當自增id
      username: “dotcoo”,
      password:“dotcoo”,
      info:"http://www.dotcoo.com/ "});
  • 本文所有筆記均來自於Mongodb教程