【发布时间】:2020-11-24 21:45:35
【问题描述】:
抱歉,如果我遗漏了什么,但我进行了一些搜索,但找不到明显的答案。我有一个系统,其中多个工作人员共享一个 postgres 表,这些工作人员需要根据 ID 更新一些行以表示某些操作已完成。因此,两个工作人员会尝试更新相同的行是非常合理的。
我的表格的简化版本如下所示,三个字段分别是 int、bool 和 timestamp:
+----+-------+--------------------------+
| id | done | done_timestamp |
+----+-------+--------------------------+
| 1 | false | null |
| 2 | false | null |
| 3 | true | 2020-11-24T21:23:04.008Z |
+----+-------+--------------------------+
我有一个更新函数,我想用它来更新所有传入的行,但不是任何已经标记为完成的行。它看起来像这样:
UPDATE operations AS o
SET done = TRUE,
done_timestamp = o2.done_timestamp
FROM (VALUES (1, NOW()), (2, NOW()), (3, NOW())) AS o2(id, done_timestamp)
WHERE o2.id = o.id AND NOT o.done;
到目前为止一切顺利。我正在更新三行中的 2 行,而我没有更新第 3 行,因为有些事情已经完成了,我不想在那里更新时间戳。这是我在桌子上得到的:
+----+------+--------------------------+
| id | done | done_timestamp |
+----+------+--------------------------+
| 1 | true | 2020-11-24T21:38:29.871Z |
| 2 | true | 2020-11-24T21:38:29.871Z |
| 3 | true | 2020-11-24T21:23:04.008Z |
+----+------+--------------------------+
最后一个难题是我想返回所有已更新的 ID,以便我可以执行一些错误检查。我的第一个想法是添加 RETURNING 语句,但这样做,我只返回此查询已更新的 id,而不是所有已完成的行。查询如下:
UPDATE operations AS o
SET done = TRUE,
done_timestamp = o2.done_timestamp
FROM (VALUES (1, NOW()), (2, NOW()), (3, NOW())) AS o2(id, done_timestamp)
WHERE o2.id = o.id AND NOT o.done
RETURNING o.id;
有没有人有一个好的方法来返回与我传入的 id 匹配的行的 所有 id,并且也被标记为已完成,而不仅仅是那些已经完成的在我的更新查询中特别更新?
提前致谢, F
【问题讨论】:
-
psql是 Postgres 命令行客户端,真的和问题无关。您想知道“如果条件为 ...,则 Postgresql 更新”。请更改标题以使这个问题更清楚。 -
啊,抱歉。我是 Postgres 的新手,并认为
psql只是一个缩写,以使其不那么冗长。已更新。 -
谢谢。 Postgres 将是名称的“官方”缩写版本。
标签: sql postgresql sql-update