mongodb如何将查询结果保存到新的集合中

mongodb如何将查询结果保存到新的集合中

背景:

       遇到一个现实问题,生产环境mongodb中有一个集合达到1.7T,磁盘空间紧张。经过核实确认,需要删除历史数据,仅需要保存最近半年的数据即可。

初步估算,大约可节约1.2T的空间(由于客观原因,期间业务开发人员也换了好几拨,长期积累下来,就这么一直到现状)。

     那么,问题来了,如何才能实现了?

    首选想到的就是,将历史数据分批删掉,然后收缩表空间即可。诚然,这样做理论上是可以的,但是实现起来比较麻烦可行性较低。

    这里,就以标题为核心,来说明如何操作。

1、假定磁盘空间还能存储下所需要的数据量大小为前提;

2、将根据条件查询出来的结果保存到新的集合中(期间不要有数据变化);

3、将原集合重名为其他;

4、将新集合重名为元集合名;

5、此时,如果有条件,可备份需要drop掉的集合,确实不需要的话,可drop掉(实践中,drop掉大集合,不会像drop mysql的大表那样产生磁盘IO问题);

   

直接上操作步骤

# 准备测试数据

use testdb
show dbs
var arr=[]
for (var i = 1; i <= 200000 ; i++){
arr.push({"seqs":i});
}
db.t1.insert(arr)

 

# 将查询结果保存到新的集合中

var results = db.getCollection("t1").find({
"seqs": {
$gte: 10000
}
})

while(results.hasNext()) db.t3.insert(results.next())

 

步骤1、插入测试数据

use testdb
show dbs
var arr=[]
for (var i = 1; i <= 200000 ; i++){
arr.push({"seqs":i});
}
db.t1.insert(arr)

drgcore:PRIMARY> use testdb
switched to db testdb
drgcore:PRIMARY> show dbs
admin   0.000GB
config  0.000GB
local   0.018GB
testdb  0.000GB
drgcore:PRIMARY> var arr=[]
drgcore:PRIMARY> for (var i = 1; i <= 200000 ; i++){
... arr.push({"seqs":i});
... }
db.t1.insert(arr)200000
drgcore:PRIMARY> db.t1.insert(arr)
BulkWriteResult({
        "writeErrors" : [ ],
        "writeConcernErrors" : [ ],
        "nInserted" : 200000,
        "nUpserted" : 0,
        "nMatched" : 0,
        "nModified" : 0,
        "nRemoved" : 0,
        "upserted" : [ ]
})
drgcore:PRIMARY> 

 

步骤2、确认数据

drgcore:PRIMARY> show tables
system.profile
t1
drgcore:PRIMARY> db.t1.find({"seqs":{$gte:10000}})
{ "_id" : ObjectId("620470814b2140af349e0003"), "seqs" : 10000 }
{ "_id" : ObjectId("620470814b2140af349e0004"), "seqs" : 10001 }
{ "_id" : ObjectId("620470814b2140af349e0005"), "seqs" : 10002 }
{ "_id" : ObjectId("620470814b2140af349e0006"), "seqs" : 10003 }
{ "_id" : ObjectId("620470814b2140af349e0007"), "seqs" : 10004 }
{ "_id" : ObjectId("620470814b2140af349e0008"), "seqs" : 10005 }
{ "_id" : ObjectId("620470814b2140af349e0009"), "seqs" : 10006 }
{ "_id" : ObjectId("620470814b2140af349e000a"), "seqs" : 10007 }
{ "_id" : ObjectId("620470814b2140af349e000b"), "seqs" : 10008 }
{ "_id" : ObjectId("620470814b2140af349e000c"), "seqs" : 10009 }
{ "_id" : ObjectId("620470814b2140af349e000d"), "seqs" : 10010 }
{ "_id" : ObjectId("620470814b2140af349e000e"), "seqs" : 10011 }
{ "_id" : ObjectId("620470814b2140af349e000f"), "seqs" : 10012 }
{ "_id" : ObjectId("620470814b2140af349e0010"), "seqs" : 10013 }
{ "_id" : ObjectId("620470814b2140af349e0011"), "seqs" : 10014 }
{ "_id" : ObjectId("620470814b2140af349e0012"), "seqs" : 10015 }
{ "_id" : ObjectId("620470814b2140af349e0013"), "seqs" : 10016 }
{ "_id" : ObjectId("620470814b2140af349e0014"), "seqs" : 10017 }
{ "_id" : ObjectId("620470814b2140af349e0015"), "seqs" : 10018 }
{ "_id" : ObjectId("620470814b2140af349e0016"), "seqs" : 10019 }
Type "it" for more
drgcore:PRIMARY> db.t1.count({"seqs":{$gte:10000}})
190001
drgcore:PRIMARY> 

步骤3、将查询的结果保存到t3中

var results = db.getCollection("t1").find({
    "seqs": {
        $gte: 10000
    }
})
 

while(results.hasNext()) db.t3.insert(results.next())
drgcore:PRIMARY> db.t1.count({"seqs":{$gte:10000}})
190001
drgcore:PRIMARY> 
drgcore:PRIMARY> 
drgcore:PRIMARY> var results = db.getCollection("t1").find({
...     "seqs": {
...         $gte: 10000
...     }
... })
drgcore:PRIMARY> while(results.hasNext()) db.t3.insert(results.next())
WriteResult({ "nInserted" : 1 })
drgcore:PRIMARY> 
drgcore:PRIMARY> db.t3.count({"seqs":{$gte:10000}})
190001

经过验证,已经将所需要的数据保存到了新的集合t3中,此时,即可drop掉原有集合t1。

drgcore:PRIMARY> db.t1.renameCollection("t1_bak")
{ "ok" : 1 }
drgcore:PRIMARY> show dbs
admin   0.000GB
config  0.000GB
local   0.025GB
testdb  0.010GB
drgcore:PRIMARY> db.t3.renameCollection("t1")
{ "ok" : 1 }
drgcore:PRIMARY> db.t1_bak.drop()
true
drgcore:PRIMARY> show dbs
admin   0.000GB
config  0.000GB
local   0.025GB
testdb  0.003GB
drgcore:PRIMARY> show tables
system.profile
t1
drgcore:PRIMARY> 

 

posted @ 2022-02-10 10:07  davie2020  阅读(1209)  评论(0编辑  收藏  举报