Nodejs 如何使用async.js来实现循环插入数据到数据库并统一汇总操作结果后返回
Nodejs 如何使用async.js来实现循环插入数据到数据库并统一汇总操作结果后返回
大家好,我现在想把一组数据插入数据库中,并且在全部插入数据后统一返回所有数据的插入结果,我听说可以用async.js来实现,但不知道如何使用,请帮一下了。下面是我的一些示例代码,现通过data.length来判读是否执行到最后一条插入命令,但这样是不能保证真正是执行到最后一条的,需要用async.js来重写,请帮忙一下。谢谢!
var data = [ {pid: 1, syncid: ‘a’}, {pid: 2, syncid: ‘b’}, {pid: 3, syncid: ‘c’} ];
function save(table, dataObject, pcallback) { var sql = ‘INSERT INTO ’ + table + ’ SET ?’; pool.acquire(function (error, client) { if (error) { // handle error - this is generally the err from your // factory.create function pcallback(error, null); } else { client.query(sql, dataObject, function (error, rows) { // return object back to pool client.release(); // console.log(‘from callback:’+ee()); pcallback(error, rows); }); } }); }
function callbackFactory(res, syncid, islast) { return function callback(err, result) { if (err) { console.log(‘err:’ + err); //throw err; } result.syncid = syncid; res.write(result.syncid + ‘,’); if (islast) { res.end(); } }; }
function sync_fee(data, res) { var i, pid, syncid, params, islast, callback; for (i = 0; i < data.length; i += 1) { pid = data[i].pid; syncid = data[i].syncid; params = {pid: pid, syncid: syncid}; islast = (i === data.length - 1); callback = callbackFactory(res, syncid, islast); save(‘tfee’, params, callback); } }
当然可以,我们可以使用 async.js
库中的 eachSeries
方法来按顺序处理数组中的每一项,并确保所有的异步操作完成后才返回结果。下面是具体的实现方式:
首先,确保你已经安装了 async.js
库。如果没有安装,可以通过 npm 安装:
npm install async
接下来是修改后的代码:
示例代码
const async = require('async');
const pool = require('./dbPool'); // 假设这是你的数据库连接池模块
var data = [
{ pid: 1, syncid: 'a' },
{ pid: 2, syncid: 'b' },
{ pid: 3, syncid: 'c' }
];
function save(table, dataObject, pcallback) {
var sql = 'INSERT INTO ' + table + ' SET ?';
pool.acquire(function (error, client) {
if (error) {
pcallback(error, null);
} else {
client.query(sql, dataObject, function (error, rows) {
client.release();
pcallback(error, rows);
});
}
});
}
function callbackFactory(res, syncid, islast) {
return function callback(err, result) {
if (err) {
console.log('err:' + err);
}
result.syncid = syncid;
res.write(result.syncid + ',');
if (islast) {
res.end();
}
};
}
function sync_fee(data, res) {
async.eachSeries(data, function(item, eachCallback) {
const { pid, syncid } = item;
const params = { pid, syncid };
const islast = data.indexOf(item) === data.length - 1;
const callback = callbackFactory(res, syncid, islast);
save('tfee', params, function(err, result) {
if (err) {
eachCallback(err);
} else {
eachCallback(null, result);
}
});
}, function(err) {
if (err) {
console.error('Error during insertion:', err);
res.end('Error during insertion');
} else {
res.end('All data inserted successfully');
}
});
}
// 假设这是一个HTTP响应的回调函数
function httpResponseHandler(req, res) {
sync_fee(data, res);
}
module.exports = httpResponseHandler;
解释
-
引入
async.js
:const async = require('async');
-
定义
sync_fee
函数:- 使用
async.eachSeries
遍历data
数组。 - 对于数组中的每个元素,调用
save
函数进行数据库插入操作。 - 每次插入操作完成后,调用
callbackFactory
创建一个回调函数,并传递给save
函数。
- 使用
-
callbackFactory
函数:- 创建一个回调函数,用于处理每个插入操作的结果,并根据当前插入操作是否为最后一个操作来决定是否结束响应。
-
save
函数:- 这个函数负责执行数据库插入操作,并在完成时调用回调函数。
-
错误处理:
- 在
async.eachSeries
的最终回调函数中处理可能发生的错误,并在响应中返回相应的信息。
- 在
通过这种方式,你可以确保所有的数据都已成功插入到数据库中,并且只有在所有操作完成后才会返回最终的结果。
var opt_result = []; async.eachLimit(items, function (item, callback) { do_your_db_opt(item, function(){ opt_result.push(item_result); callback(); }); }, function (err) { review_your_result(opt_result); });
谢谢,现在可以了,我用map来实现,map不需要自定义一个数据来接收返回值,在他的回调函数中会把每次的返回值都存起来,一次性返回。
代码类似这样:
exports.sync=function(requestcode,data,res,next){
async.mapLimit(data,10,function(item,callback){
if(item.pid!=undefined || item.pid!=’’){
callback(null,item.pid); //判断传入的数据,每次返回pid值
}else{
callback(null,item.name); //判断传入的数据,每次返回name值
}
},function(err,results){
res.send(results.join()); //异步执行完data数组中的所有数据后,把每次调用的结果自动组合成数组一次性返回
});
return next();
}
为了使用 async.js
实现循环插入数据到数据库并统一汇总操作结果后返回,我们可以使用 async.eachSeries
方法。该方法可以确保数组中的每个元素都按顺序处理,并且只有在完成当前元素的操作后才会处理下一个元素。
以下是修改后的代码示例:
const async = require('async');
const pool = require('./databasePool'); // 假设这是你的数据库连接池
var data = [
{ pid: 1, syncid: 'a' },
{ pid: 2, syncid: 'b' },
{ pid: 3, syncid: 'c' }
];
function save(table, dataObject, pcallback) {
const sql = 'INSERT INTO ' + table + ' SET ?';
pool.acquire(function (error, client) {
if (error) {
pcallback(error, null);
} else {
client.query(sql, dataObject, function (error, rows) {
client.release();
pcallback(error, rows);
});
}
});
}
function callbackFactory(res, syncid, islast) {
return function callback(err, result) {
if (err) {
console.log('err:' + err);
}
result.syncid = syncid;
res.write(result.syncid + ',');
if (islast) {
res.end();
}
};
}
function sync_fee(data, res) {
async.eachSeries(data, (item, callback) => {
const { pid, syncid } = item;
const params = { pid, syncid };
save('tfee', params, (err, result) => {
callback(err);
});
}, (err) => {
if (err) {
console.log('An error occurred:', err);
} else {
res.end(); // 所有数据已成功插入
}
});
}
// 使用示例
const res = {
write: (chunk) => console.log(chunk),
end: () => console.log('All data inserted.')
};
sync_fee(data, res);
在这个示例中,async.eachSeries
确保 data
数组中的每个元素按顺序处理。save
函数用于执行插入操作,并在回调函数中调用 callback
来表示当前元素的处理完成。当所有元素处理完成后,最终的回调函数会被调用,此时所有的插入操作已经完成,可以返回汇总的结果。