[英]Queuing using socket.io
我正在使用node.js每10秒查询一次MySQL数据库表。 使用socket.io,每隔10秒查询一次数据库后,每个连接的浏览器将从该查询中接收到唯一的一行行。
问题:使用我实施此方法的方式,每隔10秒就有一个以上的浏览器接收相同的行集。 我使用了一些检出系统(如下所示)来标记已经发送到另一个浏览器的行,但是它似乎并不能一直工作。 如何保证每个浏览器每次都获得唯一的行集?
换句话说,其他浏览器同时查询数据库比锁定行要快!
实作
每隔10秒就会发生以下情况
SELECT * FROM table WHERE checkout = 0
io.sockets.send
向所有连接的浏览器io.sockets.send
一条消息,指出行可用 socket.emit('ready')
响应 ready
发射,再次查询数据库以选择3行,然后更新表以将这3行的checkout
列设置为1
显然,与第一个浏览器使用checkout = 1
更新行相比,第二个浏览器引发SELECT...
查询的时间似乎更少。 还有另一种方法可以进行此排队吗?
屏幕截图
正如您在同时打开两个浏览器的屏幕快照中看到的那样,通常两个浏览器都将获得相同的行集。 如图所示,这些行的id是console.log
。
码
Node.js
io.sockets.on('connection', function(socket) {
// Client ready to take jobs after receiving broadcast
socket.on('ready', function() {
getListings(function(listings) {
socket.emit('job', listings); // send jobs
});
});
});
var getListings = function(callback) {
client.query('SELECT * FROM table ' +
'WHERE job_checkout = 0 ' +
'ORDER BY listing_id ASC ' +
'LIMIT 0, 3',
function(error ,results, fields) {
if (error)
throw error;
// Checkout listing now!
checkoutListings(results);
callback(results);
});
};
var checkoutListings = function(listings) {
for (var i = 0; i < listings.length; i++) {
checkoutListing(listings[i]);
}
}
var checkoutListing = function(listing) {
client.query('UPDATE table ' +
'SET job_checkout = 1 ' +
'WHERE listing_id = ?',
[ listing.listing_id ]);
}
一种简单的解决方案(如果性能不是大问题)是一种事务,它锁定您触摸要读取的每一行-如果其他任何人试图在您的选择和插入之间进行读取,那么他们将不得不等到您的锁定被释放为止
在选择行之前更新它们。 例如
update table
set job_checkout = uniqueNumber
where job_checkout = 0
limit 10
uniqueNumber可以是进程/线程ID,也可以是浏览器客户端ID,也可以是在node.js环境中适合的东西(我不熟悉)。 现在,选择具有唯一job_checkout的行。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.