首页 > 解决方案 > NodeJs MySql 多次更新

问题描述

我在 NodeJs 中有一个使用 Express 框架的方法,其中我正在迭代一个数组并在 Mysql DB 中进行更新
代码接收一个 Connection 对象和一个 Post Body,
Post Request Body 是一个对象数组,数据要保存在数据库中,
我正在尝试一个一个地循环对象并使用 Update Query 将它们保存在数据库中

现在奇怪的是,代码只有在立即被调用两次时才有效
即。在测试中我发现,为了让代码保存数据,我必须发出两次 API 请求。

我在第一次 API 调用时收到以下错误 -

Error Code: 1205. Lock wait timeout exceeded; try restarting transaction

这是一个简单的更新调用,我检查了 MySql 进程,没有死锁,

SHOW FULL PROCESSLIST;

但是相同的代码在立即的第二个 API 调用中起作用。

let updateByDonationId = async (conn, requestBody, callback) => {

    let donations = [];
    donations = requestBody.donations;

    //for(let i in donations){
    async.each(donations, function(singleDonation, callback) {
        //let params = donations[i];
        let params = singleDonation;

        let sqlData = []
        let columns = "";

        if(params.current_location != null){
            sqlData.push(params.current_location);
            columns += "`current_location` = ?,";
        }
        if(params.destination_location != null){
            sqlData.push(params.destination_location);
            columns += "`destination_location` = ?,";
        }

        if(columns != ''){
            columns = columns.substring(0,columns.length-1);

            let sqlQuery = 'UPDATE donation_data SET '+columns
            +' WHERE donation_id = "' + params.donation_id + '"';

            conn.query(sqlQuery, sqlData, function (err, result) {
                logger.info(METHOD_TAG, this.sql);
                if (err) {
                    logger.error(METHOD_TAG, err);
                    return callback(err, false);
                }
            })
        }
        else{
            return callback(null, false);
        }
        columns = "";
        sqlData = [];
    },
    function(err, results) {
        if (err) {
            logger.error(METHOD_TAG, err);
            return callback(err, false);
        }
        else{
           return callback(null, true);
        }
    });
    //return callback(null, true);

} // END

还提到以下内容,我猜他也因为奇怪的原因得到了 ER_LOCK_WAIT_TIMEOUT - NodeJS
+ mysql:使用连接池导致死锁表


正如正确指出的那样,问题似乎与 Node 的非阻塞异步性质有关
任何人都可以帮助提供正确的代码吗?

标签: mysqlnode.js

解决方案


I'd say the asynchronous nature of Node.js is going to be causing you issues here. You can try rewriting your loop. You can either use promises or the async.eachSeries method.

Try changing your loop to use the below:

        async.eachSeries(donations, function(singleDonation, callback) { 

推荐阅读