1

我正在使用 node.js、node-postgres 和 Postgres 组合一个脚本来处理来自表的大量数据。我也在使用集群模块,所以我不会被单线程困住。

我不希望集群中的一个子进程复制另一个子进程的处理。如何更新我刚刚从选择查询中收到的行,而不可能另一个进程或查询也选择了相同的行?

我假设我的 SQL 查询看起来像:

BEGIN;
SELECT * FROM mytable WHERE ... LIMIT 100;
UPDATE mytable SET status = 'processing' WHERE ...;
COMMIT;

对我对 Postgres 和 SQL 的了解不足表示歉意,我以前在一个简单的 PHP Web 应用程序中使用过它一次,而以前从未使用过 node.js。

4

2 回答 2

1

如果您使用的是多线程应用程序,则不能也不应该使用“for Update”(无论如何在主线程中)您需要使用的是咨询锁。每个线程可以查询一行或多行,验证它们没有被锁定,然后锁定它们,这样其他会话就不会使用它们。在每个线程中就像这样简单:

select * from mytab
where pg_try_advisory_lock(mytab.id)
limit 100

最后确保使用 pg_advisory_unlock 释放锁

于 2015-01-02T13:36:52.823 回答
0
BEGIN;
UPDATE mytable SET status = 'processing' WHERE status <> "processing" and id in 
( selecy ID FROM mytable where status <> "processing" limit 100) returning * ;
COMMIT;

如果其他查询正在处理相同的行,则有可能会失败,因此如果遇到错误,请重试,直到获得一些数据或没有返回行。

如果你得到零行,要么你已经完成,要么在那里;有太多像你这样的其他同时处理。

于 2015-01-05T01:43:42.043 回答