问题
When doing a research in mongo shell I often write quite complex queries and want the result to be stored in other collection. I know the way to do it with .forEach()
:
db.documents.find(query).forEach(function(d){db.results.insert(d)})
But it's kind of tedious to write that stuff each time. Is there a cleaner way? I'd like the syntax to be something like db.documents.find(query).dumpTo('collectionName')
.
回答1:
Here's a solution I'll use: db.results.insert(db.docs.find(...).toArray())
There is still too much noise, though.
UPD: There is also an option to rewrite find
using aggregation pipeline. Then you can use $out operator.
回答2:
It looks like you are doing your queries from the mongo shell, which allows you to write code in javascript. You can assign the result of queries to a variable:
result = db.mycollection.findOne(my_query)
And save the result to another collection:
db.result.save(result)
You might have to remove the _id of the result if you want to append it to the result collection, to prevent a duplicate key error
Edit:
db.mycollection.findOne({'_id':db.mycollection.findOne()['_id']})
db.foo.save(db.bar.findOne(...))
If you want to save an array, you can write a javascript function. Something like the following should work (I haven't tested it):
function save_array(arr) {
for(var i = 0; i < arr.length; i++) {
db.result.save(arr[i])
}
}
...
result = db.mycollection.find(...)
save_array(result)
If you want the function to be available every time you start mongo shell, you can include it in your .mongorc.js
file
回答3:
As far as I know, there isn't built-in functionality to do this in MongoDB.
Other options would be to use mongoexport/mongoimport or mongodump/mongorestore functionalities.
In both mongoexport and mongodump you can filter the results by adding query options using --query <JSON>
or -q <JSON>
.
回答4:
If your query is using an aggregation operator then the solution is as sample as using the $out.
I created a sample Collection with the name "tester" which contain the following records.
{ "_id" : ObjectId("4fb36bfd3d1c88bfa15103b1"), "name" : "bob", "value" : 5, "state" : "b"}
{ "_id" : ObjectId("4fb36c033d1c88bfa15103b2"), "name" : "bob", "value" : 3, "state" : "a"}
{ "_id" : ObjectId("4fb36c063d1c88bfa15103b3"), "name" : "bob", "value" : 7, "state" : "a"}
{ "_id" : ObjectId("4fb36c0c3d1c88bfa1a03b4"), "name" : "john", "value" : 2, "state" : "a"}
{ "_id" : ObjectId("4fb36c103d1c88bfa5103b5"), "name" : "john", "value" : 4, "state" : "b"}
{ "_id" : ObjectId("4fb36c143d1c88bfa15103b"), "name" : "john", "value" : 8, "state" : "b"}
{ "_id" : ObjectId("4fb36c163d1c88bfa15103a"), "name" : "john", "value" : 6, "state" : "a"}
Now using the aggregate operator I perform a group by and then save the result into a new collection using this magical operator "$out".
db.tester.aggregate([{$group:{
_id:{name:"$name",state:"$state"},
min:{$min:"$value"},
max:{$max:"$value"},
} },
{$out:"tester_max_min"}
])
What basically the query is trying to do is, group by name & state and find the min and max values for each individual group, and then save the result into a new collection named "tester_max_min"
db.tester_max_min.find();
The new collection formed will have the following documents in it :
{ "_id" : { "name" : "john", "state" : "b" }, "min" : 4, "max" : 8 }
{ "_id" : { "name" : "john", "state" : "a" }, "min" : 2, "max" : 6 }
{ "_id" : { "name" : "bob", "state" : "a" }, "min" : 3, "max" : 7 }
{ "_id" : { "name" : "bob", "state" : "b" }, "min" : 5, "max" : 5 }
I still need to explore how helpful can $out is but it works like a charm for any aggregator operator.
来源:https://stackoverflow.com/questions/20769621/saving-the-result-of-a-mongodb-query