更新自上次更新以来已更改的所有记录

时间:2018-09-25 23:23:37

标签: mongodb

我第一次与Mongo合作,我试图将数据从API调用同步到本地Mongo集合。在集合中,数据如下所示:

{
"_id" : ObjectId("5baabbf70456c16b19bfd1e3"),
"id" : "25770a02bd285ca21d428ae4",
"created" : "2016-02-25T03:06:30.814Z",
"is_public" : true,
"kind" : "aspect",
"name" : "Last Open",
"table" : "user",
"tags" : [
    "aspect",
    "predefined",
    "default"
],
"updated" : "2016-09-09T00:59:54.823Z"
}

只要API调用中具有该ID的更新时间大于与该ID相匹配的文档中的更新时间,我想更新该集合中的任何文档。

到目前为止,我有一个似乎可以使用的过滤器,但是尝试使用bulkWrite仅将整个集合附加到末尾。有没有一种方法可以更新而不是追加?下面是我用于过滤和编写的代码。

mongoUpsert(myMongoDB.collection("mongosegment"), apiResponse.data, function () {
    db.close();
});

function mongoUpsert(collection, data_array, cb) {

    var ops = data_array.map(function (data) {
        return {
            "updateOne": {
                "filter": {
                    "id": data.id, // or any other filtering mechanism to identify a doc
                    "updated": {
                        "$gt": data.updated
                    }
                },
                "update": {
                    "$set": data
                },
                "upsert": true
            }
        };
    });

    collection.bulkWrite(ops, function (err, r) {});

    return cb(false);
}

2 个答案:

答案 0 :(得分:0)

似乎您需要{multi:true}

答案 1 :(得分:0)

好像我犯了几个错误。我以为我会分享帮助任何其他来mongo的人。首先,我让过滤器读取$gt而不是$lt。这意味着一切都返回false,因为最新的查询无法返回存储值之前的更新时间。以我认为查询有效的方式,这是一个站点。其次,我有upsert: true,每当updateOne的过滤器失败时,它都会写一个新文档。如果updateOne的筛选器成功,则它将更新文档。就我而言,我强迫他们全部失败,因此每次运行都将我的文档增加一倍。我也最终使用了replaceOne,因为如果它与我的过滤器匹配,我想替换整个文档。这是此部分的最终工作代码:

function mongoUpsert(collection, data_array) {
    var ops = data_array.map(function (data) {
        return {
            "replaceOne": {
                "filter": {
                    "id": data.id,
                    "updated": {
                        "$lt": data.updated
                    }
                },
                "replacement": {
                    "$set": data
                },
                "upsert": false
            }
        };
    });

    collection.bulkWrite(ops, function (err, r) {
        insertUniqueDocs(collection, data_array);
    });
}