排序:仅更新最后几行

时间:2019-01-19 10:45:53

标签: mysql node.js promise async-await sequelize.js

我有一个数组(成千上万个),需要根据条件插入或更新。我的模型类中实现了一个简单的upsert()方法。

实施

    csv.upsert = async function (values, condition) {
    let obj = await csv.findOne({ where: condition });

    if (obj) {
        // update
        console.log("existing record updated")
        return await obj.update(values);
    } else {
        // insert
        console.log("new record inserted")
        return await csv.create(values);
    }

}

然后使用此upsert方法,在其中循环遍历对象数组以在db中插入或更新它们。

用法

try {           
    await models.sequelize.authenticate();          
    await models.sequelize.sync();          
    let dataToBeInserted = getArrayOfDatatoInsert();            
    dataToBeInserted.map(async function (data) {                
        let condition = {
            'categorygroup': data.categorygroup,
            'category': data.category,
            'country': data.country,
            'city': data.city
        };
        await csvModel.upsert(data, condition);
    })
    // await restofthestuff();
} catch (error) {
    console.log("error", error);
}

为了进行测试,我选择了一个数据集,其中所有数据都需要更新。

当我运行此方法时:

我可以在(同时打开了连续日志)日志中看到,"existing record updated"消息是为每个期望的输出而存在的每个记录打印的。数据库中仅更新了最后(30)个数据。它在csv.create(values)中起作用的地方

〜我该如何更新所有记录,显然不仅是最后30个数据,任何帮助都将受到赞赏。 〜

  

编辑:显然,我通过使用csv.update(values, {where: condition})而不是使用obj.update(values)来使它起作用。

     

新问题:我没有进一步研究sequelize的更新方法,但这是一个错误还是我在这里做错了什么?

1 个答案:

答案 0 :(得分:0)

如下面的注释代码所详述,您的日志是在您返回之后,因此将永远不会执行。

此外,您没有在异步函数中使用await,因此请不要使其异步或使用await。

csv.upsert = async function (values, condition) {
    const obj = await csv.findOne({ where: condition });
    // you can await here, no need for then as you are in an async function

    if (obj) { // update
        // you need to log before your return condition
        console.log("existing record updated")
        return obj.update(values);
        // since we return here, the rest of the code will not be executed
        // you can skip the use of else
    }
    // we are in this part of the code only if object is falsy

    // insert
    console.log("new record inserted")
    return csv.create(values);
}

您还可以使用Promise.all来确保完成所有upsert:

await Promise.all(dataToBeInserted.map(async function (data) {
    let condition = {
        'categorygroup': data.categorygroup,
        'category': data.category,
        'country': data.country,
        'city': data.city
    };
    await csvModel.upsert(data, condition);
}))

这还将确保如果发生错误,则您的try / catch会捕获到该错误

也许这将帮助您找到导致意外行为的原因。