單mongod測試(即只有一個mongod程序實例)
所有測試機均爲4g內存雙核cpu(64位系統)
測試所用文檔爲簡單的三個字段的文檔:
DBObject doc = newBasicDBObject();
doc.put("test","test"+insertNum);
doc.put("no", insertNum);
doc.put("time",swapWords(sld.format(new Date())));
一、入庫效率:
1、普通集合入庫,
每10萬條數據平均2~3秒
入庫一億條數據大概45分鐘
2、四個索引的普通集合
初始每10萬條5~6秒,時間逐漸增長,到千萬級別時每10萬條入庫時間60~80秒
入庫一千萬數據一小時多一點
3、一個索引的普通集合
初始入庫每10萬條3秒左右,耗時逐漸增長,到四千萬左右時每10萬條入庫時間15~20秒
入庫一千萬數據7、8分鐘
入庫四千萬數據大概一個半小時
4、固定集合
初始入庫每10萬條數據平均2~2.5秒
5、一個索引的固定集合
初始入庫每10萬條數據平均3~4秒
二、查詢效率:
沒有索引會進行表掃描(大表會極慢)
無論有沒有索引,大批量插入時查詢效率極慢
三、插入時機器負載:
沒索引時:cpu不到20%
有索引時,初始插入cpu 20,30~40,後期比較慢不到5~15% 猜測原因內存已經用滿,磁盤io比較多
mongos測試(三臺機器的簡單無備份mongod分片羣)
一、簡單入庫
1、test集合,分片,無索引,文檔結構大小同上例
每10萬條記錄 3~3.5秒
從sqlserver測試表導數據至mongos(三臺)測試
一、第一種入庫策略:
先入庫,再建索引及分片,按索引分片
1、測試表Test共20列1.5億數據
2、導到mongos時表不設索引,不分片,等到入庫完畢後再進行這些操作
3、導出時所有列都用的string
4、1億5千萬入庫6個半小時 10萬/10~20秒(從遠程的sqlserver數據庫導入,一邊遍歷結果集一邊插入,所以實際入庫速度應該比這個快)
5、建userid,city的二級索引大概用了半個小時(從日誌中查看)
6、按索引中(userid,city)的一個鍵分片(而不是用objectid);
操作是阻塞式的,喫完飯回來就完成了。。應該是在一個半小時內
7、在有分片及索引的情況下,追加插入效率較差,每1000條 20~30秒
8、所以考慮:撤銷索引,查看集合行數(看是否有影響),追加插入數據,建立索引,測試查詢。但是剛剛撤銷索集羣就無法訪問了(因爲分片是按索引userid分的).
二、查詢:
建立索引後:
幾次測試,同一個程序10000條數據連續查詢,平均11~13毫秒
併發測試,3個程序同時分別連續查詢10000條數據,平均14毫秒
三、刪除集合不會釋放硬盤空間
1、刪除後的表不會釋放硬盤空間而是內部標記爲空閒,需要注意
2、可以用db.repairDatabase()整理磁盤文件:
mongos會分mongod分別處理,每個mongod處理自己的
程序首先會將所有有效數據寫入臨時文件(在他的文件系統中發現諸如_tmp等文件中數據文件增加很多,而且其中文件格式和源數據文件格式相似),所以硬盤佔用率會很明顯的上升,完成整理後硬盤佔用減少。
3、所以如果使用此方法:
應該保證磁盤剩餘空間容量>mongodb數據文件中有效數據量,
保險方法是磁盤剩餘空間>mongodb數據文件
4、時間
比較慢,不到180g有效數據分在三臺機器,用了1~3個小時
4、在此過程中查詢:
在此過程中讀寫幾乎不能用
四、第二種入庫策略:
按objectid分片,索引及入庫策略不變
1、 初始入庫時間大致和之前相同(1.5億條數據)
2、 追加存入重複數據
20萬條10分鐘(先遍歷sqlserver結果集存入內存中再一次性入庫mongodb)
3、 追加新數據入庫
20萬條2分半鐘(先遍歷sqlserver結果集存入內存中再一次性入庫mongodb)
4、 根據非objectid鍵更新插入(upsert)
很慢,1000條需要6~8分鐘(實際上操作失敗,因爲upsert操作需要指定分片鍵objectid)
5、 查詢
速度比之前方案稍慢,35~40毫秒平均(連續查詢20000次)
其他
1、 windows,linux混合集羣測試
可行,效率沒大規模用過,不知道是否穩定。Linux方面程序不會主動釋放內存,windows程序據觀察在入庫時內存佔用量增大,但是入庫完後會釋放。
2、 32位windows系統程序確實只能存2g數據,大於2g數據後程序報錯退出。