再会。我READ COMMITTED
在 postgres 中使用隔离级别,发现不符合官方文档的奇怪行为。假设我有一张桌子account(id int,name text,amount int)
和两行。
test> select * from account;
-[ RECORD 1 ]-------------------------
id | 1
name | Bob
amount | 800
-[ RECORD 2 ]-------------------------
id | 2
name | Bob
amount | 200
现在我开始两个 READ COMMITTED 事务。第一个执行以下查询
UPDATE account set amount = 100 where id = 2; -- 1
然后第二个执行这个查询
UPDATE account set amount = amount+50 --2
where name in
(select DISTINCT name from account group by
name having sum(amount)>=1000);
现在它被锁定了,因为第一个事务还没有提交。所以第二笔交易要给总金额大于或等于 1000 的每个账户加 50。由于 Bob 有两个账户(800+200),那么它应该给每个账户加 50。但是,现在第一个事务已提交COMMIT; --1
,现在 Bob 总共有 900 个,根据文档读取提交的事务将
重新评估命令的搜索条件(WHERE 子句)以查看行的更新版本是否仍然匹配搜索条件。如果是这样,第二个更新程序使用该行的更新版本继续其操作
据我了解,第二笔交易将重新评估where 条件并跳过 Bob 的帐户。然而,当第二个事务被提交时,最后的行看起来像这样
id | 1 │
name | Bob │
amount | 850 │
-[ RECORD 3 ]------------------------- │
id | 2 │
name | Bob │
amount | 150
这意味着第二个事务没有重新评估搜索条件并对行应用更新,即使它们与条件不匹配。为什么会这样。我错过了文档中的某些内容吗?