我有一个像这样的示例mongodb:
{
"_id" : ObjectId("559e448dfb9fc95e5d00008c"),
"title" : "Maps ",
"link" : "https://www.youtube.com/embed/NmugSMBh_iI",
"img" : "https://i.ytimg.com/vi/NmugSMBh_iI/default.jpg",
"time" : "3:28",
"des" : "Maroon 5 - Maps (Explicit)\r\n",
"cat" : [
"maroon5"
],
"id" : 179,
"date" : "2015-07-08T16:49:11+07:00"
}
{
"_id" : ObjectId("559e451afb9fc95e5d00008d"),
"title" : "Animals",
"link" : "https://www.youtube.com/embed/qpgTC9MDx1o",
"img" : "https://i.ytimg.com/vi/qpgTC9MDx1o/default.jpg",
"time" : "4:40",
"des" : "Maroon 5 - Animals\r\n",
"cat" : [
"maroon5"
],
"id" : 180,
"date" : "2015-07-08T16:49:11+07:00"
}
现在我想在每个“链接”字段中将此字符串“embed /”替换为“watch?v =”,如下所示:
"link" : "https://www.youtube.com/watch?v=/NmugSMBh_iI"
我该怎么做?
答案 0 :(得分:2)
您将不得不循环浏览并逐个更改它们。 您可以使用以下代码在数据库中进行更改,但是,您可以将MongoDB的支持库用于您希望获得相同结果的任何语言。
var cursor = db.videos.find();
while ( cursor.hasNext() ) {
var current = cursor.next();
db.videos.update({_id: current._id}, {$set: {link: current.link.replace('embed/','watch?v=')}})
}
答案 1 :(得分:1)
如上所述,您需要循环收集结果,以便能够读取您要修改的值。 MongoDB更新运算符不支持“就地”执行此操作,并且目前不支持“regexReplce”运算符。虽然它会很好。
最有效的方法是使用"Bulk"操作API,并通过$regex
进行一点查询过滤,以确保只更新那些需要更新的项目:
var bulk = db.tube.initializeUnorderedBulkOp(),
count = 0;
db.tube.find({
"link": /(youtube\.com)(\/embed)/
}).forEach(function(doc) {
doc.link = doc.link.replace(
new RegExp("(youtube\.com)(\/embed\/)"),
new RegExp("$1/watch\?v=") );
bulk.find({ "_id": doc._id }).updateOne({ "$set": { "link": doc.link } });
count++;
// Only send operations to server once in 1000 ops. And re-init.
if ( count % 1000 == 0 ) {
bulk.execute();
bulk = db.tube.initializeUnorderedBulkOp();
}
});
// Drain any queued operations
if ( count % 1000 != 0 )
bulk.execute();
这是您最快的更新方式,因为请求是以“批次”处理的,这意味着来往服务器的流量更少。因此,速度更快。